Головна / Статті

Технічний SEO у Next.js App Router: метадані, сайт-карти та JSON-LD

Дізнайтеся, як допоміжні засоби для спільних метаданих, стандартні налаштування лейауту, файл robots.ts, динамічний сайт-мапа, коректне використання JSON-LD та аудит сторінок створюють міцну SEO-основу для додатку Next.js.

Видавець: REACTAPP.TOP4 хв читання1024 слів

Джерела: How I Got a Next.js Project to 100% SEO on Lighthouse

Додаток Next.js може виглядати готовим, але для пошукових систем залишатися важким для індексації: сторінки не мають канонічних URL, правила для пошукових роботів не визначені, а новий контент ніколи не потрапляє до сайт-мапи. У цьому посібнику розглядається сайт з API-даними для тестування, який мав багато сторінок-ресурсів, і процес підвищення його оцінки за інструментом Lighthouse у розділ SEO до 100 балів, з описом семи змін, внесених за допомогою вбудованих API метаданих App Router.

Створення метаданих сторінки за допомогою одного помічника

Ручне введення метаданих на кожній сторінці призводить до невідповідностей — наприклад, відсутності канонічного URL тут чи застарілого заголовка Open Graph там. Для вирішення цієї проблеми існує невеликий „завод“ для обробки даних: кожна сторінка передає лише свою назву, опис, шлях та необов’язковий флаг noIndex, а помічник перетворює їх на канонічні поля, дані для пошукових роботів та поля Open Graph:

export function createPageMetadata({
  title,
  description,
  path,
  noIndex = false,
}: PageMetadata) {
  return {
    title,
    description,
    alternates: {
      canonical: path,
    },
    robots: noIndex ? "noindex, nofollow" : "index, follow",
    openGraph: {
      title,
      description,
      url: path,
      type: "website",
    },
  };
}

Індексування є необов’язковим: один флаг переводить сторінку у режим noindex, nofollow. Оскільки path є відносним, допоміжний модуль спирається на базову URL, визначену у кореневому макеті.

Встановіть загальносайтові значення за замовчуванням у кореневому макеті

Усе, що використовується на всьому сайті, має бути в експорті metadata з файлу layout.tsx:

  • metadataBase
  • шаблон заголовка
  • загальноприйнятий опис
  • налаштування Open Graph за замовчуванням
  • налаштування картки Twitter
  • значення за замовчуванням для роботів
  • атрибут lang у елементі <html>

Скорочена версія цього експорту виглядає так:

export const metadata: Metadata = {
  metadataBase: new URL("https://mockdata.ir"),
  title: {
    default: "MockData",
    template: "%s | MockData",
  },
  description: "...",
};

За допомогою шаблону %s | MockData сторінка під назвою „Users API“ відображається як „Users API | MockData“, тоді як сторінки без назви використовують default. metadataBase відповідає за перетворення відносних значень canonical та URL Open Graph цього допоміжного елемента на абсолютні URL. Зауважте, що lang не є полем метаданих; його потрібно встановити на тегу <html>, який відображається у лейауті.

Визначення правил краулера за допомогою robots.ts

Замість того, щоб залишати правила краулера невизначеними, створіть файл robots.txt з файлу app/robots.ts, який повертає об’єкт типу MetadataRoute.Robots:

export default function robots(): MetadataRoute.Robots {
  return {
    rules: {
      userAgent: "*",
      allow: "/",
    },
    sitemap: "https://mockdata.ir/sitemap.xml",
  };
}

Він навмисно є мінімальним: усі пристрої-користувачі можуть краулити все, а місцезнаходження сайтмапи вказується явно.

Створення сайтмапи з ваших даних

Завдяки сторінкам ресурсів для користувачів, публікацій, продуктів та іншого, XML-сайтмап, який підтримується вручну, не підлаштовується під зростання обсягу даних. Застосунок типу sitemap.ts з параметром default export може бути async, що дозволяє йому запитувати ті самі джерела, які використовуються сторінками:

export default async function sitemap(): Promise<MetadataRoute.Sitemap> {
  const resources = await getPublicResources();

return [
    {
      url: "https://mockdata.ir",
      lastModified: new Date(),
    },
    ...resources.map((resource) => ({
      url: `https://mockdata.ir/${resource.slug}`,
      lastModified: resource.updatedAt,
    })),
  ];
}

Кожен ресурс відповідає URL, у якому updatedAt використовується замість lastModified, тому нові публічні ресурси автоматично додаються до сайтмапу. Одне уточнення: використання new Date() для головної сторінки означає, що вона вважається оновленою після кожного створення; справжній час створення контенту є більш точним.

Додавайте структуровані дані лише там, де це актуально

JSON-LD із словниковим запасом Schema.org повідомляє пошуковим системам, що представляє собою сторінка. Сам додаток описується як SoftwareApplication, а використовувані типи є наступними:

  • WebSite
  • Organization
  • SoftwareApplication
  • BreadcrumbList
  • Намагайтеся досягти точності, а не кількості: маркування має описувати вміст, який дійсно є на сторінці. Вигадані відгуки, оцінки чи інші фальшиві характеристики є оманливими та можуть порушувати правила пошукових систем.

    Зберігайте послідовність „хлібних крихт“ у інтерфейсі та схемі

    Вкладені сторінки документації показують видимий шлях, наприклад Головна → Документація → API користувачів, і та сама ієрархія відправляється у вигляді структурованих даних BreadcrumbList. Видимий шлях та маркування завжди повинні описувати однакову структуру.

    Перевіряйте кожну індексовану сторінку вручну

    Нарешті, перегляньте кожну публічну сторінку окремо:

    • Чи є у неї саме один чіткий H1?
    • Чи описує заголовок саме цю сторінку?
    • Чи відповідає опис реальному вмісту?
    • Чи є корисні внутрішні посилання на неї та з неї?
    • Чи взагалі потрібно індексувати цю сторінку?
    • Чи є якісь порожні або маловажливі сторінки, доступні для перевірки пошуковими ботами?

    Не кожен маршрут повинен потрапляти до результатів пошуку; часто правильним рішенням є використання тега noindex. Щодо структури заголовків, дивіться цей посібник з семантичного HTML для отримання інформації з цього приводу.

    Що означає та чого не означає ідеальний рейтинг SEO у Lighthouse

    Після цих виправлень Lighthouse показав рейтинг SEO 100. Це число перевіряє технічні основи, такі як заголовки, описи та можливість індексації; воно нічого не говорить про рангування. Рангування залежить від якості контенту, наміру користувача під час пошуку, авторитету сайту, зворотних посилань, конкуренції, продуктивності та багатьох інших факторів.

    Справжня цінність — це міцна технічна основа. Проведення аудиту перед розгортанням будь-якого додатку Next.js коштує недорого та допомагає виявити багато незначних помилок.

    Основні висновки

    • Централізуйте метадані кожної сторінки у допоміжному файлі та встановіть спільні значення за замовчуванням, включаючи metadataBase, у кореневій структурі.
    • Використовуйте robots.ts та асинхронний sitemap.ts, щоб правила краулерів та URL залишалися синхронізованими з вашими даними.
    • Додавайте лише структуровані дані, які точно описують сторінку, та зберігайте індикатори навігації однаковими як у інтерфейсі, так і в схемі.
    • Вважайте параметр noindex законним вибором для сторінок, які не повинні з’являтися у результатах пошуку.
    • Оцінку Lighthouse у 100 розглядайте як „технічно правильну“, а не як гарантію позиціонування.