Übersetzung von Seiten-Metadaten

Einstellung lokalisierter <title> und <description> Tags

Problem

Ein Benutzer betrachtet eine Seite auf Spanisch, und der gesamte sichtbare Inhalt ist korrekt übersetzt. Allerdings zeigen der Browser-Tab und der Snippet in den Suchmaschinenergebnissen immer noch den englischen Titel und die englische Beschreibung an. Diese Metadaten-Diskrepanz erzeugt eine verwirrende Benutzererfahrung und schadet dem SEO, indem irrelevante Informationen in der Suche präsentiert werden.

Lösung

Verwenden Sie die Next.js-Funktion generateMetadata innerhalb Ihrer Seiten und Layouts. Diese serverseitige Funktion kann die korrekten Übersetzungen basierend auf dem lang-Parameter laden (unter Verwendung derselben Dictionary-Ladelogik wie Ihre Komponenten) und ein dynamisches metadata-Objekt mit dem lokalisierten Titel und der Beschreibung zurückgeben.

Schritte

1. Erstellen Sie eine Funktion zum Laden von Wörterbüchern

Sie benötigen eine Möglichkeit, Ihre flachen Übersetzungsdateien auf dem Server zu laden. Erstellen Sie eine Hilfsfunktion dafür.

// app/get-dictionary.ts
import 'server-only';

type Messages = Record<string, string>;

const dictionaries: { [key: string]: () => Promise<Messages> } = {
  en: () => import('@/dictionaries/en.json').then((module) => module.default),
  es: () => import('@/dictionaries/es.json').then((module) => module.default),
};

export const getDictionary = async (lang: string) => {
  const load = dictionaries[lang];
  if (load) {
    return load();
  }
  return dictionaries.en();
};

2. Definieren Sie Metadaten auf einer Seite

Exportieren Sie in Ihrer Seitendatei (z.B. app/[lang]/about/page.tsx) eine async-Funktion namens generateMetadata. Next.js wird diese automatisch aufrufen, wenn die Seite gerendert wird.

// app/[lang]/about/page.tsx
import { getDictionary } from '@/app/get-dictionary';
import type { Metadata } from 'next';

type Props = {
  params: { lang: string };
};

// This function generates metadata
export async function generateMetadata({ params }: Props): Promise<Metadata> {
  // Load the dictionary for this page
  const dict = await getDictionary(params.lang);

  return {
    title: dict['about.title'], // e.g., "About Us" or "Sobre Nosotros"
    description: dict['about.description'],
  };
}

// The rest of your page component
export default function AboutPage() {
  return (
    <div>
      {/* Page content */}
      <h1>...</h1>
    </div>
  );
}

3. Setzen Sie eine Titelvorlage im Root-Layout

Um zu vermeiden, dass Sie Ihren Seitennamen in jedem Titel wiederholen müssen, können Sie eine Vorlage in Ihrem Root-Layout festlegen.

// app/[lang]/layout.tsx
import { getDictionary } from '@/app/get-dictionary';
import type { Metadata } from 'next';

type Props = {
  params: { lang: string };
  children: React.ReactNode;
};

// Sie können Metadaten auch in Layouts generieren
export async function generateMetadata({ params }: Props): Promise<Metadata> {
  const dict = await getDictionary(params.lang);

  return {
    // Dies bietet einen Basistitel und eine Vorlage
    title: {
      default: dict['site.name'], // z.B. "Meine großartige Website"
      template: `%s | ${dict['site.name']}`, // z.B. "Über uns | Meine großartige Website"
    },
    description: dict['site.description'],
  };
}

export default async function RootLayout({ children, params }: Props) {
  // ... Rest Ihres Layouts (Laden von Providern usw.)
  return (
    <html lang={params.lang}>
      <body>{children}</body>
    </html>
  );
}