Docs-as-Code позволяет работать с технической документацией по тем же принципам, что и с программным кодом: хранить ее в Git, проверять, версионировать и обновлять вместе с продуктом. Разбираем, как такой подход помогает сократить ручную работу и снизить затраты — на примере документации для наших продуктов «Бумк» и «Датасан».
Документация как призрак
Замечали ли вы, приходя на новый проект, что документация есть, но ею совершенно невозможно пользоваться? Страницы в Confluence устаревают с каждой готовой задачей. То там, то тут всплывают Google-документы. Часть документации передается из уст в уста, как былины и сказки. А другая важная информация прячется в чатах и письмах.
В такой ситуации документации воспринимается, как что-то скучное, вторичное и всегда отстающее от реальности. Такая документация замедляет онбординг новых сотрудников. Поддержка не может положиться на такую документацию при ответах клиентам. Клиенты не могут самостоятельно настроить продукт и работать с ним. А сам продукт проигрывает конкурентам, где документация актуальна и удобна для любой категории пользователей: от новичков, которым нужен быстрый старт, до разработчиков, реализующих интеграцию с помощью API.
Бизнес теряет не только лояльность клиентов и сотрудников, но и деньги: разрозненная документация превращается в постоянные операционные издержки. Сотрудники тратят время на поиск и перепроверку информации, а эксперты — на ответы на одни и те же вопросы. А если информация еще и хаотично хранится, велик риск утечек. Хорошо, если только технических — за любые персональные данные клиентов компаниям грозят многомилионные штрафы.
Есть и менее очевидный риск: знания остаются привязаны к конкретным людям. Если важную настройку знает только один разработчик или менеджер, его отпуск, увольнение или переход на другой проект стопорят работу всей команды.
Хорошая новость в том, что лучшие инженерные практики можно применять и при разработке текстов документации.
Философия Docs-as-Code
Docs-as-Code — набор инструментов, процессов и практик, позволяющих работать с текстами документации так же, как разработчики работают с программным кодом. Технические писатели, использующие эту парадигму:
С Docs-as-Code мы начинаем относиться к словам как к строкам кода. Мы применяем к ним линтинг, проводим через Review, прогоняем через CI/CD-пайплайны и, самое главное, начинаем видеть в документации Продукт. У этого продукта есть свой пользователь (разработчик или клиент) и свой интерфейс (портал документации).
Далее я расскажу о том, как работает подход Docs-as-Code, на примере наших продуктов «Бумк» и “Датасан».
Выбор инструментов и наш стек
Я пишу документацию на языке reStructuredText. Это легковесный язык разметки, который легко воспринимается человеком и парсится генераторами документации:

Почему reStructuredText, а не Markdown? RST чуть сложнее для изучения, но семантически богаче и функциональнее чем MD. Из «коробки» в RST мы получаем типизированные блоки для примеров кода, примечаний и предупреждений. Также reStructuredText имеет единый стандарт, в отличие от Markdown, для которого существуют десятки диалектов (flavors). Разные инструменты могут по-разному и даже с ошибками интерпретировать синтаксис диалектов.
Текст на RST можно писать в любом редакторе. Я использую:
<Легковесный и быстрый инструмент. Поддерживает пакеты для работы с Git и RST, что позволяет писателю не отвлекаться от контента;
Удобные плагины обеспечивают предпросмотр в реальном времени, автодополнение директив, проверку синтаксиса и интеграцию с линтерами.
В качестве сборщика итоговых документов я использую Sphinx. Sphinx позволяет собирать из одних и тех же исходников HTML-портал, PDF-руководство и DOCX-файл для согласования с клиентом. Для Sphinx разработано огромное количество расширений, например, для обработки OpenAPI-спецификаций, построения диаграмм, удобной работы с таблицами. Также в Sphinx встроена утилита для перевода текстов на различные языки. Это стало одним из главных преимуществ при выборе инструмента для документирования «Бумк», где документация нужна и на русском, и на английском языках.
Исходники документации мы храним в Github для «Бумк» и GitLab для «Датасан».
В «Бумк» для развертывания продукта используется Jenkins. И сборка документации встроена в пайплайн сборки «Бумк». Я передаю разработчикам команды для сборки документации, разработчики правят пайплайны. В «Датасан» документация пока собирается вручную, но над автоматизацией процесса идет работа.
Упрощенно процесс работы над документацией можно представить так:
- Технический писатель правит RST-файл в любимом редакторе.
- Локально проверяет сборку через Sphinx.
- Делает git push в GitHub/GitLab.
- Согласовывает тексты в команде
- CI/CD запускает финальный рендеринг и выкатывает «новую версию продукта» (документации) на сервер.
Что нам дал Docs-as-Code и выбранный стек
С использованием Docs-as-Code мы получаем ряд преимуществ.
Git
Все возможности Git, которые мы используем для работы с кодом, теперь применяются и для текстов документации.
Теперь легко найти, когда и в какой задаче изменился текст. Работа с Git гораздо удобнее, чем сравнение файлов Word из почты с версиями V2, V3, V3.1 и V4.3.2.1-финальная.
Единый источник
Я пишу контент один раз, а Sphinx генерирует из него разные форматы. Не нужно отдельно верстать PDF для одного клиента и HTML-портал для другого – всё собирается из одних RST-файлов.
Также я организовал контент в проекте так, что тексты можно переиспользовать в разных разделах документов. Например, с помощью директивы include в файле default-settings.rst я переиспользую тексты из файлов в папке _snippents.

В результате читатель получает такую страницу:

В Sphinx можно настроить условия для сборки разных версий документов из одного источника. Например, для «Бумк» мы получаем разную документацию для Cloud и Enterprise версий:

HTML-шаблоны и темы оформления
Для Sphinx реализовано множество тем оформления.
На проекте «Бумк» я использую лаконичную тему Furo, которую доработал по макетам дизайнера.
Для «Датасан» больше подошла тема PyData.
Каждую тему можно настроить под свои нужды и критерии. Для этого есть встроенные настройки, которые можно задать в конфигурационном файле проекта. Также можно поправить вручную CSS-файлы и шаблоны, написанные на языке Jinja.
Удобная работа с таблицами
Создание и редактирование таблиц в Markdown вызывает боль и страдания. В Sphinx и reStructuredText таблицы можно представить в виде списка:
.. list-table::
:widths: 50, 50
:width: 90 %
:header-rows: 1
* — Выражение jSONPath
— Результат
* — $.store.item[*].name
— Все имена товаров
* — $..brand
— Все бренды
* — $.store.*
— Все товары в магазине
В результате получим таблицу:

А с помощью расширения flat-table ячейки в такой таблице можно объединять:
.. flat-table:: Characteristics of the BLE badge
:header-rows: 1
* — Service
— Characteristic
— Properties
* — :rspan:`2` 0xfee7
— 0xfec7
— WRITE
* — 0xfec8
— INDICATE
* — 0xfec9
— READ

Создание справочников API
Для Sphinx есть расширения, которые парсят YAML-файл API спецификации и генерируют справочники с описанием всех методов. Так можно получить привычный для разработчиков Redoc прямо на сайте документации:

Тестирование документаци
Для локальной проверки документацию можно собрать утилитой sphinx-autobuild и посмотреть, что получилось в браузере. Sphinx будет мониторить изменения в файлах и автоматически пересобирать локальный сайт.
Также при любой сборке Sphinx проверяет все ссылки внутри проекта и подскажет, где нужно исправить ошибки. А для проверки внешних ссылок есть утилита linkcheck:

При переводе документации «Бумк» с русского языка на английский я ориентировался на стайлгайд от Google. Чтобы автоматически проверять, соответствуют ли мои тексты правилам стайлгайда, я добавил в проект линтер Vale. Правила для Google там уже реализованы. Дополнительно я написал несколько правил для проверки текстов на русском языке.
Линтер можно запускать в консоли, но удобнее проверять тексты в VS Code:

Локализация
Утилита sphinx-intl создает специальные PO-файлы для переводов. Текст на исходном языке, в нашем случае русском, делится на абзацы. Выглядит это так:
#: ../../source/ci-integration.rst:16
msgid «»
«Нагрузочное тестирования в |Product| можно автоматизировать с помощью сервисов непрерывной интеграции:«
msgstr «»
«You can automate load testing in |Product| using continuous integration services:«
#: ../../source/ci-integration.rst:18
msgid «:ref:`Jenkins <Example_of_using_Jenkins>`;» msgstr «:ref:`Jenkins <Example_of_using_Jenkins>`»
msgid – оригинальная строка, в msgstr нужно указать перевод. При этом необходимо соблюдать синтаксис reStructuredText.
Теперь при сборке документации достаточно указать язык. Пример команды:
sphinx-build -b dirhtml source build/html/en -d build/doctrees/en/ -t ent
-D language=en
В папке build/html/en будет создан статический сайт на английском языке для Enterprise-версии.
Итоги внедрения
Внедрив Docs-as-Code на проектах «Бумк» и «Датасан», мы получили не только новый формат работы с документацией, но и более управляемый процесс ее разработки и выпуска.
Для обоих продуктов появились единые порталы с пользовательской документацией и справочниками API. Но важнее то, что документация теперь существует не как набор отдельных файлов, а как часть продукта: у нее есть единый источник, история изменений и понятный процесс обновления.
Для «Бумк» мы перевели документацию на английский язык и встроили ее сборку в развертывание самого продукта. Это позволяет выпускать изменения в продукте и документации в рамках одного процесса и снижает риск ситуации, когда новая функциональность уже доступна пользователям, а инструкции к ней еще не обновлены.
Для «Датасан» –– настроили автоматическую генерацию DOCX- и PDF-файлов в фирменном стиле из одного источника. Благодаря этому не нужно вручную поддерживать несколько версий одного и того же документа: изменения вносятся один раз, а затем используются во всех нужных форматах.
С точки зрения бизнеса это дает несколько эффектов.
- Сокращается объем ручной работы с документацией и риск появления противоречащих друг другу версий.
- Проще поддерживать несколько продуктов, редакций и языков.
- Документация быстрее следует за изменениями продукта, а значит, на нее могут надежнее опираться клиенты, поддержка и команды внедрения.
- Наконец, знания меньше зависят от конкретных сотрудников и отдельных файлов, разбросанных по почте, чатам и корпоративным хранилищам.
Отдельно отмечу стоимость решения. Весь стек удалось собрать на базе open source-инструментов, поэтому не потребовались затраты на лицензии и отдельное согласование бюджета. При этом мы сохранили возможность самостоятельно настраивать систему, внешний вид документации и форматы выходных файлов под требования разных продуктов и клиентов.
В результате Docs-as-Code решил для нас не только задачу «как писать документацию», но и более широкую задачу: как сделать работу с корпоративными знаниями воспроизводимой, масштабируемой и встроенной в разработку продукта.
Оцените результаты сами!
Читать документацию «Бумк» для российского рынка.