GFM, CommonMark и Pandoc Markdown: сравнение синтаксиса

Узнайте, какие функции Markdown поддерживаются надёжно

Содержимое страницы

Markdown выглядит как один язык, пока один и тот же файл не начинает отображаться по-разному в GitHub, Hugo, Obsidian или Pandoc. И проблема заключается не в том, что Markdown ненадежен.

Дело в том, что «Markdown» описывает семейство связанных синтаксисов, парсеров и функций платформ, а не единый универсальный формат документов. CommonMark определяет точное переносимое ядро, GitHub Flavored Markdown добавляет функции, полезные для сотрудничества в разработке программного обеспечения, а Pandoc Markdown расширяет язык до серьезного формата авторства документов.

Markdown dialects comparison

Выбор между ними зависит от того, где должен отображаться документ. Файл README, запись в блоге Hugo и научная статья имеют разные требования. Это сравнение является частью более широкой картины инструментов для документации и охватывает формальные диалекты, расширения для конкретных платформ и практические правила переносимости, чтобы вы могли выбрать правильный синтаксис для вашей целевой среды. Для быстрого справочника по синтаксису шпаргалка по Markdown охватывает основные элементы форматирования.

Markdown — это не один язык

Оригинальный синтаксис Markdown был намеренно мал и слабо специфицирован. Это сделало его легким для чтения и реализации, но разные парсеры начали по-разному интерпретировать неоднозначный ввод.

CommonMark был создан для определения согласованных правил разбора для фундаментальных структур Markdown. GitHub Flavored Markdown, обычно называемый GFM, строится на этой основе с несколькими широко используемыми расширениями.

Pandoc Markdown использует другой подход. Вместо того чтобы оставаться небольшим синтаксисом, ориентированным на веб, он добавляет функции документов, такие как цитаты, метаданные, сноски, списки определений, атрибуты и математические обозначения.

Упрощенная схема отношений выглядит так:

flowchart TD M[Семейство Markdown] --> C[Ядро CommonMark] C --> G[GitHub Flavored Markdown] C --> X[Другие рендереры на базе CommonMark] M --> P[Pandoc Markdown] G --> GH[Функции платформы GitHub] X --> H[Hugo с Goldmark] X --> GL[GitLab Flavored Markdown] P --> PDF[Рабочие процессы PDF и академические документы] P --> DOCX[Рабочие процессы DOCX и публикации]

Эта иерархия полезна, но она не является точным наследованием в каждой реализации. Каждый рендерер может независимо включать, отключать или добавлять синтаксис.

Краткий ответ

Используйте синтаксис, совместимый с CommonMark, когда переносимость имеет наибольшее значение.

Используйте GFM при написании файлов README, запросов на включение (pull requests), шаблонов проблем и технической документации, предназначенной в первую очередь для платформ, совместимых с GitHub.

Используйте Pandoc Markdown, когда исходный документ должен стать PDF, DOCX, EPUB, LaTeX, презентациями или научной статьей с цитатами и метаданными.

Для технического блога на Hugo используйте ядро CommonMark плюс расширения Goldmark, которые явно включены на вашем сайте. Не предполагайте, что каждая функция, видимая на GitHub, будет работать просто потому, что Hugo описывается как совместимый с GFM.

Субъективное мнение: если вы запомните только одно правило для технического блога на Hugo, относитесь к CommonMark плюс таблицам и спискам задач в стиле GFM как к значениям по умолчанию, и относитесь ко всему остальному — сноскам, математике, выделенным блокам, атрибутам заголовков — как к явным, протестированным расширениям, а не к предполагаемым значениям по умолчанию. Эта одна привычка предотвращает большинство проблем с переносимостью, описанных ниже.

CommonMark: Переносимое ядро

CommonMark — это формальная спецификация для базового языка Markdown. Его главный вклад — не большая коллекция функций, а согласованный разбор.

Он определяет, как парсеры должны интерпретировать:

  • Абзацы
  • Заголовки ATX и Setext
  • Блочные цитаты
  • Нумерованные и ненумерованные списки
  • Закрытые и отступленные блоки кода
  • Упор и сильный упор (курсив и жирный шрифт)
  • Ссылки и изображения
  • Ссылки в стиле ссылок
  • Встроенный код
  • Тематические разрывы (горизонтальные линии)
  • Блоки сырого HTML
  • Жесткие и мягкие переносы строк

Документ CommonMark все еще может вести себя по-разному на уровне представления. CSS, подсветка синтаксиса, якоря заголовков, санитизация HTML и политики ссылок находятся за пределами основных правил разбора.

Поэтому CommonMark следует рассматривать как надежную структурную базовую линию, а не как обещание, что каждый рендерер произведет идентичную страницу.

Переносимый пример CommonMark

# Развертывание сервиса

Сервис предоставляет небольшой HTTP API.

## Требования

- Linux
- Docker
- 8 ГБ памяти

## Запуск сервиса

```bash
docker compose up -d
```

См. [руководство по конфигурации](configuration.md) для подробностей.

Такой тип документа работает практически в каждой современной среде Markdown. Он использует заголовки, абзацы, списки, закрытый код и обычные ссылки, не полагаясь на расширения специфичные для диалектов.

GitHub Flavored Markdown: CommonMark для проектов программного обеспечения

GitHub Flavored Markdown — это формальный диалект на базе CommonMark. Он сохраняет модель разбора CommonMark и добавляет функции, обычно необходимые для документации репозиториев и сотрудничества.

Формальная спецификация GFM добавляет:

  • Таблицы с вертикальными линиями (pipe tables)
  • Элементы списка задач
  • Зачеркивание текста
  • Расширенные автоматические ссылки
  • Ограничения вокруг некоторых тегов сырого HTML

Эти расширения стали настолько распространенными, что многие пользователи считают их частью стандартного Markdown. Они не являются частью ядра CommonMark.

Таблицы GFM

| Бэкенд | Лучшее применение |
|---|---|
| Ollama | Локальные эксперименты |
| vLLM | Общий инференс |
| SGLang | Структурированные рабочие нагрузки |

Строгий парсер CommonMark может трактовать это как обычный текстовый абзац. Парсер, совместимый с GFM, распознает это как таблицу. Для более глубокого взгляда на синтаксис таблиц и варианты выравнивания см. Таблицы в Markdown.

Списки задач GFM

- [x] Установить Docker
- [x] Загрузить модель
- [ ] Добавить мониторинг

Синтаксис списка задач полезен в задачах, запросах на включение и документации проекта. Вне поддерживающего рендерера он может выглядеть как обычный список, содержащий буквальные квадратные скобки.

Зачеркивание GFM

Используйте ~~старый endpoint~~ новый endpoint.

Зачеркивание широко поддерживается, но оно все еще является расширением, а не переносимым синтаксисом CommonMark.

Автоматические ссылки GFM

GFM распознает больше текста, похожего на URL и электронную почту, без необходимости угловых скобок или явного синтаксиса ссылок.

Посетите https://example.com/docs для подробностей.

В строгом CommonMark явные автоматические ссылки используют угловые скобки:

<https://example.com/docs>

Явная форма безопаснее, когда документ должен пройти через неизвестные процессоры Markdown.

GitHub.com поддерживает больше, чем формальный GFM

Частый источник путаницы — это предположение, что каждая функция Markdown, видимая на GitHub, принадлежит к спецификации GFM.

Это не так.

GitHub.com добавляет обработку и функции на уровне платформы вокруг парсера GFM. В зависимости от контекста GitHub может поддерживать:

  • Математические выражения
  • Диаграммы Mermaid
  • Предупреждения (Alerts)
  • Ссылки на задачи и запросы на включение
  • Упоминания пользователей и команд
  • Ссылки на коммиты
  • Короткие коды эмодзи
  • Сворачиваемые секции HTML
  • Предпросмотр цветов
  • Ссылки, относительные к репозиторию
  • Автоматические якоря заголовков

Некоторые из этих функций являются расширениями синтаксиса. Другие — это поведение постобработки или интеграции с данными GitHub.

Это различие важно, потому что другой рендерер может точно утверждать о совместимости с GFM, не реализуя рендерер математики GitHub, интеграцию Mermaid, ссылки на задачи или стилизацию предупреждений.

Диаграммы Mermaid в GitHub

GitHub отображает закрытый блок кода, помеченный mermaid, как диаграмму:

```mermaid
flowchart LR
    A[Markdown] --> B[Отрендеренная диаграмма]
```

Общий рендерер GFM может отобразить тот же блок как выделенный исходный код. Markdown остается валидным, но улучшенное отображение является специфичным для платформы. Для практического введения в синтаксис Mermaid см. Быстрый старт диаграмм Mermaid.

Математические выражения в GitHub

GitHub поддерживает встроенные и блочные математические выражения, используя разделители доллара и дополнительные формы экранирования.

Размер кэша составляет примерно $2nlhd$ байт.
$$
C = 2nlhd
$$

Математика не является частью формального GFM. Перенос этого контента в другой рендерер требует совместимого расширения для математики, такого как KaTeX, MathJax или поддержка математики Pandoc.

Предупреждения GitHub

GitHub поддерживает блочные цитаты в стиле предупреждений, такие как:

> [!WARNING]
> Изменение этой настройки очищает кэш.

На GitHub это может выглядеть как стилизованное предупреждение. На простом рендерере CommonMark оно обычно выглядит как обычная блочная цитата, содержащая [!WARNING].

Этот откат читабелен, что делает предупреждения GitHub менее опасными, чем расширения, которые исчезают полностью. Они все еще не являются переносимыми элементами представления.

Pandoc Markdown: Markdown как язык документов

Pandoc Markdown предназначен для преобразования документов, а не для одного конкретного веб-сайта. Он использует Markdown как исходный синтаксис для создания HTML, PDF, DOCX, EPUB, LaTeX, презентаций и других форматов.

Его ридер Markdown по умолчанию включает большой набор расширений. Важные возможности включают:

  • Блоки метаданных YAML
  • Сноски
  • Цитаты
  • Несколько форматов таблиц
  • Списки определений
  • Математические обозначения
  • Идентификаторы и атрибуты заголовков
  • Атрибуты блоков кода
  • Закрытые дивы (Fenced divisions)
  • Скобочные спаны
  • Верхний и нижний индексы
  • Зачеркивание
  • Блоки строк
  • Нумерованные списки примеров
  • Сырой LaTeX
  • Сырой HTML
  • Автоматическая нумерация разделов
  • Обработка библиографии

Pandoc Markdown гораздо более выразителен, чем CommonMark или формальный GFM. Эта выразительность делает его мощным для публикации, но менее безопасным как формат обмена.

Сноски Pandoc

У Markdown есть несколько несовместимых диалектов.[^dialects]

[^dialects]: CommonMark, GFM и Pandoc Markdown — три
    важных примера.

Синтаксис сносков поддерживается многими современными инструментами, но он не является частью CommonMark или формального GFM.

В настоящее время GitHub отображает сноски в нескольких контекстах контента, но это функция платформы GitHub, а не формальная гарантия GFM. Рендерер, заявляющий только о совместимости с CommonMark или GFM, может не поддерживать их.

Цитаты Pandoc

PagedAttention улучшает управление памятью KV-кэша
[@kwon2023pagedattention].

С файлом библиографии и стилем цитирования Pandoc может разрешить это в форматированную академическую цитату и библиографию.

pandoc article.md \
  --citeproc \
  --bibliography references.bib \
  --csl ieee.csl \
  -o article.pdf

Синтаксис цитирования остается читаемым в неподдерживаемом рендерере, но он не станет форматированной ссылкой без Pandoc или другого совместимого процессора цитат. Гибкость ридера Pandoc также лежит в основе рабочих процессов преобразования в другом направлении — см. преобразование документов Word в Markdown для практического примера использования расширенного диалекта Pandoc в качестве промежуточного формата.

Списки определений Pandoc

CommonMark
: Точная спецификация для ядра Markdown.

GFM
: Диалект на базе CommonMark с расширениями, ориентированными на программное обеспечение.

Pandoc Markdown
: Расширенный формат авторства для преобразования документов.

Списки определений полезны в руководствах, глоссариях и технических книгах. Они обычно плохо деградируют в рендерерах, которые их не поддерживают, потому что строки с двоеточиями остаются видимыми как обычный текст.

Атрибуты заголовков Pandoc

## Конфигурация кэша {#cache-config .deployment}

Pandoc интерпретирует фигурные скобки как явный идентификатор и список классов. Многие другие рендереры Markdown показывают текст атрибута непосредственно в заголовке.

Это один из самых четких примеров полезного синтаксиса, который не следует помещать в документ, ожидаемый к отображению везде.

Закрытые дивы Pandoc

::: warning
Изменение этой опции перезапускает сервер.

Pandoc преобразует это в структурный див с классом. Шаблоны, CSS, фильтры или писатели вывода могут решить, как эта структура должна выглядеть.

Большинство рендереров CommonMark и GFM не распознают этот забор. Они отображают двоеточия и контент как обычный текст.

CommonMark против GFM против Pandoc Markdown

Следующая матрица описывает формальные диалекты, а не каждую функцию, добавленную GitHub.com, Hugo, Obsidian, GitLab или другой платформой.

Функция CommonMark Формальный GFM Pandoc Markdown
Заголовки Да Да Да
Упор Да Да Да
Ссылки и изображения Да Да Да
Блочные цитаты Да Да Да
Нумерованные и ненумерованные списки Да Да Да
Закрытые блоки кода Да Да Да
Синтаксис сырого HTML Да Ограничен в некоторых контекстах Да
Таблицы с вертикальными линиями Нет Да Да
Списки задач Нет Да Да
Зачеркивание Нет Да Да
Расширенные автоматические ссылки Нет Да Конфигурируемо
Сноски Нет Нет Да
Цитаты Нет Нет Да
Метаданные YAML Нет Нет Да
Списки определений Нет Нет Да
Математические обозначения Нет Нет Да
Атрибуты заголовков Нет Нет Да
Закрытые дивы Нет Нет Да
Сырой LaTeX Нет Нет Да
Обработка библиографии Нет Нет Да

Слово «Нет» не означает, что платформа никогда не может поддерживать функцию. Это означает, что функция не гарантируется формальной спецификацией этого диалекта.

Какой синтаксис работает на GitHub?

Для файлов README, задач, запросов на включение, обсуждений и вики GFM является естественной базовой линией.

Вы обычно можете использовать:

  • Синтаксис CommonMark
  • Таблицы
  • Списки задач
  • Зачеркивание
  • Расширенные автоматические ссылки
  • Заборы кода с подсветкой синтаксиса
  • Специфичные для GitHub ссылки
  • Поддерживаемую GitHub математику
  • Поддерживаемые GitHub диаграммы
  • Предупреждения GitHub
  • Сноски там, где они поддерживаются поверхностью контента

Риск переносимости начинается, когда GitHub выполняет дополнительную рендеризацию за пределами формального GFM. Диаграммы Mermaid, математические обозначения, ссылки на задачи и представление предупреждений могут не выжить вне GitHub.

Для файлов репозитория, которые также публикуются в другом месте, тестируйте источник во втором рендерере, а не считайте предпросмотр GitHub авторитетным.

Какой синтаксис работает в Hugo?

Hugo использует Goldmark в качестве рендерера Markdown по умолчанию. Goldmark соответствует CommonMark и предоставляет расширения, совместимые с важными частями GFM.

В типичной конфигурации Hugo хорошо работают следующие элементы:

  • Структура CommonMark
  • Закрытые блоки кода
  • Таблицы с вертикальными линиями
  • Зачеркивание
  • Списки задач
  • Автоматические идентификаторы заголовков
  • Подсветка синтаксиса
  • Сноски, когда расширение включено
  • Списки определений, когда включены
  • Типографские замены, когда включены

Hugo также добавляет функции за пределами Markdown через:

  • Front matter (метаданные)
  • Шорткоды
  • Хуки рендеризации
  • Ресурсы страниц
  • Функции внутренних ссылок
  • Обработку шаблонов
  • Конфигурацию сайта

Эти функции Hugo не перемещаются вместе с файлом Markdown. Для практического примера развертывания Hugo см. Развертывание Hugo в AWS S3.

Front Matter Hugo — это не контент Markdown

Страница Hugo обычно начинается с метаданных YAML, TOML или JSON:

---
title: "Совместимость Markdown"
description: "Сравнение диалектов и рендереров Markdown."
date: 2026-07-31
tags:
  - Markdown
  - документация
---

Pandoc также может распознавать блоки метаданных YAML, но он интерпретирует поля в соответствии со своими собственными шаблонами и писателями. GitHub обычно отображает блок как секцию, похожую на YAML, или рассматривает его как метаданные репозитория только в определенных системах.

Таким образом, один и тот же синтаксис может быть распознан более чем в одном инструменте, не имея одинаковой семантики.

Сырой HTML в Hugo

Goldmark по умолчанию не рендерит потенциально небезопасный сырой HTML в стандартной конфигурации Hugo.

Блок, такой как:

<div class="notice">
  Перезапустите сервис после изменения этого значения.
</div>

может быть опущен, если рендеризация сырого HTML не включена или контент не реализован через шорткод или хук рендеризации.

Для контролируемого технического блога включение сырого HTML может быть разумным. Это все еще делает источник менее переносимым и должно быть осознанным решением на уровне сайта.

Mermaid в Hugo

Закрытый блок mermaid все еще является просто блоком кода, если тема Hugo, хук рендеризации, шорткод или конвейер JavaScript не преобразует его в диаграмму.

GitHub и Hugo могут поэтому принимать идентичный исходный код Mermaid, используя совершенно разные механизмы рендеризации.

Какой синтаксис работает в Pandoc?

Pandoc может явно читать несколько диалектов Markdown:

pandoc --from=markdown input.md
pandoc --from=commonmark input.md
pandoc --from=gfm input.md
pandoc --from=commonmark_x input.md

Это одно из самых полезных свойств переносимости Pandoc. Оператор может сказать Pandoc, какой диалект использует источник, вместо того чтобы полагаться на размытое расширение файла .md.

Pandoc также позволяет включать или отключать отдельные расширения:

pandoc \
  --from=markdown-footnotes-pipe_tables \
  input.md \
  -o output.html

Или начать с более узкого формата и добавить одну функцию:

pandoc \
  --from=commonmark+footnotes \
  input.md \
  -o output.html

Вы можете проверить доступные расширения с помощью:

pandoc --list-extensions=markdown
pandoc --list-extensions=commonmark
pandoc --list-extensions=gfm

Эта модель расширений мощна, но это означает, что «Pandoc Markdown» не всегда является одной фиксированной конфигурацией. Команды сборки и файлы значений по умолчанию являются частью спецификации документа.

Какой синтаксис работает в Obsidian?

Obsidian хранит заметки как файлы Markdown, но его модель авторства включает несколько специфичных для приложения функций.

Общие примеры включают:

  • Вики-ссылки
  • Встроенные заметки
  • Встроенные файлы
  • Выделенные блоки (Callouts)
  • Блочные ссылки
  • Теги
  • Свойства
  • Выделение
  • Комментарии
  • Запросы Dataview из плагинов
  • Специфичные для приложения URI-ссылки

Вики-ссылка, такая как:

[[Совместимость Markdown]]

имеет смысл внутри хранилища Obsidian. GitHub, CommonMark и ридер Pandoc по умолчанию обычно отображают ее как буквальный текст в скобках.

Встраивание еще более специфично для приложения:

![[compatibility-table]]

Ссылочный контент не присутствует в самом файле. Таким образом, экспорт или публикация заметки требует шага расширения, который разрешает встраивание.

Obsidian — хороший пример того, почему хранение в файлах .md не гарантирует переносимость Markdown. Для практического взгляда на Obsidian как инструмент управления знаниями см. Obsidian для персонального управления знаниями.

Какой синтаксис работает в GitLab?

GitLab Flavored Markdown использует CommonMark как свое ядро и включает функции GFM, такие как таблицы и списки задач. Затем он добавляет специфичное для GitLab поведение, включая перекрестные ссылки, математические обозначения, диаграммы и другие функции сотрудничества.

README, написанный в консервативном GFM, обычно перемещается между GitHub и GitLab без серьезных повреждений.

Платформенные интеграции не перемещаются так надежно. Ссылки на задачи, упоминания пользователей, диаграммы, обработка математики и специальный блочный синтаксис могут вести себя по-разному, даже когда базовый Markdown остается читаемым.

Матрица поддержки платформ

Эта матрица описывает обычное поведение по умолчанию. Темы, плагины, расширения и конфигурация могут изменять отдельные ячейки.

Функция GitHub Hugo Goldmark Pandoc Obsidian GitLab
Ядро CommonMark Да Да Да В основном Да
Таблицы с вертикальными линиями Да Да Да Да Да
Списки задач Да Да Да Да Да
Зачеркивание Да Да Да Да Да
Сноски Да Конфигурируемо Да Да Да
Метаданные YAML Зависит от контекста Front matter Да Свойства Зависит от контекста
Математика Да Требует настройки Да Да Да
Mermaid Да Требует настройки Зависит от вывода Да Да
Цитаты Нет встроенной библиографии Требует инструментов Да Зависит от плагина Нет встроенной библиографии
Списки определений Нет Конфигурируемо Да Ограничено Ограничено
Атрибуты заголовков Ограничено Зависит от рендерера Да Ограничено Ограничено
Вики-ссылки Нет Нет по умолчанию Нет по умолчанию Да Зависит от вики
Callouts или предупреждения Синтаксис GitHub Тема или шорткод Зависит от шаблона Синтаксис Obsidian Синтаксис GitLab
Сырой HTML Санитизирован или ограничен Отключен по умолчанию Да Зависит от контекста Санитизирован или ограничен

«Да» все еще не гарантирует идентичный HTML или визуальное представление. Это означает, что среда распознает общую функцию.

Синтаксис, который обычно безопасен везде

Самый безопасный переносимый подмножество включает:

  • Заголовки ATX, использующие #
  • Обычные абзацы
  • Пустые строки между блоками
  • - для ненумерованных списков
  • 1. для нумерованных списков
  • Закрытые блоки кода, использующие обратные кавычки
  • Встроенный код, использующий обратные кавычки
  • Упор, использующий *text*
  • Сильный упор, использующий **text**
  • Обычные ссылки
  • Обычные изображения
  • Блочные цитаты
  • Тематические разрывы
  • Явные автоматические ссылки с угловыми скобками

Намеренно консервативный документ может выглядеть так:

# Руководство по развертыванию

Это руководство объясняет, как развернуть сервис.

## Требования

- Docker
- Linux
- Поддерживаемая GPU

## Конфигурация

Создайте файл с именем `compose.yaml`.

```yaml
services:
  application:
    image: example/application:1.0
```

Для дополнительной информации см. [справочник по конфигурации](config.md).

> Сделайте резервную копию существующих данных перед обновлением.

Этот синтаксис хорошо переносится, потому что он не зависит от таблиц, сносков, атрибутов, выделенных блоков или платформенной обработки.

Синтаксис, который часто ломается

Проблемы с переносимостью, как правило, группируются вокруг небольшого числа функций.

Таблицы с вертикальными линиями

Таблицы с вертикальными линиями хорошо поддерживаются инструментами, ориентированными на GFM, но не строгим CommonMark.

Таблица может деградировать в нечитаемый текст при прохождении через парсер, который ее не распознает. Для высоко переносимых документов рассмотрите короткие списки или семантический HTML, сгенерированный во время шага сборки.

Сноски

Синтаксис сносков стал распространенным, но он остается расширением.

Различные инструменты могут:

  • Поддерживать только один формат сносков
  • Размещать сноски по-разному
  • Генерировать разные идентификаторы
  • Отклонять многострочные сноски
  • Рендерить источник буквально

Используйте сноски, когда конвейер публикации известен. Избегайте зависимости от них в файлах README, которые должны отображаться через произвольные системы.

Идентификаторы и атрибуты заголовков

Этот синтаксис Pandoc не переносим:

## Установка {#installation .procedure}

Используйте обычный заголовок и позвольте рендереру сгенерировать свой собственный якорь, когда важна переносимость.

Также избегайте жесткой кодировки ссылок на автоматически сгенерированные идентификаторы заголовков, если каждая цель не использует одинаковые правила слогификации.

Callouts и предупреждения

GitHub, Obsidian, GitLab, MkDocs, Docusaurus и темы Hugo могут поддерживать блоки, похожие на callouts, но они часто используют разный синтаксис.

Переносимый откат — это обычная блочная цитата:

> Предупреждение: Сделайте резервную копию базы данных перед обновлением.

Это менее визуально впечатляюще, но оно сохраняет смысл везде.

Вики-ссылки

Вики-ссылки лаконичны внутри инструментов управления знаниями:

[[KV Cache]]

Они являются плохим синтаксисом обмена, потому что целевой путь, имя файла, правила заголовков и поведение разрешения принадлежат приложению.

Используйте стандартные ссылки Markdown в контенте, предназначенном для публикации:

[KV cache](kv-cache.md)

Сырой HTML

Сырой HTML — это обычный аварийный выход, когда Markdown не может выразить макет. Это также частая проблема переносимости и безопасности.

Рендерер может:

  • Удалить HTML
  • Экранировать его
  • Санитизировать выбранные элементы
  • Разрешить блоки, но не встроенные элементы
  • Отказываться от разбора Markdown внутри HTML
  • Передавать его неизменным только в доверенном режиме

Используйте сырой HTML только тогда, когда цель публикации контролируется.

Математические обозначения

Математика с разделителями доллара популярна, но не интерпретируется универсально.

Исходный код:

Сложность составляет $O(n^2)$.

может стать:

  • Отрендеренной математикой
  • Обычным текстом со знаками доллара
  • Неправильным упором
  • Вводом для другого парсера математики

Выберите один конвейер математики и протестируйте его в каждой целевой среде.

Блоки диаграмм Mermaid и других

Забор кода Mermaid синтаксически безопасен, потому что неподдерживаемые рендереры обычно отображают его как код.

Семантический результат все еще различен. Читатели могут увидеть отрендеренную диаграмму архитектуры на GitHub и исходный код Mermaid в другой среде.

Это изящная деградация, а не истинная совместимость.

Три уровня совместимости Markdown

Помогает разделить совместимость на три уровня.

Уровень 1: Совместимость разбора

Распознает ли парсер структуру?

Примеры включают заголовки, таблицы, сноски и закрытые дивы.

Уровень 2: Совместимость трансформации

Применяет ли платформа дополнительную обработку?

Примеры включают:

  • Рендеринг Mermaid
  • Разрешение цитат
  • Расширение вики-ссылок
  • Ссылки на номера задач
  • Обработка шорткодов
  • Генерация таблицы содержания

Уровень 3: Совместимость представления

Выглядит и ведет ли результат соответствующим образом?

Примеры включают:

  • Стилизацию таблиц
  • Подсветку синтаксиса
  • Цвета предупреждений
  • Якоря заголовков
  • Адаптивные изображения
  • Размещение сносков
  • Шрифты математики

Две платформы могут разобрать идентичный синтаксис, производя существенно различное представление.

Лучшая модель переносимости

Вместо того чтобы спрашивать, является ли файл «валидным Markdown», задайте четыре более узких вопроса:

  1. В каком диалекте написан источник?
  2. Какой парсер его читает?
  3. Какие расширения включены?
  4. Какие платформенные трансформации запускаются после этого?

Например:

Диалект: CommonMark плюс таблицы GFM
Парсер: Goldmark
Расширения: таблицы, зачеркивание, списки задач, сноски
Платформа: Hugo
Дополнительная обработка: хуки рендеризации и JavaScript Mermaid

Это описание гораздо полезнее, чем сказать «сайт использует Markdown».

Выбор диалекта по случаю использования

Файлы README

Используйте GFM.

Файлы README выигрывают от:

  • Таблиц
  • Списков задач
  • Закрытого кода
  • Автоматических ссылок
  • Зачеркивания
  • Ссылок GitHub

Избегайте чрезмерной зависимости от функций, доступных только на GitHub, когда репозиторий зеркалируется на GitLab, рендерится на реестре пакетов или включается в сгенерированную документацию.

Технические статьи Hugo

Используйте Markdown, совместимый с CommonMark, с документированным набором расширений Goldmark.

Таблицы, заборы кода, сноски и Mermaid могут быть разумными, потому что вы контролируете конвейер сборки. Предпочитайте шорткоды Hugo или хуки рендеризации внедрению больших объемов сырого HTML.

Держите специфичный для Hugo синтаксис изолированным и легким для поиска.

Академические документы

Используйте Pandoc Markdown.

Цитаты, обработка библиографии, сноски, метаданные, математические обозначения, перекрестные ссылки и преобразование в PDF или DOCX оправдывают сниженную переносимость.

Храните команду Pandoc, файл значений по умолчанию, фильтры, библиографию и шаблоны рядом с источником. Сам файл источника не описывает сборку полностью.

Книги и документация в длинном формате

Pandoc Markdown обычно является сильнейшим из трех вариантов, когда важно несколько форматов вывода.

Списки определений, цитаты, атрибуты, метаданные и структурированные трансформации становятся более важными по мере роста сложности документа.

Для документации только для веба, размещенной в репозитории Git, GFM или генератор документации на базе CommonMark могут оставаться проще.

Заметки и базы персональных знаний

Используйте нативный синтаксис выбранного приложения для заметок, когда функции приложения предоставляют реальную ценность.

Вики-ссылки, встраивания и callouts Obsidian полезны внутри хранилища. Рассматривайте экспорт как процесс компиляции, а не предполагайте, что сырые файлы уже являются переносимыми публикациями.

Общая документация через неизвестные системы

Используйте консервативный подмножество CommonMark.

Избегайте:

  • Вики-ссылок
  • Платформенных предупреждений
  • Атрибутов заголовков
  • Цитат
  • Сырого HTML
  • Пользовательских контейнеров
  • Приложений встраивания
  • Шорткодов

Переносимость обычно требует отказа от удобных функций.

Практические правила для переносимого Markdown

Начните со структуры CommonMark

Используйте CommonMark для скелета документа:

  • Заголовки
  • Абзацы
  • Списки
  • Ссылки
  • Изображения
  • Блочные цитаты
  • Блоки кода

Это обеспечивает, что основное значение выживает даже при сбое опциональных расширений.

Добавляйте функции GFM осознанно

Таблицы и списки задач разумны, когда все важные цели их поддерживают.

Не предполагайте, что «большинство инструментов поддерживают GFM», не тестируя точную цель. Некоторые заявляют о совместимости с GFM, включая только выбранные расширения.

Изолируйте платформенные расширения

Держите специфичный для платформы синтаксис в четко идентифицируемых блоках.

Например, централизуйте шорткоды Hugo, цитаты Pandoc или встраивания Obsidian, а не раскидывайте их через каждый абзац.

Изоляция облегчает последующее преобразование.

Предпочитайте изящную деградацию

Блок Mermaid деградирует в читаемый исходный код. Предупреждение GitHub деградирует в блочную цитату.

Встраивание вики может деградировать в необъяснимое имя файла, в то время как закрытый див Pandoc может обнажить пунктуацию вокруг контента.

Выбирайте расширения, чей откат остается понятным.

Не полагайтесь на автоматически сгенерированные идентификаторы заголовков

Алгоритмы якорей заголовков различаются между GitHub, Hugo, Pandoc и генераторами документации.

Для ссылок между документами используйте явные идентификаторы, поддерживаемые рендерером, только когда целевой конвейер контролируется. В противном случае ссылитесь на документ, а не на сгенерированный фрагмент.

Храните конфигурацию сборки с контентом

Расширения Pandoc, настройки Hugo, плагины, фильтры и интеграции JavaScript определяют, как ведет себя Markdown.

Коммитьте соответствующие файлы конфигурации с источником:

content/
  article.md
pandoc.yaml
references.bib
config/
  _default/
    markup.yaml
layouts/
  _default/
    _markup/

Одного расширения .md недостаточно, чтобы захватить среду публикации. Для структурированного подхода к документированию этих решений см. Записи решений для разработки, управляемой ИИ.

Тестируйте Markdown против каждой важной цели

Визуальный предпросмотр в одном редакторе недостаточен. Редактор может поддерживать более богатый диалект, чем производственный рендерер.

Для Pandoc тестируйте явные форматы ввода:

pandoc --from=commonmark article.md -o commonmark.html
pandoc --from=gfm article.md -o gfm.html
pandoc --from=markdown article.md -o pandoc.html

Предупреждения и видимая пунктуация источника раскрывают, какие функции специфичны для диалекта.

Для Hugo постройте производственный сайт:

hugo --gc --minify

Затем проверьте сгенерированный HTML, а не полагайтесь только на предпросмотр редактора.

Для репозиториев просматривайте закоммиченный файл на фактической платформе хостинга. Локальные расширения Markdown в VS Code могут не соответствовать GitHub или GitLab.

Устранение неполадок общих несоответствий рендеризации

Когда файл, который работал на одной платформе, ломается на другой, сбой обычно попадает в один из нескольких повторяющихся паттернов. Таблица ниже перечисляет симптом так, как вы его на самом деле увидите, наиболее вероятную причину и конкретную команду или проверку для подтверждения и исправления.

Симптом Вероятная причина Подтвердите и исправьте
Таблица с вертикальными линиями рендерится как один длинный абзац с видимыми символами | Рендерер — строгий CommonMark без расширения таблиц Запустите pandoc --from=commonmark file.md -o test.html и проверьте вывод; либо включите расширение таблиц, либо экспортируйте с --from=gfm
[^note] остается встроенным как буквальный текст вместо того, чтобы стать маркером сноска верхнего индекса Расширение сноска Goldmark не включено В Hugo проверьте наличие footnote под markup.goldmark.extensions в hugo.yaml, перестройте с hugo --gc --minify и поищите <sup> в сгенерированном HTML
Забор ```mermaid показывает как простой серый исходный код вместо диаграммы Платформа не выполняет постобработку закрытого блока GitHub рендерит его нативно; Hugo требует хука рендеризации, шорткода или JS-конвейера — проверьте сгенерированный HTML на наличие <pre><code class="language-mermaid"> против <svg>
## Заголовок {#id} показывает буквальные фигурные скобки в отрендеренном тексте заголовка Синтаксис атрибутов заголовка специфичен для Pandoc, а не CommonMark или GFM Удалите синтаксис атрибута для переносимого вывода или предварительно преобразуйте с pandoc --from=markdown --to=gfm file.md -o out.md
[[Имя заметки]] отображается как буквальные двойные квадратные скобки Синтаксис вики-ссылок специфичен для приложений, таких как Obsidian Замените стандартной ссылкой Markdown, [Имя заметки](note-name.md), перед экспортом за пределы хранилища
[@kwon2023pagedattention] остается как простой текст в скобках вместо форматированной цитаты Не применялся проход библиографии или citeproc Запустите снова с pandoc --citeproc --bibliography=refs.bib input.md -o output.pdf и подтвердите, что стиль CSL указан
> [!WARNING] рендерится как обычный цитируемый абзац вместо стилизованного предупреждения Стилизация предупреждений — функция платформы GitHub.com, а не часть формального GFM Ожидается вне GitHub; держите текст читаемым как обычную блочную цитату, а не полагайтесь на цветовую стилизацию

Это самый быстрый первый прогон перед предположением об «ошибке» Markdown — большинство этих несоответствий — отсутствующее расширение или функция только для платформы, а не сломанный синтаксис. Для проблем, специфичных для заборов кода, таких как отсутствующая подсветка синтаксиса или неподдерживаемые идентификаторы языков, см. посвященное руководство по блокам кода Markdown.

Линтинг переносимого подмножества

Линтер Markdown не может гарантировать совместимость рендерера, но он может убрать избежимую неоднозначность.

Полезные правила включают:

  • Используйте согласованные стили заголовков
  • Добавляйте пустые строки вокруг списков и блоков кода
  • Используйте закрытый, а не отступленный код
  • Указывайте языки заборов кода
  • Избегайте пропуска уровней заголовков
  • Используйте согласованные маркеры списков
  • Избегайте неоднозначного упора вокруг пунктуации
  • Держите окончания строк согласованными
  • Валидируйте ссылки и изображения

Для публикации с несколькими целями добавьте тест сборки для каждого важного рендерера, а не полагайтесь только на линтинг синтаксиса.

Преобразование между диалектами с помощью Pandoc

Pandoc может нормализовать документы из одного диалекта в другой:

pandoc \
  --from=markdown \
  --to=gfm \
  article.md \
  -o article-gfm.md

Или преобразуйте GFM в Pandoc Markdown:

pandoc \
  --from=gfm \
  --to=markdown \
  README.md \
  -o document.md

Это полезно, но преобразование не гарантировано сохранить каждую функцию.

Потенциальные потери включают:

  • Платформенные ссылки
  • Стилизацию callouts
  • Сложные таблицы
  • Встроенные объекты приложений
  • Пользовательские атрибуты
  • Поведение сырого HTML
  • Синтаксис плагинов
  • Рендеринг диаграмм
  • Точные пробелы и форматирование

Pandoc сохраняет структуру документа лучше, чем исходное форматирование. Рассматривайте преобразование как шаг сборки, а не как обратимый текстовый форматтер.

Рекомендуемая стратегия для сайтов Hugo

Для технического блога на Hugo самая практическая политика:

  1. Используйте CommonMark для основного текста и структуры.
  2. Включите небольшой документированный набор расширений Goldmark.
  3. Используйте таблицы и списки задач в стиле GFM там, где они улучшают читаемость.
  4. Реализуйте Mermaid через один согласованный хук рендеризации или шорткод.
  5. Обрабатывайте математику через один документированный конвейер KaTeX или MathJax.
  6. Используйте front matter Hugo только в начале файлов контента.
  7. Предпочитайте хуки рендеризации и шорткоды сырому HTML.
  8. Держите исходные ссылки как стандартные ссылки Markdown, где возможно.
  9. Тестируйте перенесенные или внешние документы через Hugo.
  10. Документируйте любой синтаксис, который не будет рендериться правильно на GitHub.

Этот подход принимает, что контент Hugo не является универсально переносимым, сохраняя границу переносимости видимой.

Худший подход — случайное смешение диалектов: предупреждения GitHub, встраивания Obsidian, атрибуты Pandoc и шорткоды Hugo, помещенные в один документ без определенного конвейера сборки.

Таблица решений

Случай использования Рекомендуемый синтаксис Причина
Переносимый документ в виде обычного текста CommonMark Наименьшая надежная базовая линия
README GitHub GFM Таблицы, задачи и рабочие процессы репозитория
Шаблон задачи GitHub GFM плюс функции GitHub Платформа является целевой
Пост блога Hugo CommonMark плюс настроенные расширения Goldmark Контролируемый конвейер публикации
Научная статья Pandoc Markdown Цитаты, математика, метаданные, вывод PDF
Книга в нескольких форматах Pandoc Markdown Структурированное преобразование во многие выходы
Хранилище Obsidian Obsidian Markdown Обратные ссылки, встраивания и рабочие процессы знаний
Зеркало GitHub и GitLab Консервативный GFM Сильный набор общих функций
Неизвестный рендерер Подмножество CommonMark Наименьший риск совместимости

Заключение

CommonMark, GitHub Flavored Markdown и Pandoc Markdown — не конкурирующие версии одного продукта. Они решают разные проблемы.

CommonMark предоставляет надежную основу для разбора. GFM добавляет практические функции для сотрудничества в разработке программного обеспечения, в то время как Pandoc Markdown превращает Markdown в богатый исходный язык для публикации и преобразования.

Правило безопасности простое: пишите наименьший диалект, который удовлетворяет реальной цели. Используйте CommonMark, когда контент должен путешествовать, GFM, когда сотрудничество в стиле GitHub является целью, и Pandoc Markdown, когда структура документа и форматы вывода важнее универсальной рендеризации.

Переносимость Markdown достигается не избеганием каждого расширения. Она достигается знанием того, какие расширения являются частью контракта источника, и тестированием их в каждом рендерере, который имеет значение.

Ссылки

Подписаться

Получайте новые материалы про системы, инфраструктуру и AI engineering.