DEV Community

Léo Guillaume (Dibodev)
Léo Guillaume (Dibodev)

Posted on Fully Autonomous

My French homepage showed up in English on Google. A default Nuxt i18n option was the reason.

This week I searched for my own brand on Google, and my French homepage came up with an English title and a "Translate this page" link under it.

My site is French first. The homepage at / serves French, the English version lives at /en, and the Spanish one at /es. So why was Google showing the English page for the French URL?

The site is a static Nuxt 4 build (SSG) with @nuxtjs/i18n and the prefix_except_default strategy. I started with the boring checks.

Everything looked right

The raw HTML of / was French:

curl -s https://dibodev.fr/ | grep -o 'lang="[a-z]*"\|<title>[^<]*</title>' | head -2
# lang="fr"
# <title>Dibodev — Développeur Web Freelance à Rennes</title>
Enter fullscreen mode Exit fullscreen mode

The canonical pointed to /, and the hreflang tags were correct: fr-FR → /, en-US → /en, es-ES → /es, x-default → /. Even with a Googlebot user agent, the server returned the same French page with a 200.

So the server side was fine. The problem had to be in the browser.

Reproducing it with a browser in English

Google doesn't just download your HTML: it renders the page in a headless Chrome and executes your JavaScript. A crawler doesn't tell you it speaks French. So I opened the homepage in Playwright with an English browser locale:

from playwright.sync_api import sync_playwright

with sync_playwright() as p:
    browser = p.chromium.launch()
    for locale in ["fr-FR", "en-US"]:
        page = browser.new_context(locale=locale).new_page()
        page.goto("https://dibodev.fr/", wait_until="networkidle")
        print(locale, "->", page.url, "|", page.title())
    browser.close()
Enter fullscreen mode Exit fullscreen mode
fr-FR -> https://dibodev.fr/ | Dibodev — Développeur Web Freelance à Rennes
en-US -> https://dibodev.fr/en | Dibodev — Freelance Web Developer in Rennes
Enter fullscreen mode Exit fullscreen mode

There it was. Any browser set to English landed on /, got the French HTML, and was redirected to /en right after hydration. Same result with a Googlebot user agent. As far as the renderer was concerned, the content of / was the English page.

The culprit: a default option

I never asked for a language redirect. But @nuxtjs/i18n has a detectBrowserLanguage option, and it is enabled by default. By default it only acts on the root path, and it remembers the choice in a cookie. For real visitors, that's a nice touch: an English speaker lands on the English site.

On a prerendered site, though, the redirect can't happen on the server: the HTML is already generated. It happens in the browser, once the app is running. And a headless browser with an English locale and no cookie gets the redirect every single time.

My config never mentioned the option:

// nuxt.config.ts (before, simplified)
i18n: {
  locales: [
    { code: 'fr', language: 'fr-FR', file: 'fr.json' },
    { code: 'en', language: 'en-US', file: 'en.json' },
    { code: 'es', language: 'es-ES', file: 'es.json' },
  ],
  defaultLocale: 'fr',
  strategy: 'prefix_except_default',
},
Enter fullscreen mode Exit fullscreen mode

The fix: one line

// nuxt.config.ts (after)
i18n: {
  // ...same as before
  strategy: 'prefix_except_default',
  // No redirect to the browser language: crawlers render in English and were sent from / to /en.
  detectBrowserLanguage: false,
},
Enter fullscreen mode Exit fullscreen mode

Visitors can still switch languages with the selector, and search engines already know about every version through hreflang. That's also what Google recommends: don't redirect users to a language version based on their browser, link the versions and let people choose.

After deploying, the same Playwright script gives:

fr-FR -> https://dibodev.fr/ | Dibodev — Développeur Web Freelance à Rennes
en-US -> https://dibodev.fr/ | Dibodev — Développeur Web Freelance à Rennes
Enter fullscreen mode Exit fullscreen mode

Why I care: AI search too

I noticed this because I'm working on how my site shows up in AI answers (ChatGPT, Copilot, Perplexity, Google's AI mode). Copilot and ChatGPT lean on Bing's index, and Bing renders pages with a browser too. A homepage that "becomes English" when rendered is exactly the kind of mixed signal that makes a small French business harder to recommend for French queries.

It's the second rendering trap I found on this site in two days. The first one: some project descriptions were rendered client-side, and AI crawlers like GPTBot or PerplexityBot don't run JavaScript at all, so for them that text simply didn't exist.

Takeaways

  • @nuxtjs/i18n enables detectBrowserLanguage by default. On a static or SEO-critical site, decide explicitly whether you want it.
  • Test your pages with a browser in another language, not just with curl: redirects after hydration don't show up in the raw HTML.
  • Crawlers render your site without your cookies and often without your language. Check what they get, not what you get.

I'm asking Google to recrawl the homepage, and I'll update this post when the French title is back in the results.


I'm a freelance developer in Rennes, France, building custom business tools and websites for small businesses. The site this happened on, and more write-ups like this one: dibodev.fr.

Top comments (0)