Subscribe on changes!

SSR: CSS variable with quotes causes [Vue warn]: Hydration text mismatch

avatar
Feb 22nd 2023

Vue version

3.2.47

Link to minimal reproduction

https://stackblitz.com/github/nuxt-contrib/vue3-ssr-starter/tree/main?file=src/App.vue

Steps to reproduce

I am writing a component that loads in css variables like this:

<template>
  <component is="style">
    --test: 'test'
    --test2: "test2"
  </component>
</template>

It works, but I get this warning, because my variables contain quotes:

[Vue warn]: Hydration text mismatch:
- Client: " --test: &#39;test&#39; --test2: &quot;test2&quot; "
- Server: " --test: 'test' --test2: \"test2\" " 
  at <App>

I think, the quotes should result in the same escape sequences on client and server, or this should be ignored.

What is expected?

The css variables render the same way on server and client.

What is actually happening?

The css variables on the client render with different escape sequences than on the server.

System Info

No response

Any additional comments?

No response

avatar
Feb 22nd 2023

The underlying problem seems to be that browsers have special handling for the data property of a text node when it appears as the direct child of some elements. Specifically, <style>, <script>, <noscript> and <iframe>.

Using a <style> or <script> tag directly inside a Vue template isn't allowed, and I'm not sure whether using <component :is> to workaround that is officially supported either. The issue #3890 is already tracking this loophole.

Perhaps <noscript> is a legitimate use case for SSR? I can imagine using Vue on the server-side to generate a <noscript> tag, which then needs to be handled gracefully in the client.

SFC Playground - <noscript> failure

avatar
Jul 14th 2023

Got the same issue using vue-datepicker inline styles

  <component :is="'style'">
    {{ datepickerStyles }}
  </component>

I hope #7776 will be merged some day!