Short definition

Hreflang — an annotation in the HTML, an HTTP header or the sitemap that tells search engines which pages are language or country versions of each other, so they show every visitor the right version.

Also known as: hreflang tag, hreflang attribute, x-default.

Hreflang is an annotation that tells search engines which pages are language or country versions of each other, so Google shows every visitor the version in their language or for their country. It isn’t a ranking trick: hreflang helps decide which version appears, not how high it ranks.

What does hreflang look like?

In HTML, hreflang is a set of link elements in the page’s head. Each version gets one line with its language code and its full URL, including https://. A site with a Dutch version for Belgium, a Dutch version for the Netherlands and a French version for Belgium looks like this:

html
<link rel="alternate" hreflang="nl-BE" href="https://example.be/" />
<link rel="alternate" hreflang="nl-NL" href="https://example.be/nl-nl/" />
<link rel="alternate" hreflang="fr-BE" href="https://example.be/fr/" />
<link rel="alternate" hreflang="x-default" href="https://example.be/" />

The same set of lines appears on all three versions, so every page also points to itself. You can put the same links in an HTTP header (useful for PDFs) or in the XML sitemap with xhtml:link entries. According to Google’s documentation on localized versions, the three methods are equivalent.

Language codes and country codes

An hreflang value always starts with a language code from ISO 639-1, such as nl, fr or en. A country code from ISO 3166-1 can follow: nl-BE is Dutch for Belgium, fr-BE is French for Belgium and nl-NL is Dutch for the Netherlands. A language code on its own, such as nl, applies to everyone who speaks that language, in any country.

A country code on its own doesn’t work. be doesn’t mean Belgium; it’s the language code for Belarusian. UK and EU have no effect either, because they aren’t valid ISO country codes. Use en-GB for the United Kingdom.

What does x-default do?

x-default is a reserved value. It points to the page for visitors whose language doesn’t match any version, for example someone with a German browser on a site in Dutch and French. According to Google, x-default was designed for language selector pages and works best there. You don’t add a language code to it.

Why do both pages have to point to each other?

Hreflang only works in both directions. If page A points to page B, page B has to point back to page A. If it doesn’t, Google ignores the link. That way, another site can’t claim to be a translation of your page.

That rule makes hreflang fragile when you maintain it by hand. When you add a new language version, you have to update every existing version. Miss one page and the link for that page drops out, without any visible sign on the site itself.

Common hreflang mistakes

  • a return link is missing, so Google ignores the pair;
  • the codes are wrong, such as be for Belgium or be-nl instead of nl-BE (be-nl means Belarusian for the Netherlands);
  • relative URLs such as /fr/ instead of full URLs with https://;
  • a canonical URL that points to another country’s version, so only that version counts;
  • hreflang pointing to a translation that doesn’t exist.

Google doesn’t use hreflang to detect the language of a page, by the way. It works that out from the text itself. A page with hreflang="fr" but Dutch text is still a Dutch page to Google.

How we handle hreflang on straffesites.com

Our site exists in Dutch and English. One fixed list of page pairs in the code decides which Dutch and English pages are translations of each other. On every deploy, we build both the hreflang links in the HTML and the xhtml:link entries in the sitemap from that list. Because both come from the same source, they can’t drift apart, and every link is automatically two-way.

Pages that exist in only one language get no hreflang links, just a canonical URL. So we never point to a translation that isn’t there. You can check this yourself in the source code of this page: it points to its Dutch counterpart, and that page points back.

Hreflang is one part of international SEO, alongside choosing a domain or subfolder, local keywords and measuring per country. It works together with the canonical URL: for versions that target different countries, each canonical URL points to itself. The guide to Storyblok localization for a multilingual site shows how to set one up with a headless CMS.