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 ourterms of serviceand privacy statement.We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

handle chunk loading errors that are not triggered by navigation #23612

Open
2 of 4 tasks
nandi95opened this issue Oct 11, 2023 · 16 comments · May be fixed by#28160
Open
2 of 4 tasks

handle chunk loading errors that are not triggered by navigation #23612

nandi95opened this issue Oct 11, 2023 · 16 comments · May be fixed by#28160

Comments

@nandi95
Copy link
Contributor

nandi95 commented Oct 11, 2023

Describe the feature

When a chunk has been given a new name during build as it has changed, some clients will try to load the old chunk name. This results in errors like:

  • TypeError: error loading dynamically imported module:....
  • Importing a module script failed.
  • Failed to fetch dynamically imported module:...

With pages this issue gets detected, and the page reloaded which is necessary.

reloadNuxtApp({path,persistState:true})

However, when I other lazy components that aren't pages, they might fail the same way, but there's have no strategy in place for them, nor can I safely tell the page and another lazy component error apart.

Solutions:

  1. Don't emit app:chunkError for pages as this issue is handled and there's nothing further to be done (This counts as a breaking change, I take it). This would mean the user is free to implement their own error handling strategy.
  2. Perhaps force reload the manifest file and attempt to load the chunk again.
  3. Weave in an argument to the app:chunkError hook that signifies that the chunk is a page or not.

I don't think it would be wise to refresh the page on any and all chunk errors (as a lazy component might not be too critical and it's more important to have a smooth ux).

If nuxt cannot resolve this issue universally, perhaps we could come up with a strategy and some documentation to include in the docs.

Original Issue for this feature:#14594 (comment)

Additional information

  • Would you be willing to help implement this feature?
  • Could this feature be implemented as a module?

Final checks

@danielroe
Copy link
Member

Currently you can setexperimental.emitRouteChunkErrortomanualwhich will call theapp:chunkErrorhook but not handle it at all, which means you can experiment with your own plugin to handle it.

@danielroe danielroe changed the title Chunk loading error. handle chunk loading errors that are not triggered by navigation Oct 11, 2023
@quroom
Copy link

quroom commented Nov 10, 2023

@danielroe

I get the same errorTypeError: Failed to import a dynamically imported module: 'but it is not a related app:chunkError. it catched app:error.
I don't know the reason.

It happens when I click the login button in sidebase/nuxt-auth and then press the back button in window browser, sometimes I get a normal page but sometimes I get the error.

I am using nuxt for product level service.
Is there only solution makding refresh button and clicking it by user manually?
And does it happen in product?

I didn't deploy yet but I would like to know and prevent it.

@quroom
Copy link

quroom commented Nov 10, 2023

As you said, I set but chunk error not catched. So I made own my error catch plugin.
My nuxt version is 3.7.1
Anyway I found workaround.

// plugins/error-handler.ts

exportdefaultdefineNuxtPlugin((nuxtApp)=>{
nuxtApp.hook("app:error",(error,instance,info)=>{
constreoload_error_list=[
"error loading dynamically imported module",
"Importing a module script failed",
"Failed to fetch dynamically imported module",
];
for(constmessageofreoload_error_list){
if(error.message.indexOf(message)>-1){
window.location.reload();
}
}
});
});

It's not real solution but temprory it could help page working properly without all the time manual refresh

PS. In my caseTypeError: Failed to import a dynamically imported module:...is not catched in chunkError. It's handled in app:error.

@tomsdob
Copy link

tomsdob commented Apr 23, 2024

@quroom,do you still use the workaround you provided here and did it solve your issue? I am facing the same issue and I am looking for a fix.

@quroom
Copy link

quroom commented Apr 23, 2024

@quroom,do you still use the workaround you provided here and did it solve your issue? I am facing the same issue and I am looking for a fix.

Yeah. I am using that code still. I haven't seen that chunk error until now after including code that I mentioned.

@AlejandroAkbal

This comment was marked as duplicate.

@gregmsanderson
Copy link

I too found that a lazy-loaded component would not cause any error and would just silently fail without a retry.

I found that the "app:error" hook suggested by@quroomwould not fire.

Insteadthe "app:chunkError" hook is needed. essentially replacing the name of the hook in the code above. That hook is not documented onhttps://nuxt /docs/api/advanced/hooks#app-hooks-runtimebut (as that page suggests) itisin the code:https://github /nuxt/nuxt/blob/main/packages/nuxt/src/app/nuxt.ts#L48and so does work when combined withhttps://nuxt /docs/guide/going-further/experimental-features#emitroutechunkerror.

The app thendoesreload.

However the code above could result in infinite reloads on a network issue (can simulate by simply deleting a chunk) and so I would guess it needs an "attempts" counter in sessionStorage/localStorage and then give up. I assume (?) Nuxt's handler is smart enough to avoid infinite retries. We could look how it does that.

@danielroe danielroe removed the 3.x label Jun 30, 2024
@maxibue
Copy link

maxibue commented Jul 2, 2024

However the code above could result in infinite reloads on a network issue (can simulate by simply deleting a chunk) and so I would guess it needs an "attempts" counter in sessionStorage/localStorage and then give up. I assume (?) Nuxt's handler is smart enough to avoid infinite retries. We could look how it does that.

The code@quroomprovided does in my implementation result in an infinite reload loop so I would advise to use it with caution.

@maxibue
Copy link

maxibue commented Jul 2, 2024

By the way, are there any other/new fixes available? Because none oof the provided solutions helped me fix the error.

@gregmsanderson
Copy link

@maximatically I don't believe the issue itself is fixed, however building on the above example the infinite-reload could perhaps be solved by using Nuxt's own functionreloadNuxtApp().

Fromhttps://nuxt /docs/api/utils/reload-nuxt-appit looks like if/when that's calledagainwithin its default time of 10s, that will be ignored.

Something like:

exportdefaultdefineNuxtPlugin((nuxtApp)=>{
nuxtApp.hook("app:chunkError",(err)=>{
consterror_list=[
"error loading dynamically imported module",
"Importing a module script failed",
"Failed to fetch dynamically imported module",
];
for(constmessageoferror_list){
if(message.indexOf(message)>-1){
console.error("app:chunkError reloading...");

reloadNuxtApp();
}
}
});
});

@maxibue
Copy link

maxibue commented Jul 2, 2024

@maximatically I don't believe the issue itself is fixed, however building on the above example the infinite-reload could perhaps be solved by using Nuxt's own functionreloadNuxtApp().

Fromhttps://nuxt /docs/api/utils/reload-nuxt-appit looks like if/when that's calledagainwithin its default time of 10s, that will be ignored.

Something like:

exportdefaultdefineNuxtPlugin((nuxtApp)=>{
nuxtApp.hook("app:chunkError",(err)=>{
consterror_list=[
"error loading dynamically imported module",
"Importing a module script failed",
"Failed to fetch dynamically imported module",
];
for(constmessageoferror_list){
if(message.indexOf(message)>-1){
console.error("app:chunkError reloading...");

reloadNuxtApp();
}
}
});
});

Sadly this doesn't seem to fix my problems. I think I will leave it for now and once I have time I'll write the nuxt/ui component I'm using from scratch.

@jonkuze
Copy link

jonkuze commented Jul 11, 2024

I'm also facing this issue when deploying my new website built with Nuxt 3 + Nuxt UI Pro to Cloudflare. I can load the homepage just fine if I append a query param. I tried the above work-arounds, but no luck.

Update:I was able to resolve it for now by totally deleting my Cloudflare page project and redeploying. That's pretty rough... hope this gets fixed soon.

@BracketJohn
Copy link
Contributor

@danielroewould you be open to receiving a small PR that adds aemitRouteChunkError: 'automatic-navigation-and-lazy'option which adds a plugin that (in essence):

exportdefaultdefineNuxtPlugin({
name:'nuxt:chunk-reload-navigation-and-lazy',
setup(nuxtApp){
nuxtApp.hook('app:chunkError',()=>{reloadNuxtApp()})
},
})

The PR would also extend docs on this to explain the different trade-offs (eg:navigation-and-lazyleading to more frequent reloads, potentially even without user-interaction).

One potential improvement to this proposal I already see is renaming theautomatic-option toautomatic-navigationand add the new option asautomatic/automatic-complete/automatic-total(as it reloads forallchunkErrors). However, I'm concerned that this would be too breaking (as users already use theautomaticstrategy).

I think this would be useful as many users (see this issue & the many duplicates) seem to encounter the Lazy-chunk error, but don't seem to be comfortable with adding their ownmanualplugin / seem to be unsure whether this implementation would actually solve their problem (although it should, as you agreedheregiven the same proposal by@edwhright above that reply).

If you think this is useful, I'd be happy to open a PR & push it through.

Thanks 💯

@danielroe
Copy link
Member

I would! Thank you for the idea.

@BracketJohn
Copy link
Contributor

Great (: I've opened#28160to implement the proposal.

@maxibue
Copy link

maxibue commented Oct 6, 2024

Great (: I've opened#28160to implement the proposal.

Excited to see this finally fixed! 👀

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