You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
I am not an expert in nextjs, and I don't quite get how it avoids FOUC (Flash of Unstyled Content) problem, as (at least in this example) instead of inlining styles in <head> it only ads <link preload ... >.
Question is does nextjs somehow block render until styles are loaded or not?
Yesterday I investigated it a bit and found out that Next simply places display: none; on <body> until everything is loaded. I believe that is not a good idea for a production application (slow FCP and so on), so I'm planning on writing some plugin which will somehow bundle css on remote in a way that it can be easily consumed on host to be injected in html on server-side.
If anyone here faces the same issue, I hope we can discuss solutions here despite it does not directly relate to node-mf lib and this particular repository.
Ah, was not aware of this behavior on the next.js side. I think for SSR it is more complicated to ensure that contents can be shown only after everything was loaded successfully. Interested in your solution.
Coming back at the issue. As to anyone interested, we managed to solve the remotes CSS issue in the Vue 3 SSR by inlining the styles programmatically on the server.
It might not be the most optimal solution, as inlining styles isn't as good as using extracted CSS. Anyways, the general process for solving the issue for Vue 3 SFC is:
Use the webpack loader to inject CSS into your component's generated code. I did it by adding a injectStyles function which would require all the component's styles and inject them into the renderer context.
The injectStyles function is then linked to the component lifecycle hook which you know would be executed on the server (beforeCreate for Vue). It is important to have access to SSR context inside the component. In Vue 3 it is done by invoking useSSRContext().
Create a renderer context and pass it to the application (e.g. app = createSSRApp(); html = renderToString(app, ctx)).
After rendering, the styles will be on ctx.styles.
By the way, all the mentioned steps are implemented in Vue 2 already (make sure you have vue-loader v15), but not in Vue 3 (vue-loader v16 doesn't support it, that's pity). For Vue 3, you need to manually add vue-style-loader to automatically collect the styles into a convenient format (of course, you can collect the output of CSSLoader yourself).
I believe as soon as you treat the remote components as render + script + styles (instead of just render + script which is the default behavior of vue-loader@16), it is a relatively straightforward task.
Activity
fatawesome commentedon Aug 18, 2021
Yesterday I investigated it a bit and found out that Next simply places
display: none;on<body>until everything is loaded. I believe that is not a good idea for a production application (slow FCP and so on), so I'm planning on writing some plugin which will somehow bundle css on remote in a way that it can be easily consumed on host to be injected in html on server-side.If anyone here faces the same issue, I hope we can discuss solutions here despite it does not directly relate to
node-mflib and this particular repository.telenko commentedon Aug 18, 2021
Ah, was not aware of this behavior on the next.js side. I think for SSR it is more complicated to ensure that contents can be shown only after everything was loaded successfully. Interested in your solution.
phoenix-ru commentedon Oct 14, 2021
Coming back at the issue. As to anyone interested, we managed to solve the remotes CSS issue in the Vue 3 SSR by inlining the styles programmatically on the server.
It might not be the most optimal solution, as inlining styles isn't as good as using extracted CSS. Anyways, the general process for solving the issue for Vue 3 SFC is:
injectStylesfunction which would require all the component's styles and inject them into the renderer context.injectStylesfunction is then linked to the component lifecycle hook which you know would be executed on the server (beforeCreatefor Vue). It is important to have access to SSR context inside the component. In Vue 3 it is done by invokinguseSSRContext().app = createSSRApp(); html = renderToString(app, ctx)).ctx.styles.By the way, all the mentioned steps are implemented in Vue 2 already (make sure you have vue-loader v15), but not in Vue 3 (vue-loader v16 doesn't support it, that's pity). For Vue 3, you need to manually add vue-style-loader to automatically collect the styles into a convenient format (of course, you can collect the output of CSSLoader yourself).
I believe as soon as you treat the remote components as render + script + styles (instead of just render + script which is the default behavior of vue-loader@16), it is a relatively straightforward task.