-
Notifications
You must be signed in to change notification settings - Fork 29.8k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Top-level await + dynamic import + cyclic import causes "unsettled TLA" error #55468
Comments
Sure but linking is only important for static imports, no? Because static imports need to know in advance the exported names of each dependencies.
The |
@aduh95 Thanks for your explanation.
But I'm just a bit confused that, in "static" cyclic dependencies, for example, // a.js
import { b } from "./b.js";
await new Promise((r) => setTimeout(r, 1000));
console.log("module a loaded");
// b.js
import * as a from "./a.js";
console.log(a);
export const b = 1; The |
Take the following shell script: mkdir repro
cd repro
cat -> a.mjs <<'EOF'
import { b } from "./b.mjs";
await new Promise((r) => setTimeout(r, 1000));
console.log("module a loaded");
EOF
cat -> b.mjs <<'EOF'
import * as a from "./a.mjs";
console.log(a);
export const b = 1;
EOF
echo "a.mjs is the entry point:"
node a.mjs
echo
echo "b.mjs is the entry point:"
node b.mjs
cd ..
rm -rf repro This outputs:
As you can see, the order depends on which is the entry point, and the entry point is always executed last.
Because there's no cyclic module graph when you use dynamic imports. Cyclic module has its own section of the spec, it's not surprising you get different results with static import and dynamic imports. |
This was considered but ultimately rejected as it was favoured that dynamic import should always return a fully evaluated module. Spec-wise, it wouldn't actually be that complicated to have an option to Technically I think it would actually be conforming for hosts to have this behaviour by an import attribute (e.g. I don't know if there's really enough demand that Node (let alone other hosts) would add this (though I have seen basically this exact issue be raised a couple times before, so maybe the demand is high enough, but someone would have to implement it). |
I've encountered this issue because Vite is building TLA + Original source: // main.ts
await import("./module_1");
// module_1.ts
import("./moudle_2"); builds to: // main.js
export const __vite_preload = /* ... */;
await __vite_preload(() => import("./module_1.js"));
// module_1.js
import { __vite_preload } from "./main.js";
__vite_preload(() => import("./module_2.js")); The corresponding Vite issue is vitejs/vite#18156 -- this issue does affect a number of user. |
Version
v22.10.0
Platform
Subsystem
No response
What steps will reproduce the bug?
Create following files:
package.json
:foo.js
:bar.js
:Then run
node foo.js
.How often does it reproduce? Is there a required condition?
Every time.
What is the expected behavior? Why is that the expected behavior?
Outputs
It works!
.import {} from "./foo.js"
doesn't import anything, andfoo.js
has already been linked, so it should not block the evaluation ofbar.js
.What do you see instead?
And the process exited with error code
13
.Additional information
Behavior of other runtime:
It works!
successfully.It works!
successfully.I'm not sure what is the correct behavior that ECMAScript specification defines.
The text was updated successfully, but these errors were encountered: