У дата-сайентиста множество обязанностей в каждом проекте, но именно подготовку документации он чаще всего оставляет на последний момент. Возможно, вы добросовестно пишете строки документации для классов и функций (молодцы!), но достаточно ли этого?

На мой взгляд, документация не должна зависеть от вашего кода. Ни ваша команда, ни вы сами (а такое тоже возможно) не должны по прошествии некоторого времени продираться сквозь сотни строк кода в модулях Python в отчаянных попытках разобраться, что к чему. А ведь можно создавать прекрасную, стандартизированную документацию в едином стиле, просто применяя строки документации (docstrings) за несколько простых шагов. И проект будет говорить сам за себя.

В этой статье я расскажу о генераторе документации Sphinx, с помощью которого можно автоматически создавать документацию для модулей Python. Кроме того, я буду использовать шаблон проекта Cookiecutter Data Science в Visual Studio Code (VS Code), поскольку он легко интегрируется в Sphinx и имеет стандартизированную структуру директорий. Официальное пособие по использованию Sphinx — отличный ресурс для пользователей, которые хотят углубиться в детали. А моя статья — это краткое руководство по началу работы с этим инструментом. 

Пара слов о строках документации

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

Есть три основных формата docstring: Google, reStructuredText (reST) и NumPy. Все они содержат одну и ту же информацию, различия сводятся только к формату. Здесь можно посмотреть примеры каждого формата docstring.

Я буду использовать формат Google, так как его легко открыть и посмотреть и он занимает меньше места, чем остальные. Этот блок кода — типичный пример docstring в Google:

"""Description of the function, class or method etc.

Args:
    varA (str): Description of varA
    varB (bool): Description of varB

Returns:
    list: Description of returned list

Raises:
    ValueError: Description of raised error
"""

Загрузите autoDocstring — Python Docstring Generator в VS Code, чтобы автоматически генерировать строки документации при вводе трёх двойных кавычек. Создавайте docstring, только когда закончили с функцией, чтобы все вводные данные, результаты и ошибки вошли в генерируемый шаблон docstring.

Приступим к созданию документации.

Для этой статьи я создала модуль Python demo.py, который содержит класс и три базовых функции. Все они, кроме одной функции, снабжены аннотациями в виде docstrings. Именно в этом модуле я и буду создавать документацию для статьи. Вот содержание модуля demo.py:

Содержание модуля demo.py, к которому мы создаём документацию. Снимок состояния сделан с помощью расширения CodeSnap в VS Code
Содержание модуля demo.py, к которому мы создаём документацию. Снимок состояния сделан с помощью расширения CodeSnap в VS Code

1. Настройка

Для начала нужно всё настроить. Установите VS Code и настройте новый проект вместе с Sphinx. Здесь есть два варианта: 

  1. Настроить новый проект с помощью Cookiecutter, где соответствующая настройка Sphinx выполняется в момент создания стандартизированных директорий.

  2. Создать собственную структуру проекта и установить Sphinx отдельно.

Вариант 1: установка Cookiecutter

В терминале выполните pip install Cookiecutter и создайте новый проект:

pip install cookiecutter
cookiecutter https://github.com/drivendata/cookiecutter-data-science

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

Готово, новый проект создан. Фреймворк Sphinx хранится в директории проекта /docs.

Вариант 2: быстрый запуск Sphinx

Если вам не особо нравится шаблон Cookiecutter, создайте структуру проекта с нуля и установите Sphinx. Вполне разумно создать директорию для документации и установить в ней Sphinx. В терминале это выглядит так:

mkdir docs
cd docs

pip install sphinx
sphinx-quickstart

2. Структура папки Sphinx

После установки Sphinx тем или иным способом в директории проекта для документации появится несколько файлов. 

Файл conf.py — это основной файл конфигурации. Именно в него вносят изменения, чтобы отразить особенности документации, — об этом мы подробнее поговорим в следующем разделе.

Файл index.rst — своего рода оглавление документации. Здесь можно подробнее узнать об этом файле.

Файлы getting-started.rst и commands.rst — предлагаемые шаблоны документации. Если они вам не нужны, удалите их. 

Файлы make (make.bat и Makefile) нужны для создания документации. Эти файлы не нужно редактировать. Их вызывают в окне терминала в момент создания документации.

Файлы Sphinx, установленные по умолчанию
Файлы Sphinx, установленные по умолчанию

3. Файл conf.py

Всё самое важное происходит именно в файле конфигурации. Он используется в процессе сборки, так что очень важно настроить его правильно. Последовательность действий при изменении файла conf.py:

  1. Преобразовываем комментарий к строке sys.path обратно в код (строка 20):

#  sys.path.insert(0,  os.path.abspath('.')) 
  1. Меняем путь os.path.abspath к соответствующему месту размещения кода, который нужно задокументировать (от файла conf.py). Допустим, модули Python, документацию для которых нужно создать, находятся в директории проекта src/. Соответственно, я меняю os.path.abspath на место в директории /src, которая находится в родительской папке файла conf.py. Можно указать относительное местоположение с помощью синтаксиса . and /:

sys.path.insert(0,  os.path.abspath('../src'))

"""
# you can use the following syntax to specify relative locations:

'.' # current path of conf.py
'..' # parent path of conf.py
'../..' # parent of the parent path of conf.py
"""
Относительное местоположение директории, в которой содержатся модули Python для папки с документацией. В этом примере нужно составить документацию к модулю demo.py, который находится в директории src/data/
Относительное местоположение директории, в которой содержатся модули Python для папки с документацией. В этом примере нужно составить документацию к модулю demo.py, который находится в директории src/data/
  1. Добавляем необходимые расширения. Вам понадобится добавить к файлу conf.py несколько расширений, чтобы пользоваться дополнительными функциональными возможностями при создании документации. Всё это необязательно, но поперебирать разные расширения можно здесь. Я рекомендую минимум пять расширений:

    • Sphinx.ext.autodoc — использует документацию из docstrings.

    • Autodocsumm — вверху HTML-страницы генерирует таблицу со сводной информацией из всех docstrings, удобен, если у вас много docstrings. Примечание: вам понадобится выполнить pip install autodocsumm в терминале.

    • Sphinx.ext.napoleon — позволяет Sphinx выполнять парсинг строк документации в формате Google.

    • Sphinx.ext.viewcode — добавляет ссылку на HTML-страницу, которая содержит исходный код каждого модуля.

    • Sphinx.ext.coverage — выдаёт сводную информацию о количестве классов или функций, у которых есть docstrings. Если процент таких классов и функций довольно высок, база кода снабжена достаточным объёмом пояснений.

Вот как включить эти расширения в файл conf.py (строка 29):

#  add in the extension names to the empty list variable 'extensions'
extensions = [
      'sphinx.ext.autodoc', 
      'sphinx.ext.napoleon', 
      'autodocsumm', 
      'sphinx.ext.coverage'
]

# add in this line for the autosummary functionality
auto_doc_default_options = {'autosummary': True}
  1. Меняем тему. По умолчанию для создания документации используется довольно лаконичная тема. Но если вдруг вы захотите поэкспериментировать с разными вариантами, для этого нужно заменить значение ‘default’ переменной html_theme (строка 94) на какую-нибудь стандартную тему или тему стороннего разработчика. В этой статье я покажу тему по умолчанию и тему Read the Docs.

html_theme = 'sphinx_rtd_theme' # read the docs theme. This variable is 'default' by default.

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

4. Делаем HTML-страницы

Итак, файл conf.py готов. У вас в коде прекрасные docstrings, мы вот-вот займёмся скрейпингом и создадим HTML-страницы.

Генерируем файлы .rst пакетов Python

Эти файлы — родной формат Sphinx. Именно из них формируют HTML-страницы. Создаём их до HTML-файлов. Для этого выполняем команду sphinx.apidoc, которая использует расширение autodoc для поиска всех модулей Python (например, любых файлов .py) в местоположении sys.path, указанном в файле conf.py. При выполнении команды apidoc можно задавать дополнительные параметры, описанные в документации, но я использовала следующий шаблон:

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

sphinx-apidoc -f -o output_dir module_dir/

-f — принудительная перезапись любых имеющихся сгенерированных файлов.

-o output_dir — директория для размещения выходных файлов. Если её ещё нет, то как раз на этом этапе она будет создана. На забудьте заменить output_dir именем директории на ваше усмотрение. Я указала директорию /docs.

module_dir — местоположение пакетов Python, документацию к которым мы создаём.

После выполнения этой команды в папке docs должны появиться новые .rst-файлы.

Содержимое папки с документацией после выполнения команды sphinx-apidoc для создания файлов .rst
Содержимое папки с документацией после выполнения команды sphinx-apidoc для создания файлов .rst

Обратите внимание, что появилось два новых файла .rst: data.rst и modules.rst. В дополнение к modules.rst для каждой директории, которая содержит по крайней мере один модуль Python, будет создан файл .rst. В моём примере генерируется data.rst, так как я сохранила файл demo.py в директории src/data. 

Если у вас несколько директорий для модулей Python в местоположении, указанном в sys.path в файле conf.py, будет создано несколько файлов .rst. Примечание: эти файлы ещё не содержат извлечённую документацию, в них есть только информация, необходимая autodoc для создания HTML-файлов на следующем этапе.

Редактируем файл index.rst

Помните, что index.rst функционирует как страница с оглавлением, — надо отредактировать этот файл и включить в него все модули Python, для которых нужна документация. 

К счастью, modules.rst ссылается на исходное местоположение всех модулей Python, идентифицированных в sys.path, поэтому можно просто добавить этот файл в index.rst. Для этого откройте файл index.rst и добавьте modules в раздел toctree (дерево содержания). Проверьте, есть ли строка между параметром :maxdepth: и именами файлов .rst.

getting-started и commands уже будут включены в файл index.rst. Их можно удалить из файла, если вы не планируете создавать HTML-страницы. Хотя создать страницу getting-started — не такая уж плохая идея.

Содержание файла index.rst. Я добавила modules, чтобы файл modules.rst использовался в процессе создания HTML
Содержание файла index.rst. Я добавила modules, чтобы файл modules.rst использовался в процессе создания HTML

Создание HTML-файлов

Теперь для сборки HTML-файлов мы можем использовать файлы make в директории с документацией. Эти файлы появятся в директории _build/html/ в папке с документацией. Предварительный просмотр этих файлов доступен в VS Code, если загрузить расширение HTML Preview.

Измените директорию для размещения файла make.bat и выполните следующую команду в терминале cmd:

make html

Если вы работаете в терминале Windows PowerShell, а не cmd, используйте следующий синтаксис:

.\make.bat html

Если при выполнении команды make html возникает предупреждение autodoc: failed to import module, скорее всего, autodoc не удалось найти модули из-за ошибок в конфигурации sys.path в файле conf.py. Убедитесь, что вы верно указали директорию, в которой находятся модули Python.

Редактируем HTML-файлы

Если вы собираетесь редактировать docstrings и вносить изменения в HTML-файлы, запустите команду:

make clean html

Посмотрим на нашу документацию

Напомню, что я оформила документацию для модуля Python demo.py в двух стилях (см. скриншоты ниже). На первом скриншоте — тема по умолчанию, на втором — тема Read the Docs.

Пример созданной в Sphinx HTML-страницы с документацией к модулю Python: тема по умолчанию
Пример созданной в Sphinx HTML-страницы с документацией к модулю Python: тема по умолчанию
Пример созданной в Sphinx HTML-страницы с документацией к модулю Python: тема Read the Docs
Пример созданной в Sphinx HTML-страницы с документацией к модулю Python: тема Read the Docs

Содержание в обоих случаях одинаково, но выглядит документация по-разному. Давайте рассмотрим элементы, из которых состоят оба варианта:

  • панель навигации — слева;

  • сводная информация по всем классам или функциям модуля представлена в таблицах вверху страницы (благодаря расширению autodocsumm);

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

При создании HTML-страниц появится несколько иерархических HTML-страниц. В частности, появится домашняя страница и страницы по каждому пакету и модулю. Просмотрите страницы, изучите их структуру и почитайте официальную документацию, чтобы выяснить, как ещё можно кастомизировать эти страницы.

Например, чтобы в документации можно было просматривать raw code каждой функции, добавьте расширение sphinx.ext.viewcode в файл conf.py. Напротив каждой функции или метода класса появится гиперссылка, при нажатии на которую будет показан raw code. Таким образом можно легко найти код, не углубляясь в базу программного кода.


Готово! Простая красивая документация к модулям Python, для создания которой понадобилось несколько несложных действий в Sphinx. Надеюсь, вам было интересно, а инструмент для автоматического создания документации пригодится вам в ваших проектах. Если у вас есть полезные советы, делитесь ими в комментариях :)

Ближайшие курсы по программированию:

Топ бесплатных курсов и онлайн-встреч:

Комментарии (2)


  1. pvzh
    21.05.2024 17:48

    Чем мне особенно нравится Sphinx – документацию легко можно скопировать для просмотра оффлайн. Например, с помощью HTTrack. Сейчас это актуально со всеми этими шатдаунами и блокировками. При этом даже поиск работать будет! Хотя иногда приходится чуть править HTML, делать адрес страницы поиска относительным.


  1. shsmad
    21.05.2024 17:48

    А еще можно задружить MyST и Sphinx, если кому-то не по душе rst: https://myst-parser.readthedocs.io/en/v0.15.1/sphinx/index.html