summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--cli/tests/integration_tests.rs32
-rw-r--r--cli/tests/subdir/subdir2/dynamic_import.ts6
-rw-r--r--deno_typescript/README.md11
-rw-r--r--deno_typescript/system_loader.js21
4 files changed, 69 insertions, 1 deletions
diff --git a/cli/tests/integration_tests.rs b/cli/tests/integration_tests.rs
index 8342da108..98c564b4d 100644
--- a/cli/tests/integration_tests.rs
+++ b/cli/tests/integration_tests.rs
@@ -491,6 +491,38 @@ fn bundle_js() {
}
#[test]
+fn bundle_dynamic_import() {
+ let dynamic_import =
+ util::root_path().join("cli/tests/subdir/subdir2/dynamic_import.ts");
+ assert!(dynamic_import.is_file());
+ let t = TempDir::new().expect("tempdir fail");
+ let bundle = t.path().join("dynamic_import.bundle.js");
+ let mut deno = util::deno_cmd()
+ .current_dir(util::root_path())
+ .arg("bundle")
+ .arg(dynamic_import)
+ .arg(&bundle)
+ .spawn()
+ .expect("failed to spawn script");
+ let status = deno.wait().expect("failed to wait for the child process");
+ assert!(status.success());
+ assert!(bundle.is_file());
+
+ let output = util::deno_cmd()
+ .current_dir(util::root_path())
+ .arg("run")
+ .arg(&bundle)
+ .output()
+ .expect("failed to spawn script");
+ // check the output of the test.ts program.
+ assert!(std::str::from_utf8(&output.stdout)
+ .unwrap()
+ .trim()
+ .ends_with("Hello"));
+ assert_eq!(output.stderr, b"");
+}
+
+#[test]
fn repl_test_console_log() {
let (out, err) = util::run_and_collect_output(
true,
diff --git a/cli/tests/subdir/subdir2/dynamic_import.ts b/cli/tests/subdir/subdir2/dynamic_import.ts
new file mode 100644
index 000000000..a8921390d
--- /dev/null
+++ b/cli/tests/subdir/subdir2/dynamic_import.ts
@@ -0,0 +1,6 @@
+(async (): Promise<void> => {
+ const { printHello } = await import("../mod2.ts");
+ printHello();
+})();
+
+export {};
diff --git a/deno_typescript/README.md b/deno_typescript/README.md
index 220b04ae4..8ab969c78 100644
--- a/deno_typescript/README.md
+++ b/deno_typescript/README.md
@@ -34,6 +34,17 @@ module specifier, a reference to the dynamic `import()` and the equivalent of
and its value, or an object record of keys of the named exports and the values
of the exports.
+Currently, TypeScript does not re-write dynamic imports which resolve to static
+strings (see
+[microsoft/TypeScript#37429](https://github.com/microsoft/TypeScript/issues/37429)),
+which means the import specifier for a dynamic import which has been
+incorporated in the bundle does not automatically match a module specifier that
+has been registered in the bundle. The `di()` function provides the capability
+to try to identify relative import specifiers and resolve them to a specifier
+inside the bundle. If it does this, it resolves with the exports of the module,
+otherwise it simply passes the module specifier to `import()` and returns the
+resulting promise.
+
The running of the factories is handled by `rF()`. When the factory is run, it
returns an object with two keys, `execute` and `setters`. `execute` is a
function which finalises that instantiation of the module, and `setters` which
diff --git a/deno_typescript/system_loader.js b/deno_typescript/system_loader.js
index b5b10af48..0004d055d 100644
--- a/deno_typescript/system_loader.js
+++ b/deno_typescript/system_loader.js
@@ -15,10 +15,29 @@ let System, __instantiateAsync, __instantiate;
},
};
+ async function dI(mid, src) {
+ let id = mid.replace(/\.\w+$/i, "");
+ if (id.includes("./")) {
+ const [o, ...ia] = id.split("/").reverse(),
+ [, ...sa] = src.split("/").reverse(),
+ oa = [o];
+ let s = 0,
+ i;
+ while ((i = ia.shift())) {
+ if (i === "..") s++;
+ else if (i === ".") break;
+ else oa.push(i);
+ }
+ if (s < sa.length) oa.push(...sa.slice(s));
+ id = oa.reverse().join("/");
+ }
+ return r.has(id) ? gExpA(id) : import(mid);
+ }
+
function gC(id, main) {
return {
id,
- import: async (id) => r.get(id)?.exp,
+ import: (m) => dI(m, id),
meta: { url: id, main },
};
}