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

fix: document body undefined #518

Merged
merged 7 commits into from
Feb 22, 2024

Conversation

Aslemammad
Copy link
Contributor

Partially resolves #344

When refreshing a waku page (website), the hydration failed and as result, hmr would not work.

The reason behind the failure, is that for the next refreshes, the /main.tsx file is optimized and warm so it gets resolved before the <body> is getting streamed to the browser since it was in the <head> and that loads before the <body>, what that mean is the document.body would be undefined during the hydration and React would throw an error since that is undefined. One solution was to restart the server so we get /main.tsx cold again.

What this PR does is that it puts the script of /main.tsx in the body so it gets resolved after the body is being streamed and as a result, document.body would be never be undefined.

This also fixed the hmr issue after the page manual refresh.

Copy link

vercel bot commented Feb 21, 2024

The latest updates on your projects. Learn more about Vercel for Git ↗︎

Name Status Preview Updated (UTC)
waku ✅ Ready (Inspect) Visit Preview Feb 21, 2024 11:13pm

Copy link

codesandbox-ci bot commented Feb 21, 2024

This pull request is automatically built and testable in CodeSandbox.

To see build info of the built libraries, click here or the icon next to each commit SHA.

server.transformIndexHtml(req.url || '', html).then((content) => {
res.statusCode = 200;
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is not related to the PR, but it's a minor change, since we used to set the status 200 even though the .then might never work and the promise might reject.

So we just bring it when we're sure the promise is getting resolved.

Comment on lines 106 to 112
// enqueue `mainJs` first in the body to avoid the document.body undefined error, before we used to inject it in the head which sometimes made it load before the document.body was loaded
controller.enqueue(
encoder.encode(
`<script src="${config.basePath}${config.srcDir}/${config.mainJs}" async type="module"></script>`,
),
);

Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here, this adds <script ...> multiple times.
npm run examples:dev:04_promise can reproduce it.

Copy link
Owner

@dai-shi dai-shi left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

should be good.

@dai-shi dai-shi merged commit 4400750 into dai-shi:main Feb 22, 2024
28 checks passed
@Aslemammad Aslemammad deleted the fix/document-body-undefined branch February 22, 2024 02:25
@@ -102,6 +104,16 @@ globalThis.__WAKU_PREFETCHED__ = {
if (scriptsClosed) {
return;
}
if (!mainJsSent) {
// enqueue `mainJs` first in the body to avoid the document.body undefined error, before we used to inject it in the head which sometimes made it load before the document.body was loaded
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

My oversight, this should be DEV only, right?

npm run examples:prd:04_promise

image

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This should in general send the mainJs one time, weird error, do you know why that happens?

Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here's the fix #528

main.tsx doesn't exist on PRD, right?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, what exists then if that does not exist? because as far as I checked the website, there was an alternative. And we need that to be in the body too, so the behaviour is normalized between two environments.

Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

it's bundled by vite.

it sounds like you just miss a point. do you understand why we get 404?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

But the error that this PR fixed was reproduced with async too, so I don't think that can always be true and we need to be sure about that.

Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

My understanding is that the issue this PR fixed is for HMR in dev mode. I never see such an issue in PRD.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes it fixed the HMR issue after the refresh in DEV, but I was just concerned how it'd be handled in PRD. That's it. sorry for the confusion.

Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So, my question for you is how Vite+React does it. My guess is that all scripts are in <head>.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yep, they're in the head! because the body is always sent in the initial template (index.html)

dai-shi added a commit that referenced this pull request Feb 23, 2024
dai-shi added a commit that referenced this pull request Feb 23, 2024
@Aslemammad
Copy link
Contributor Author

Aslemammad commented Feb 23, 2024 via email

@dai-shi
Copy link
Owner

dai-shi commented Feb 24, 2024

I think usually document.body is available with "async" script.
Can you try creating Vite+React app and see its built result? All scripts are in <head>, right?

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

Successfully merging this pull request may close these issues.

website: local development issue
2 participants