Sitemap генерация

MDX представляет собой расширение Markdown с возможностью внедрения JSX-компонентов, что делает его удобным инструментом для статических сайтов и документации. Одной из важных задач при построении таких сайтов является генерация sitemap.xml — файла, который помогает поисковым системам индексировать страницы и оптимизировать SEO.

Основы генерации Sitemap

Для работы с Sitemap в проектах на MDX обычно используются инструменты Node.js, которые обходят файловую систему и извлекают метаданные из MDX-файлов. Основная задача — собрать список всех доступных страниц и их метаданные, такие как:

  • url — адрес страницы;
  • lastmod — дата последнего изменения;
  • changefreq — частота обновления;
  • priority — приоритет страницы для поисковиков.

Пример структуры MDX-файла с метаданными в frontmatter:

---
title: "Пример страницы"
date: "2026-03-23"
slug: "primer-stranitsy"
---

Содержимое страницы в формате MDX.

Из frontmatter можно извлечь slug и дату для использования в sitemap.xml.

Обход MDX-файлов

Для генерации списка страниц используется модуль fs:

import fs from 'fs';
import path from 'path';
import matter from 'gray-matter';

const postsDirectory = path.join(process.cwd(), 'content');

function getAllPosts() {
  const filenames = fs.readdirSync(postsDirectory);

  return filenames.map(filename => {
    const filePath = path.join(postsDirectory, filename);
    const fileContents = fs.readFileSync(filePath, 'utf8');
    const { data } = matter(fileContents);

    return {
      slug: data.slug,
      lastmod: data.date
    };
  });
}

Здесь gray-matter используется для парсинга frontmatter MDX-файлов. Возвращается массив объектов с slug и lastmod.

Генерация XML-файла

После получения всех страниц необходимо создать XML-файл в формате Sitemap. Используется стандартная структура:

function generateSitemap(posts) {
  const baseUrl = 'https://example.com';
  
  const urls = posts.map(post => {
    return `
  <url>
    <loc>${baseUrl}/${post.slug}</loc>
    <lastmod>${post.lastmod}</lastmod>
    <changefreq>weekly</changefreq>
    <priority>0.8</priority>
  </url>`;
  }).join('');

  return `<?xml version="1.0" encoding="UTF-8"?>
<urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9">
${urls}
</urlset>`;
}

Файл sitemap.xml затем можно записать на диск:

fs.writeFileSync('public/sitemap.xml', generateSitemap(getAllPosts()));

Интеграция с Next.js и MDX

Если проект построен на Next.js, генерация Sitemap может происходить во время сборки (build time) с использованием функции getStaticProps или через отдельный скрипт, запускаемый командой npm run build.

Пример скрипта generate-sitemap.js:

import fs from 'fs';
import path from 'path';
import matter from 'gray-matter';

const postsDirectory = path.join(process.cwd(), 'content');

function getPosts() {
  return fs.readdirSync(postsDirectory).map(file => {
    const content = fs.readFileSync(path.join(postsDirectory, file), 'utf8');
    const { data } = matter(content);
    return { slug: data.slug, lastmod: data.date };
  });
}

function buildSitemap(posts) {
  const baseUrl = 'https://example.com';
  const urls = posts.map(p => `
  <url>
    <loc>${baseUrl}/${p.slug}</loc>
    <lastmod>${p.lastmod}</lastmod>
    <changefreq>weekly</changefreq>
    <priority>0.8</priority>
  </url>`).join('');

  return `<?xml version="1.0" encoding="UTF-8"?>
<urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9">
${urls}
</urlset>`;
}

fs.writeFileSync('public/sitemap.xml', buildSitemap(getPosts()));

Автоматическое обновление Sitemap

Чтобы sitemap всегда был актуальным, можно интегрировать генерацию с watcher, например через chokidar, который следит за изменениями в директории MDX и автоматически пересоздаёт файл sitemap.xml.

import chokidar from 'chokidar';

const watcher = chokidar.watch('content/**/*.mdx');

watcher.on('add', generate);
watcher.on('change', generate);
watcher.on('unlink', generate);

function generate() {
  fs.writeFileSync('public/sitemap.xml', buildSitemap(getPosts()));
  console.log('Sitemap обновлён');
}

Использование дополнительных метаданных

MDX позволяет расширять frontmatter. В sitemap можно включать:

  • alternate — для разных языковых версий страницы;
  • images — изображения, которые индексируются поисковиками;
  • video — если на странице есть видео-контент.

Пример расширенного frontmatter:

---
title: "Пример страницы"
date: "2026-03-23"
slug: "primer-stranitsy"
alternate:
  - lang: "en"
    url: "/en/example-page"
images:
  - "/images/cover.jpg"
video:
  - "/videos/intro.mp4"
---

Генератор sitemap должен учитывать эти поля для корректного формирования тегов <xhtml:link>, <image:image> и <video:video> в XML.

Вывод

Генерация Sitemap для MDX-проектов — это комбинация парсинга frontmatter, обхода файловой системы и динамического формирования XML. Такой подход обеспечивает:

  • точную индексацию контента;
  • возможность учёта мультиязычности и мультимедиа;
  • автоматическое обновление при изменении контента.

Встроенные возможности MDX и Node.js позволяют создавать гибкие и расширяемые генераторы Sitemap, которые легко интегрируются в современные статические сайты и фреймворки.