summaryrefslogtreecommitdiff
path: root/core/runtime.rs
diff options
context:
space:
mode:
Diffstat (limited to 'core/runtime.rs')
-rw-r--r--core/runtime.rs31
1 files changed, 25 insertions, 6 deletions
diff --git a/core/runtime.rs b/core/runtime.rs
index 97c822848..f82f06207 100644
--- a/core/runtime.rs
+++ b/core/runtime.rs
@@ -886,13 +886,28 @@ impl JsRuntime {
// Dynamic module loading - ie. modules loaded using "import()"
{
- let poll_imports = self.prepare_dyn_imports(cx)?;
- assert!(poll_imports.is_ready());
+ // Run in a loop so that dynamic imports that only depend on another
+ // dynamic import can be resolved in this event loop iteration.
+ //
+ // For example, a dynamically imported module like the following can be
+ // immediately resolved after `dependency.ts` is fully evaluated, but it
+ // wouldn't if not for this loop.
+ //
+ // await delay(1000);
+ // await import("./dependency.ts");
+ // console.log("test")
+ //
+ loop {
+ let poll_imports = self.prepare_dyn_imports(cx)?;
+ assert!(poll_imports.is_ready());
- let poll_imports = self.poll_dyn_imports(cx)?;
- assert!(poll_imports.is_ready());
+ let poll_imports = self.poll_dyn_imports(cx)?;
+ assert!(poll_imports.is_ready());
- self.evaluate_dyn_imports();
+ if !self.evaluate_dyn_imports() {
+ break;
+ }
+ }
self.check_promise_exceptions()?;
}
@@ -1505,7 +1520,9 @@ impl JsRuntime {
}
}
- fn evaluate_dyn_imports(&mut self) {
+ // Returns true if some dynamic import was resolved.
+ fn evaluate_dyn_imports(&mut self) -> bool {
+ let mut resolved_any = false;
let state_rc = Self::state(self.v8_isolate());
let mut still_pending = vec![];
let pending =
@@ -1536,6 +1553,7 @@ impl JsRuntime {
};
if let Some(result) = maybe_result {
+ resolved_any = true;
match result {
Ok((dyn_import_id, module_id)) => {
self.dynamic_import_resolve(dyn_import_id, module_id);
@@ -1547,6 +1565,7 @@ impl JsRuntime {
}
}
state_rc.borrow_mut().pending_dyn_mod_evaluate = still_pending;
+ resolved_any
}
/// Asynchronously load specified module and all of its dependencies.