@nuxt/docs-nightly 4.0.2-29220245.c4317e05 → 4.0.2-29224087.d4d04725

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,188 @@
1
+ ---
2
+ navigation.title: 'Nuxt and hydration'
3
+ title: Nuxt and hydration
4
+ description: Why fixing hydration issues is important
5
+ ---
6
+
7
+ When developing, you may face hydration issues. Don't ignore those warnings.
8
+
9
+ # Why is it important to fix them?
10
+
11
+ Hydration mismatches are not just warnings - they are indicators of serious problems that can break your application:
12
+
13
+ ## Performance Impact
14
+
15
+ - **Increased time to interactive**: Hydration errors force Vue to re-render the entire component tree, which will increase the time for your Nuxt app to become interactive
16
+ - **Poor user experience**: Users may see content flashing or unexpected layout shifts
17
+
18
+ ## Functionality Issues
19
+
20
+ - **Broken interactivity**: Event listeners may not attach properly, leaving buttons and forms non-functional
21
+ - **State inconsistencies**: Application state can become out of sync between what the user sees and what the application thinks is rendered
22
+ - **SEO problems**: Search engines may index different content than what users actually see
23
+
24
+ # How to detect them
25
+
26
+ ## Development Console Warnings
27
+
28
+ Vue will log hydration mismatch warnings in the browser console during development:
29
+
30
+ ![Screenshot of Vue hydration mismatch warning in the browser console](/assets/docs/best-practices/vue-console-hydration.png)
31
+
32
+ # Common reasons
33
+
34
+ ## Browser-only APIs in Server Context
35
+
36
+ **Problem**: Using browser-specific APIs during server-side rendering.
37
+
38
+ ```html
39
+ <template>
40
+ <div>User preference: {{ userTheme }}</div>
41
+ </template>
42
+
43
+ <script setup>
44
+ // This will cause hydration mismatch!
45
+ // localStorage doesn't exist on the server!
46
+ const userTheme = localStorage.getItem('theme') || 'light'
47
+ </script>
48
+ ```
49
+
50
+ **Solution**: You can use [`useCookie`](/docs/api/composables/use-cookie):
51
+
52
+ ```html
53
+ <template>
54
+ <div>User preference: {{ userTheme }}</div>
55
+ </template>
56
+
57
+ <script setup>
58
+ // This works on both server and client
59
+ const userTheme = useCookie('theme', { default: () => 'light' })
60
+ </script>
61
+ ```
62
+
63
+ ## Inconsistent Data
64
+
65
+ **Problem**: Different data between server and client.
66
+
67
+ ```html
68
+ <template>
69
+ <div>{{ Math.random() }}</div>
70
+ </template>
71
+ ```
72
+
73
+ **Solution**: Use SSR-friendly state:
74
+
75
+ ```html
76
+ <template>
77
+ <div>{{ state }}</div>
78
+ </template>
79
+
80
+ <script setup>
81
+ const state = useState('random', () => Math.random())
82
+ </script>
83
+ ```
84
+
85
+ ## Conditional Rendering Based on Client State
86
+
87
+ **Problem**: Using client-only conditions during SSR.
88
+
89
+ ```html
90
+ <template>
91
+ <div v-if="window?.innerWidth > 768">
92
+ Desktop content
93
+ </div>
94
+ </template>
95
+ ```
96
+
97
+ **Solution**: Use media queries or handle it client-side:
98
+
99
+ ```html
100
+ <template>
101
+ <div class="responsive-content">
102
+ <div class="hidden md:block">Desktop content</div>
103
+ <div class="md:hidden">Mobile content</div>
104
+ </div>
105
+ </template>
106
+ ```
107
+
108
+ ## Third-party Libraries with Side Effects
109
+
110
+ **Problem**: Libraries that modify the DOM or have browser dependencies (this happens a LOT with tag managers).
111
+
112
+ ```html
113
+ <script setup>
114
+ if (import.meta.client) {
115
+ const { default: SomeBrowserLibrary } = await import('browser-only-lib')
116
+ SomeBrowserLibrary.init()
117
+ }
118
+ </script>
119
+ ```
120
+
121
+ **Solution**: Initialise libraries after hydration has completed:
122
+
123
+ ```html
124
+ <script setup>
125
+ onMounted(async () => {
126
+ const { default: SomeBrowserLibrary } = await import('browser-only-lib')
127
+ SomeBrowserLibrary.init()
128
+ })
129
+ </script>
130
+ ```
131
+
132
+ ## Dynamic Content Based on Time
133
+
134
+ **Problem**: Content that changes based on current time.
135
+
136
+ ```html
137
+ <template>
138
+ <div>{{ greeting }}</div>
139
+ </template>
140
+
141
+ <script setup>
142
+ const hour = new Date().getHours()
143
+ const greeting = hour < 12 ? 'Good morning' : 'Good afternoon'
144
+ </script>
145
+ ```
146
+
147
+ **Solution**: Use [`NuxtTime`](/docs/api/components/nuxt-time) component or handle it client-side:
148
+
149
+ ```html
150
+ <template>
151
+ <div>
152
+ <NuxtTime :date="new Date()" format="HH:mm" />
153
+ </div>
154
+ </template>
155
+ ```
156
+
157
+ ```html
158
+ <template>
159
+ <div>
160
+ <ClientOnly>
161
+ {{ greeting }}
162
+ <template #fallback>
163
+ Hello!
164
+ </template>
165
+ </ClientOnly>
166
+ </div>
167
+ </template>
168
+
169
+ <script setup>
170
+ const greeting = ref('Hello!')
171
+
172
+ onMounted(() => {
173
+ const hour = new Date().getHours()
174
+ greeting.value = hour < 12 ? 'Good morning' : 'Good afternoon'
175
+ })
176
+ </script>
177
+ ```
178
+
179
+ ## In summary
180
+
181
+ 1. **Use SSR-friendly composables**: [`useFetch`](/docs/api/composables/use-fetch), [`useAsyncData`](/docs/api/composables/use-async-data), [`useState`](/docs/api/composables/use-state)
182
+ 2. **Wrap client-only code**: Use [`ClientOnly`](/docs/api/components/client-only) component for browser-specific content
183
+ 3. **Consistent data sources**: Ensure server and client uses the same data
184
+ 4. **Avoid side effects in setup**: Move browser-dependent code to `onMounted`
185
+
186
+ ::tip
187
+ You can read the [Vue documentation on SSR hydration mismatch](https://vuejs.org/guide/scaling-up/ssr.html#hydration-mismatch) for a better understanding of hydration.
188
+ ::
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@nuxt/docs-nightly",
3
- "version": "4.0.2-29220245.c4317e05",
3
+ "version": "4.0.2-29224087.d4d04725",
4
4
  "repository": {
5
5
  "type": "git",
6
6
  "url": "git+https://github.com/nuxt/nuxt.git",