Skip to content
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

Circular imports in HMR #16580

Open
4 tasks done
n9 opened this issue May 2, 2024 · 0 comments
Open
4 tasks done

Circular imports in HMR #16580

n9 opened this issue May 2, 2024 · 0 comments

Comments

@n9
Copy link

n9 commented May 2, 2024

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:

if (isWithinCircularImport) {
importPromise.catch(() => {
console.info(
`[hmr] ${acceptedPath} failed to apply HMR as it's within a circular import. Reloading page to reset the execution order. ` +
`To debug and break the circular import, you can run \`vite --debug hmr\` to log the circular dependency path if a file change triggered it.`,
)
pageReload()
})
}

This happens when modules with the isWithinCircularImport flag are imported in a different than the original order.

Example:

  • Main imports Links
  • Links imports PageA, PageB, ...
  • PageA imports Links
  • PageB imports Links
  • ...

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:

And the following issues:

Validations

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

1 participant