We use cookies. Privacy Policy

    PageGlass - JavaScript SEO Rendering for React & Vue Sites

    Next.js SEO: keep your routes indexed even when you ship Client Components

    Next.js can serve fully-rendered HTML, but the moment a route is marked 'use client' or fetches data with useEffect, Googlebot reads an empty shell. Hydration takes seconds; crawlers don't wait.

    This is a known problem, and the fix is simpler than you think.

    100+ bots supportedPre-rendered by PageGlassFive-minute setupBuilt on Cloudflare's edge
    Paste your Next.js site's URL above to see what Googlebot sees on the first request, before hydration.

    Don't want an external tool? We understand.

    If you're prepared to refactor every interactive route into a Server Component, move data fetching into loaders, and rebuild any state machines that assume the browser exists, that's the right long-term answer. PageGlass is the five-minute bridge for the routes you don't have time to rewrite.

    Fix this in three steps

    1. Run a free Next.js scan. Confirm the bot visibility gap caused by Next.js client component rendering - the scan takes ten seconds and needs no signup. You get exactly what Googlebot, Bingbot, and the AI crawlers see when they hit your URLs today, side by side with what your users see.
    2. Add one CNAME record. Point your Next.js site's domain through PageGlass in your DNS provider. The change takes thirty seconds and is fully reversible. Zero code changes, no deploy, no impact on the bundle your real users download.
    3. Next.js content is now indexable. Bot traffic now receives fully-rendered HTML for every URL on your Next.js site, while human visitors keep getting the exact same dynamic experience as before. Come back to PageGlass and run the scan again to confirm the fix.

    Where Next.js SEO actually breaks

    Next.js gets credit for being SEO-friendly, and it deserves it - but only for the parts of your application that are Server Components or use the Pages Router data-fetching APIs. The moment you mark a page or layout with 'use client', every component below that boundary renders in the browser. Googlebot still receives HTML, but it's the App Router's streaming shell, not your content.

    The most common pattern that breaks is dashboards or detail pages that load data with useEffect + fetch or with useSWR. These run after the React tree mounts, which means the crawler sees the loading skeleton, not the data.

    Common Next.js fixes that don't actually work

    • Setting metadata via useEffect. The effect runs after hydration. Crawlers reading the initial HTML never see the title or description you set this way.
    • next/head inside a 'use client' component. Deferred until hydration. Same outcome as the useEffect pattern.
    • Server Component with a client-only child that owns the data. Looks server-rendered in the parent, but the heading, list, or table that crawlers care about is filled in only after the client child fetches and renders. The shell is server-rendered; the content isn't.
    • Trusting Search Console URL inspection. The inspection tool runs Google's full rendering service, which executes JavaScript. A page can pass URL inspection and still be invisible to the first-pass crawler that decides whether to render at all.

    What actually works

    Three paths: (1) refactor each affected route to a Server Component with server-side data fetching, which is the official answer but a real time cost; (2) move to generateStaticParams + ISR for routes with stable data, accepting that personalised routes still need another solution; or (3) use PageGlass to detect bot user-agents at the edge and serve a fully-rendered HTML version of every route - including Client Components - without touching your application code. The third option is what most teams actually choose when the rewrite isn't on this quarter's roadmap.

    Related resources

    Frequently asked questions