1use crate::child;
4use crate::command::build::{BuildProfile, Target};
5use crate::install::{self, Tool};
6use crate::manifest::CrateData;
7use anyhow::{bail, Context, Result};
8use semver;
9use std::path::Path;
10use std::process::Command;
11
12pub fn wasm_bindgen_build(
15 wasm_path: &str,
16 data: &CrateData,
17 install_status: &install::Status,
18 out_dir: &Path,
19 out_name: &Option<String>,
20 disable_dts: bool,
21 weak_refs: bool,
22 reference_types: bool,
23 target: Target,
24 profile: BuildProfile,
25) -> Result<()> {
26 let out_dir = out_dir.to_str().unwrap();
27
28 let dts_arg = if disable_dts {
29 "--no-typescript"
30 } else {
31 "--typescript"
32 };
33 let bindgen_path = install::get_tool_path(install_status, Tool::WasmBindgen)?
34 .binary(&Tool::WasmBindgen.to_string())?;
35
36 let mut cmd = Command::new(&bindgen_path);
37 cmd.arg(&wasm_path)
38 .arg("--out-dir")
39 .arg(out_dir)
40 .arg(dts_arg);
41
42 if weak_refs {
43 cmd.arg("--weak-refs");
44 }
45
46 if reference_types {
47 cmd.arg("--reference-types");
48 }
49
50 let target_arg = build_target_arg(target, &bindgen_path)?;
51 if supports_dash_dash_target(&bindgen_path)? {
52 cmd.arg("--target").arg(target_arg);
53 } else {
54 cmd.arg(target_arg);
55 }
56
57 if let Some(value) = out_name {
58 cmd.arg("--out-name").arg(value);
59 }
60
61 let profile = data.configured_profile(profile);
62 if profile.wasm_bindgen_debug_js_glue() {
63 cmd.arg("--debug");
64 }
65 if !profile.wasm_bindgen_demangle_name_section() {
66 cmd.arg("--no-demangle");
67 }
68 if profile.wasm_bindgen_dwarf_debug_info() {
69 cmd.arg("--keep-debug");
70 }
71 if profile.wasm_bindgen_omit_default_module_path() {
72 cmd.arg("--omit-default-module-path");
73 }
74 if profile.wasm_bindgen_split_linked_modules() {
75 cmd.arg("--split-linked-modules");
76 }
77
78 child::run(cmd, "wasm-bindgen").context("Running the wasm-bindgen CLI")?;
79 Ok(())
80}
81
82fn supports_web_target(cli_path: &Path) -> Result<bool> {
84 let cli_version = semver::Version::parse(&install::get_cli_version(
85 &install::Tool::WasmBindgen,
86 cli_path,
87 )?)?;
88 let expected_version = semver::Version::parse("0.2.39")?;
89 Ok(cli_version >= expected_version)
90}
91
92fn supports_dash_dash_target(cli_path: &Path) -> Result<bool> {
94 let cli_version = semver::Version::parse(&install::get_cli_version(
95 &install::Tool::WasmBindgen,
96 cli_path,
97 )?)?;
98 let expected_version = semver::Version::parse("0.2.40")?;
99 Ok(cli_version >= expected_version)
100}
101
102fn build_target_arg(target: Target, cli_path: &Path) -> Result<String> {
103 if !supports_dash_dash_target(cli_path)? {
104 Ok(build_target_arg_legacy(target, cli_path)?)
105 } else {
106 Ok(target.to_string())
107 }
108}
109
110fn build_target_arg_legacy(target: Target, cli_path: &Path) -> Result<String> {
111 log::info!("Your version of wasm-bindgen is out of date. You should consider updating your Cargo.toml to a version >= 0.2.40.");
112 let target_arg = match target {
113 Target::Nodejs => "--nodejs",
114 Target::NoModules => "--no-modules",
115 Target::Web => {
116 if supports_web_target(cli_path)? {
117 "--web"
118 } else {
119 bail!("Your current version of wasm-bindgen does not support the 'web' target. Please update your project to wasm-bindgen version >= 0.2.39.")
120 }
121 }
122 Target::Bundler => "--browser",
123 Target::Deno => "--deno",
124 };
125 Ok(target_arg.to_string())
126}