Suspense unmounts with an error if it renders a component with a root node implementing a client-only behavior
Vue version
3.5.13
Link to minimal reproduction
https://play.vuejs.org/#eNqFU8tu2zAQ/BWWF9uoa6FoT65sNC1yaIG2QV3kxIsqrWQmNCnwoTgQ9O/dFSXZRRLHJ3J3Zji7Grf8qq5XTQC+5qnLraw9c+BDvRVaHmpjPWtZAaXUcOUedf7VYFGD9ktmoWQdK605sBkKzD4JLXRutPOMUGzzLG8+X7DNlkXt+WyVUIcMzBaLMwW3N0EVu715+J+Oqvju3NsABE+T6Bnd4sXDoVaZB7wxlv4N3hvNPudK5vcbwS9IvnmpJ/jWm6pSkCZRLkrvgqtBO2DNO1lekEY64ZFBpXik38FVyLqVHthbdhtA8NhLonwy6uM1Taap+JJ7h+spZbW6c0bjJ2sJL3iO6lKB/VV7iesTfM36DvUypczD975GW1uO9XwP+f0z9Tt3pJrgNxYc2AbNTT2f2QpwKmpf737CEc9T82CKoBB9ofkbnFGBPEbYl6ALtH2G691+68MhdfXHXR89LmIciowSsuvxgmNsaLEvjX6y+2H1secJ3eEWx8hdyrzRP0zQHoqnQaesxWjfWFO7ef8eftI123mLrtFctzhFWbpBachumSnXh1fo6ZHhX9ErTfhVk6kAyKKxEd+9lvhCNmMiJ5FTBPfvt21LPlnXpQneSKHvEC9XmXNIzDN74uBYg0oEJogcIjqd4qOAMw0kbfxIY4+4/jP4WZjpcd79A7O0hXo=
Steps to reproduce
- Click the
togglebutton
What is expected?
The Suspense component unmounts without an error.
What is actually happening?
The Suspense component unmounts, but the app crashes - the error pops up and the toggle button no longer works.
System Info
Any additional comments?
I was trying to implement a loader for async components with some reload logic (retries, reload when connection is restored - things like that). And one of the components had a client-only logic in it: it was rendering the actual content only after the mounted hook. I didn't use the errorComponent/onError from the AsyncComponentOptions because i needed to reload the component again, so i used Suspense and its fallback slot.
I understand that Suspense is experimental and i have been able to resolve this issue in my project by wrapping the template of the async component in a static div, but the issue itself is there.
a workaround
<Suspense v-if="shouldShowAsyncComponent">
+ <div>
<Comp msg="Vite + Vue" />
+ </div>
</Suspense>
see playground
FYI - it's very easy to hit this problem with inertia. Put a <Suspense> in your layout, and your app will crash with Unhandled error during execution of component update and Failed to execute 'insertBefore' on 'Node'. Only when visiting non-async inertia pages.
Just add the magic <div> wrapper as a workaround. Thanks all, we love vue