Метод marked.lexer

Метод marked.lexer является фундаментальной частью библиотеки Marked для работы с Markdown в JavaScript. Его основная задача — разбор Markdown-текста на токены, которые затем могут быть обработаны для генерации HTML или других форматов. Этот метод позволяет получить детализированное представление структуры документа без немедленного рендеринга в HTML, что особенно важно при построении собственных парсеров, редакторов и инструментов анализа Markdown.


Основные принципы работы

marked.lexer принимает на вход строку с Markdown-контентом и возвращает массив токенов. Каждый токен представляет собой объект с определённым типом, содержимым и дополнительными свойствами, которые уточняют его назначение.

Сигнатура метода:

const tokens = marked.lexer(src, options);
  • src — исходный Markdown-текст (тип string).
  • options — объект с настройками парсера. Позволяет управлять поведением лексера, например, включить поддержку GitHub Flavored Markdown (GFM), таблиц, автоматических ссылок и т.д.

Структура токенов

Каждый токен — это объект с обязательным полем type, которое определяет его категорию. Основные типы токенов:

  • heading — заголовок. Содержит depth (уровень заголовка) и text.

  • paragraph — абзац. Поле text содержит исходный текст.

  • list — список. Поля:

    • ordered — булево значение, упорядоченный ли список.
    • items — массив токенов-элементов списка.
  • list_item — элемент списка. Может содержать вложенные токены.

  • blockquote — блок цитаты. Поле tokens содержит массив вложенных токенов.

  • code — блок кода. Поля text и lang (язык программирования).

  • hr — горизонтальная линия.

  • table — таблица. Поля header (массив заголовков), align (выравнивание колонок) и rows (массив массивов ячеек).

Пример токена заголовка:

{
  type: 'heading',
  depth: 2,
  text: 'Пример заголовка'
}

Опции метода

Настройки marked.lexer влияют на разбор Markdown. Ключевые параметры:

  • gfm (boolean) — включает поддержку расширенного синтаксиса GitHub (таблицы, задачи, автоматические ссылки).
  • breaks (boolean) — перенос строки в Markdown преобразуется в <br> в HTML.
  • pedantic (boolean) — строгий режим, близкий к оригинальному Markdown.
  • smartLists (boolean) — улучшенный анализ списков.
  • smartypants (boolean) — преобразование обычных кавычек и тире в типографские символы.

Пример использования с опциями:

const tokens = marked.lexer('# Заголовок\n\nТекст абзаца', { gfm: true, breaks: true });

Обработка вложенных элементов

Лексер анализирует вложенность элементов. Например, список может содержать абзацы, кодовые блоки или даже другие списки. Для доступа к этим элементам используется поле tokens или items:

const markdown = `
- Пункт 1
  - Подпункт 1
- Пункт 2
`;

const tokens = marked.lexer(markdown);
console.log(tokens[0].items[0].tokens[0].text); // 'Подпункт 1'

Такой подход позволяет построить полное дерево документа для последующего анализа или кастомного рендеринга.


Применение marked.lexer в реальных задачах

  1. Создание редакторов Markdown — лексер позволяет выделять структуру документа для подсветки синтаксиса, автоформатирования и навигации по заголовкам.
  2. Статический анализ Markdown — проверка правильности форматирования, подсчет заголовков, поиск ссылок и изображений.
  3. Кастомный рендеринг — токены можно преобразовать в HTML, JSON или другой формат, минуя стандартный рендер Marked.
  4. Превью Markdown — быстрый парсинг документа без немедленного HTML-рендеринга, что ускоряет работу интерфейсов.

Важные нюансы

  • Метод не модифицирует исходный текст, он лишь возвращает массив токенов.
  • Лексер обрабатывает только синтаксическую часть, поэтому преобразование в HTML или другой формат требует использования marked.parser.
  • В случае сложных Markdown-конструкций (например, таблицы с многострочными ячейками) токены могут иметь вложенные массивы, что требует рекурсивной обработки.

Примеры токенизации

Простой пример:

const markdown = `
# Заголовок 1

Простой абзац текста.
`;

const tokens = marked.lexer(markdown);
console.log(tokens);

Результат:

[
  { type: 'heading', depth: 1, text: 'Заголовок 1' },
  { type: 'paragraph', text: 'Простой абзац текста.' }
]

Сложный пример с списком и блоком кода:

const markdown = `
- Пункт 1
- Пункт 2
\`\`\`js
console.log('Пример кода');
\`\`\`
`;

const tokens = marked.lexer(markdown);

Результат включает токены list с вложенными list_item и code.


Практические рекомендации

  • Всегда проверять опции gfm и breaks, если текст создается с использованием GitHub-совместимого Markdown.
  • Для обработки вложенных списков использовать рекурсивный обход items и tokens.
  • Для сложных документов предпочтительно сначала токенизировать весь текст, затем анализировать массив токенов, не комбинируя лексер с непосредственным рендерингом.

Метод marked.lexer обеспечивает гибкий и точный разбор Markdown, создавая основу для любых инструментов, работающих с этим форматом. Понимание структуры токенов и возможностей настройки лексера позволяет строить собственные парсеры, редакторы и анализаторы Markdown с высокой точностью и эффективностью.