Hydration failed: server HTML didn't match the client (Next.js)
Error: Hydration failed because the server rendered HTML didn't match the client.In one sentence: The page Next.js rendered on the server looked different from what React rendered in the browser.
What it means
Next.js renders your page to HTML on the server, then React "hydrates" it in the browser by rendering again and attaching event handlers. If the two renders produce different HTML, React complains.
This is usually caused by something that's different between server and browser: the current time, random numbers, `window`/`localStorage`, or invalid HTML nesting.
Common causes
- Rendering `new Date()`, `Date.now()` or `Math.random()` directly in JSX.
- Reading `window`, `localStorage` or `navigator` during render (they don't exist on the server).
- Invalid HTML nesting, like a `<div>` inside a `<p>`, or a `<a>` inside another `<a>`.
- Browser extensions (Grammarly, translators, password managers) modifying the page before React loads.
How to fix it
- Move browser-only values into `useEffect` so they're set after hydration.
- Fix invalid nesting: change the outer `<p>` to a `<div>`.
- For a component that can only run in the browser, load it with `dynamic(() => import('./X'), { ssr: false })` from a client component.
- Test in an incognito window with extensions off to rule them out. Use `suppressHydrationWarning` only for a single unavoidable text difference like a timestamp.
Before
export default function Clock() {
return <span>{new Date().toLocaleTimeString()}</span>;
}After
"use client";
import { useEffect, useState } from "react";
export default function Clock() {
const [time, setTime] = useState("");
useEffect(() => setTime(new Date().toLocaleTimeString()), []);
return <span>{time}</span>;
}Prompt to paste into your AI tool
Next.js shows a hydration mismatch. Find anything that renders differently on server vs client (dates, random values, window/localStorage, invalid HTML nesting) and move it into useEffect or fix the nesting. Don't just add suppressHydrationWarning everywhere.Still stuck?
Paste your exact error and code. Get a plain-English explanation free, or the full fix for $5.
Related errors
- TypeError: Cannot read properties of undefined
- CORS error: blocked by CORS policy
- Module not found: Can't resolve '...'
- Supabase: new row violates row-level security policy
Weekly: the errors breaking vibe-coded apps and how to fix them. Free.
No spam. Unsubscribe anytime.