So optimieren Sie SEO für eine mehrsprachige Next.js-App
Warum mehrsprachiges SEO besondere Aufmerksamkeit braucht
Die meisten Entwickler, die i18n zu ihrer Next.js-App hinzufügen, konzentrieren sich auf die Übersetzung der UI und halten die Sache damit für erledigt. Aber wenn Suchmaschinen Ihre Sprachversionen nicht finden, indexieren und korrekt miteinander verknüpfen können, bleibt die gesamte Übersetzungsarbeit unsichtbar.
Eine mehrsprachige Website ohne korrektes SEO-Setup bringt Probleme mit sich:
- Google indexiert möglicherweise nur eine Sprachversion und ignoriert den Rest
- Nutzern, die auf Spanisch suchen, wird die englische Seite angezeigt
- Duplicate-Content-Strafen, weil Google
/en/aboutund/fr/aboutals dieselbe Seite ansieht - Falsche Sprache in Suchergebnis-Snippets
Die gute Nachricht: Mehrsprachiges SEO in Next.js korrekt einzurichten, ist nicht kompliziert. Es gibt fünf Dinge, die Sie richtig machen müssen, und diese Anleitung behandelt sie alle anhand von gt-next.
1. Sprachbasiertes URL‑Routing
Die Grundlage für mehrsprachiges SEO sind eindeutige URLs für jede Sprache. Suchmaschinen benötigen separate, crawlfähige URLs, um jede Sprachversion unabhängig zu indexieren.
Das bedeutet Locale-in-der-URL – keine Cookies, keine Query-Parameter und keine alleinige Accept-Language-Erkennung.
✅ generaltranslation.com/en/about
✅ generaltranslation.com/fr/about
✅ generaltranslation.com/es/about
❌ generaltranslation.com/about?lang=fr
❌ generaltranslation.com/about (mit Locale in einem Cookie)
Einrichten des Locale-Routings mit gt-next
Verschachteln Sie Ihre Seiten zunächst unter einem dynamischen [locale]-Segment:
app/
└── [locale]/
├── layout.tsx
├── page.tsx
└── about/
└── page.tsx
Erstellen Sie dann eine Middleware im Wurzelverzeichnis Ihres Projekts (proxy.ts für Next.js 16+ oder middleware.ts für Next.js 15 und älter):
import { createNextMiddleware } from 'gt-next/middleware';
export default createNextMiddleware();
export const config = {
matcher: ['/((?!api|static|.*\\..*|_next).*)'],
};Damit erhalten Sie automatisch URLs mit Sprachpräfix.
Standardmäßig erhält die Standardsprache (z. B. Englisch) kein Präfix – /about bleibt unverändert,
während spanische Benutzer /es/about und französische Benutzer /fr/about sehen.
2. Setzen des HTML-Attributs lang
Das lang-Attribut in Ihrem <html>-Tag teilt Browsern und Suchmaschinen mit, in welcher Sprache die Seite ist.
Es ist eine der einfachsten und wirkungsvollsten Maßnahmen, die Sie für Barrierefreiheit und SEO ergreifen können.
Ohne dieses Attribut raten Screenreader die Sprache (oft falsch), und Suchmaschinen haben weniger Vertrauen in ihre Sprachklassifizierung.
gt-next stellt den useLocale-Hook bereit, mit dem Sie dies in Ihrem Root-Layout ganz einfach setzen können:
import { useLocale, GTProvider } from 'gt-next';
export default function RootLayout({ children }: { children: React.ReactNode }) {
const locale = useLocale();
return (
<html lang={locale}>
<body>
<GTProvider>
{children}
</GTProvider>
</body>
</html>
);
}useLocale gibt den BCP-47-Locale-Code zurück (z. B. en-US, ar, zh-Hans).
3. Canonical-URLs
Canonical-Tags teilen Suchmaschinen mit, welche URL die „primäre“ Version einer Seite ist. Auf mehrsprachigen Websites sollte jede Sprachversion sich selbst als kanonische Version angeben:
<!-- Auf /fr/about -->
<link rel="canonical" href="https://example.com/fr/about" />Dadurch verhindern Sie, dass Suchmaschinen Ihre französische Seite als Duplikat Ihrer englischen Seite einstufen.
In Next.js legen Sie Canonical-URLs über die metadata API fest.
Kombinieren Sie diese mit der getLocale-Funktion von gt-next, um für jedes Locale die korrekte Canonical-URL zu erzeugen:
import { getLocale } from 'gt-next/server';
const BASE_URL = 'https://example.com';
export async function generateMetadata() {
const locale = await getLocale();
return {
alternates: {
canonical: `${BASE_URL}/${locale}/about`,
},
};
}
export default function AboutPage() {
return <h1>Über uns</h1>;
}Für das Standard-Locale ohne Präfix passen Sie dies entsprechend an:
import { getLocale, getDefaultLocale } from 'gt-next/server';
export async function generateMetadata() {
const locale = await getLocale();
const defaultLocale = getDefaultLocale();
const path = '/about';
const prefix = locale === defaultLocale ? '' : `/${locale}`;
return {
alternates: {
canonical: `${BASE_URL}${prefix}${path}`,
},
};
}4. Hreflang-Tags
Hreflang-Tags sind das wichtigste Signal für mehrsprachiges SEO. Sie teilen Suchmaschinen mit: "Diese Seite existiert in diesen anderen Sprachen, und hier sind die URLs."
Ohne Hreflang muss Google raten, welche Sprachversion in den Suchergebnissen angezeigt werden soll — und liegt dabei häufig falsch.
<link rel="alternate" hreflang="en" href="https://example.com/about" />
<link rel="alternate" hreflang="fr" href="https://example.com/fr/about" />
<link rel="alternate" hreflang="es" href="https://example.com/es/about" />
<link rel="alternate" hreflang="x-default" href="https://example.com/about" />Das x-default-Tag weist Suchmaschinen an, welche URL angezeigt werden soll, wenn keine der angegebenen Sprachen zur Sprache der Nutzer passt.
In Next.js können Sie hreflang über die alternates.languages-Eigenschaft der Metadata-API hinzufügen.
Hier ist eine wiederverwendbare Hilfsfunktion, die mit gt-next funktioniert:
import { getLocale, getDefaultLocale } from 'gt-next/server';
const BASE_URL = 'https://example.com';
const SUPPORTED_LOCALES = ['en', 'fr', 'es'];
export async function getI18NMetadata(path: string) {
const locale = await getLocale();
const defaultLocale = getDefaultLocale();
const getUrl = (loc: string) => {
const prefix = loc === defaultLocale ? '' : `/${loc}`;
return `${BASE_URL}${prefix}${path}`;
};
const languages: Record<string, string> = {};
for (const loc of SUPPORTED_LOCALES) {
languages[loc] = getUrl(loc);
}
languages['x-default'] = getUrl(defaultLocale);
return {
alternates: {
canonical: getUrl(locale),
languages,
},
};
}Verwenden Sie es anschließend auf einer beliebigen Seite:
import { getI18NMetadata } from '@/lib/i18n-metadata';
export async function generateMetadata() {
return await getI18NMetadata('/about');
}Dies generiert sowohl den Canonical-Tag als auch alle hreflang-Tags in einem einzigen Aufruf.
5. Übersetzte Metadaten
Suchmaschinen zeigen den Seitentitel und die Beschreibung in den Ergebnissen an. Wenn diese für eine französische Seite auf Englisch vorliegen, klicken Nutzer seltener – und Google könnte das Ergebnis herabstufen.
Verwenden Sie die getGT-Funktion von gt-next, um Metadaten-Strings zu übersetzen:
import { getGT } from 'gt-next/server';
import { getI18NMetadata } from '@/lib/i18n-metadata';
export async function generateMetadata() {
const t = await getGT();
const i18nMeta = await getI18NMetadata('/about');
return {
title: t('Über uns'),
description: t('Erfahren Sie mehr über unsere Mission und unser Team.'),
...i18nMeta,
};
}So erhalten Sie lokalisierte Titel und Beschreibungen in den Suchergebnissen, was die Klickraten für nicht englischsprachige Suchanfragen deutlich verbessert.
6. Mehrsprachige Sitemaps
Eine Sitemap hilft Suchmaschinen, all Ihre Seiten zu entdecken, einschließlich jeder Sprachversion. Für mehrsprachige Websites sollten Sie in Ihrer Sitemap auch hreflang-Attribute angeben.
Next.js unterstützt programmatische Sitemaps über eine sitemap.ts-Datei:
import { MetadataRoute } from 'next';
const BASE_URL = 'https://example.com';
const LOCALES = ['en', 'fr', 'es'];
const DEFAULT_LOCALE = 'en';
const PAGES = ['/', '/about', '/blog', '/contact'];
export default function sitemap(): MetadataRoute.Sitemap {
return PAGES.flatMap((path) => {
const getUrl = (locale: string) => {
const prefix = locale === DEFAULT_LOCALE ? '' : `/${locale}`;
return `${BASE_URL}${prefix}${path === '/' ? '' : path}`;
};
const languages: Record<string, string> = {};
for (const locale of LOCALES) {
languages[locale] = getUrl(locale);
}
return LOCALES.map((locale) => ({
url: getUrl(locale),
lastModified: new Date(),
alternates: { languages },
}));
});
}Dies erzeugt eine Sitemap mit einem Eintrag pro Seite und Locale, wobei jeder Eintrag hreflang-Attribute enthält, die auf alle Sprachversionen verweisen.
Checkliste
Hier eine kurze Zusammenfassung aller behandelten Punkte:
| SEO-Anforderung | Implementierung |
|---|---|
| Locale in der URL | createNextMiddleware() mit dynamischem Segment [locale] |
HTML-Attribut lang | useLocale() im Root-Layout |
| Kanonische URLs | getLocale() + Next.js metadata API alternates.canonical |
| Hreflang-Tags | Next.js metadata API alternates.languages mit allen unterstützten Locales |
| Übersetzte Metadaten | getGT() für Seitentitel und -beschreibungen |
| Mehrsprachige Sitemap | sitemap.ts mit Einträgen pro Locale und hreflang-Alternativen |
Nächste Schritte
- gt-next Quickstart, um den vollständigen i18n-Stack einzurichten
- Middleware-Anleitung für die Routing-Konfiguration
- SSG-Anleitung für die statische Generierung von mehrsprachigen Seiten
- RTL-Unterstützung für Sprachen mit Schreibrichtung von rechts nach links