All fix guides
CriticalAccessibility

Fix the Missing HTML lang Attribute

The missing_html_lang issue means the root <html> tag has no lang attribute (or an empty lang=""), so screen readers, browsers, and AI crawlers can't reliably tell what language the page is written in. The fix is a one-line change: add lang="en" (or your actual BCP 47 language code) to the <html> element. On most platforms it lives in a theme setting or template rather than raw markup.

What this means

Every HTML document has a single root element: <html>. The lang attribute on that element declares the primary language of the page's content using a BCP 47 language tag: en for English, es for Spanish, fr for French, or a region-specific form like en-US, en-GB, or pt-BR.

When the audit flags missing_html_lang, it found either <html> with no lang at all, or an empty lang="". Assistive technology and machine consumers then have to guess the language from the text, which is unreliable on short, code-heavy, or mixed-language pages.

This is different from hreflang (which tells search engines about alternate-language versions of a URL) and from the Content-Language HTTP header. The lang attribute on <html> is the in-document declaration that accessibility tools and WCAG check for. It declares the primary language only. If a page mixes languages, you add lang to individual elements for the exceptions, but the root declaration must still be present.

Why it matters

The most direct impact is accessibility. Screen readers like NVDA, JAWS, and VoiceOver use the lang value to select the correct pronunciation rules and voice. Without it, an English page can be read with the phonetics of whatever default the screen reader is set to, which ranges from confusing to unusable. This is why WCAG 2.1 makes it a Level A requirement (Success Criterion 3.1.1, Language of Page), the lowest and most essential conformance level. Lighthouse and axe both flag a missing lang as a failure, and it drags down your accessibility score.

For classic Google ranking, lang is not a strong direct signal. Google detects a page's language mainly from its visible content, not the attribute. But a low accessibility score is a page-quality red flag, and a correct lang also helps browsers offer the right translation prompt and apply correct hyphenation and quotation-mark rules.

For AI answer engines and crawlers (ChatGPT, Perplexity, Google AI Overviews, Claude), a declared language removes ambiguity about what you're serving. On short pages, code-heavy pages, or pages with mixed-language navigation, the visible text alone can be a weak language signal. An explicit lang tag is a clean, machine-readable statement of intent that helps these systems classify and correctly attribute your content.

How to fix it

  1. 1

    Add lang to the root html element

    In raw HTML this is a one-line fix. Change your opening tag to include the correct language code, for example <html lang="en">. Use a two-letter ISO 639-1 code for the language, optionally followed by a region subtag when it matters (en-US vs en-GB, pt-BR vs pt-PT). Don't invent values: lang="english" or lang="us" are invalid and won't be recognized.

  2. 2

    Pick the correct BCP 47 tag

    Use the primary language of the page's main content, not the language of your admin panel. Common valid tags: en, en-US, en-GB, es, es-MX, fr, de, hi, pt-BR, zh-Hans, ar. Add a region subtag only when spelling, currency, or dialect genuinely differs; a bare en is fine for most English sites. By convention the language is lowercase and the region uppercase (en-US), though the tag is case-insensitive. Never leave it as lang="", which fails the check the same as a missing attribute.

  3. 3

    Fix it in your CMS or framework, not the raw HTML

    On most platforms the <html> tag is generated by a template, so you set the language in a setting rather than editing markup directly. See the platform steps below. After changing it, re-check the served HTML with View Source or curl rather than trusting the setting, because caching plugins and CDNs sometimes serve a stale copy.

  4. 4

    Handle mixed-language and multilingual sites

    The root lang declares the page's main language. If a passage is in a different language, wrap it and set lang on that element, for example <blockquote lang="fr">…</blockquote>, so screen readers switch pronunciation for just that section. If you run separate URLs per language, each URL's <html> should carry its own correct lang, paired with hreflang annotations so search engines connect the versions.

  5. 5

    Re-crawl and confirm the flag cleared

    Reload the page, run View Source, and confirm the <html> element shows a valid lang value at the top of the document. Then re-run the audit (and optionally Lighthouse or axe DevTools) to confirm the missing_html_lang / WCAG 3.1.1 flag is gone. If you use a CDN like Cloudflare, purge the cache first so the crawler fetches the corrected HTML.

Example

<!doctype html>
<html lang="en">
  <head>
    <meta charset="utf-8">
    <title>Your Page Title</title>
  </head>
  <body>
    <p>This page is primarily in English.</p>

    <!-- Override for a passage in another language -->
    <blockquote lang="fr">
      La qualité prime sur la quantité.
    </blockquote>
  </body>
</html>

Add a valid lang attribute to the root html element (top). For multilingual passages, set lang on the specific element (bottom).

Platform-specific steps

WordPress (Yoast / Rank Math)

WordPress outputs the lang attribute automatically via language_attributes() in the theme's header.php, driven by Settings > General > Site Language. Set the correct site language there first. Neither Yoast nor Rank Math controls this tag, so if it's still missing, your theme's header.php is likely hardcoding <html> without calling language_attributes(). Edit it to <html <?php language_attributes(); ?>>. Clear any caching plugin (WP Rocket, W3 Total Cache, LiteSpeed) afterward.

Shopify

Shopify themes set the language in theme.liquid, typically <html lang="{{ request.locale.iso_code }}">. If the attribute is missing, open the theme code editor (Online Store > Themes > Edit code), open layout/theme.liquid, and ensure the opening <html> tag includes lang="{{ request.locale.iso_code }}". Confirm your store's languages are set under Settings > Languages so the ISO code resolves correctly.

Wix / Squarespace

On both hosted builders you don't edit the <html> tag directly; the platform sets it from your site's language setting. In Wix, set it under your site language settings (and use the Multilingual feature if you run multiple languages). In Squarespace, it follows your site language in the site settings. If it's wrong or missing, correct the site language setting. Custom code header injection only adds to <head>, not <html>, so it can't fix this.

Next.js / React

In the Next.js App Router, set it on the root layout: return (<html lang="en"><body>{children}</body></html>). In the Pages Router, edit pages/_document.js and set <Html lang="en">. For a plain Vite or Create React App SPA, the lang lives in the static index.html <html> tag; set it there, since the crawler sees that shell before hydration.

Cloudflare (and other CDNs)

A CDN doesn't set the lang attribute, but it can mask your fix by serving cached HTML. After correcting lang at the origin, purge the cache (Cloudflare: Caching > Configuration > Purge Everything, or purge the specific URL). Then verify with curl -s https://yoursite.com | head to confirm the served <html> tag carries the lang value before you re-run the audit.

Free tool
Check this with the Meta Tag Checker

Frequently asked

What language code should I use for the html lang attribute?

Use the BCP 47 tag for your page's primary content language. For most sites that's a simple two-letter code like en, es, fr, de, or hi. Add a region subtag only when the dialect matters, such as en-US vs en-GB or pt-BR vs pt-PT. By convention write the language in lowercase and the region in uppercase (en-US). Avoid invented values like "english" or "usa"; they're invalid.

Is the html lang attribute a Google ranking factor?

Not a strong direct one. Google detects a page's language mainly from its visible text, not the lang attribute. But it's a Level A WCAG accessibility requirement, it affects your Lighthouse accessibility score, and it helps browsers and AI answer engines classify the page correctly. Treat it as a required accessibility and quality fix, not a ranking hack.

What's the difference between lang and hreflang?

The lang attribute on <html> declares the language of the current page for browsers, screen readers, and crawlers. hreflang is a separate annotation (in <head> link tags or the sitemap) that tells search engines about equivalent pages in other languages or regions. You need lang on every page; you only need hreflang if you publish the same content in multiple languages. They complement each other.

Can I set the language with the Content-Language HTTP header instead?

You can send a Content-Language header, but it doesn't satisfy the accessibility check. WCAG 3.1.1 and tools like Lighthouse and axe specifically look for a valid lang attribute on the <html> element in the document itself. The header is a weaker, secondary hint, so always set the lang attribute regardless of what your server sends.

My CMS setting shows the right language but the audit still fails. Why?

Almost always caching. A page cache, optimization plugin, or CDN like Cloudflare is serving an older copy of the HTML that predates your fix. Purge every cache layer, then confirm with View Source or a curl of the live URL that the <html> tag actually contains the lang value before re-running the audit.

Does your site have this issue?

Run a free, AI-powered audit and we’ll flag this and 150+ other checks in about a minute. No signup.

No signup needed. Results in under 60 seconds.

Related fixes