Description
Description
As a developer migrating to Vite I want HMR to work with circular imports.
HMR currently fallbacks to full-reload when an exception is thrown during import:
vite/packages/vite/src/client/client.ts
Lines 159 to 167 in 2bc5d3d
This happens when modules with the isWithinCircularImport
flag are imported in a different than the original order.
Example:
Main
importsLinks
Links
importsPageA
,PageB
, ...PageA
importsLinks
PageB
importsLinks
- ...
Simplified content of the Links
module:
import PageA from "./PageA";
import PageB from "./PageB";
export const pageA = defineLink(PageA);
export const pageB = defineLink(PageB);
...
Modules PageA
, PageB
, ... define pages with their parameters and render links to other pages.
When Links
is changed, HMR posts js-update
with Links
, which is fine.
However, when PageA
is changed, HMR posts js-update
with PageA
, which fails with ReferenceError: Cannot access 'UsersPage' before initialization
. (The exception is thrown because PageA
imports the invalidated module Links
, which references to PageA
that has not yet been initialized.)
Suggested solution
The solution is to change HMR so that it imports modules in the same order as they were initially imported.
For the example above:
When PageA
is changed, send js-update
with Links
instead of PageA
.
Alternative
No response
Additional context
I found the following PRs that attempts to address HMR issues with circular imports:
- feat(hmr): improve circular import updates #14867
- feat(hmr): reload for circular imports only if error #15118
And the following issues:
- HMR should handle cyclic dependencies #10208 (comment)
- Circular imports bring a poor experience to users #14975 (comment)
- Hot Reload not working #15053 (comment)
Validations
- Follow our Code of Conduct
- Read the Contributing Guidelines.
- Read the docs.
- Check that there isn't already an issue that request the same feature to avoid creating a duplicate.