Автоматизация сборки
TODO В 2025 году лекция занала час. Может, добавить сборку wheel обратно?
Этапы формирования дистрибутива
- Разработка 
- Сборка генератов
 - Тестирование
 
 - Сборка дистрибутива
 - Публикация исходников
 - Публикация дистрибутива
 - Генерат
 - файл, получающийся в процессе сборки дистрибутива
 Целевой генерат: генерат, входящий в дистрибутив
Промежуточный генерат: генерат, не входящий ни в какой дистрибутив
Генераты не хранятся в репозитории, однако некоторые из них (например, документация, скомпилированные переводы и т. п.) используются при публикации.
- Если предполагается, что среда сборки будет неполной, генераты хранить нужно: 
Исходники изображений в проприетарных форматах разработки (типа .psd) ⇒ хранение целевых генератов (.svg/.png)
Для изготовления промежуточного генерата configure требуется Autotools и насколько сопутствующих инструментов (которые в некоторых системах могут даже отсутствовать или не заработать) ⇒ хранение configure
Makefile, который образуется после sphinx-quickstart — не генерат, т. к. нет автоматизированной процедуры его порождения из какого-то исходника. Этим Makefile-ом (а также make.bat) можно не пользоваться вообще, и тогда это просто мусор.
 
 Повторение: .gitignore 
Автоматизация сборки
Как понятие «сборка» стало «оркестрацией»
Интерпретируемые ЯП ⇒ нет понятия сборки
- Малые проекты: всё вручную
 - Большие проекты: всё на CI-сервере 
- Документация
 - Тесты
 - Проверка синтаксиса
 
 
Как следствие: использование инструментов не по назначению:
Tox (автоматизация тестирования)
- Сборку генератов можно представить как test suit-ы
 - Но вообще-то tox не для этого
 
- Git hooks 
- одноуровневая схема «стимул-реакция»
 - бедное окружение Git for windows (хотя и *NIX-like)
 
 - Github actions 
- одноуровневая (?) схема «стимул-реакция»
 - достоинство и оно же недостаток: на машину разработчика даже инструментальные зависимости ставить не надо
 - ⇒ работа превращается в магические пляски над чёрным ящиком
 - некроссплатформенность не имеет (?) значения (модно писать 10050 скриптов для 100500 ОС то на шелле, то на cmd)
 
 
Универсальный инструмент сборки
Классический вариант: рецепты и файловые зависимости
Общий недостаток: цели — далеко не всегда файлы, начинаются 🩼🩼
GNU Make (его даже использует Sphinx).
- off-python зависимости — сам Make, Bash и другие *NIX-like утилиты
 - для Windows некроссплатформенно 
хотя если у вас есть git, то часть *NIX-окружения (включая vim) уже есть, остальное можно поставить разными способами
Например, скачать отсюда) и распаковать
Установить не Git, а Git for windows SDK (там есть pacman)
Использовать всевозможные package manager-ы типа chocolatey или pacman
- … (ни всё это непросто, если честно)
 
 есть almost-make
Он до некоторой степени совместим с Make
- не лучше, а хуже Make — откуда брать *nix утилиты?
 
- Есть сборки в составе пакетов на PyPI
 - Рассчитаны на «стандартные» подходы компилируемых языков (например, в документации по Meson нет ни Sphinx, ни Babel)
 
 Ещё? 
Задача на самом деле сложная: предусмотреть кроссплатформеннные варианты процедуры сборки!
Упрощённый вариант: задания и зависимости между ними
- Общий недостаток: если зависимость заданий не идеальна, часто приходиться «всё стереть и переделать». Например, отсутствуют/устарели какие-то генераты, а про соответствующее задание известно, что оно успешно завершено. и притом совсем недавно.
 Тысячи их! (буквально)
Вариант, рекомендуемый Tox: Invoke
Я увидел такую конструкцию в примере: c.run("rm -rf target")
- та же сказка про белого бычка: off-python / некроссплатформенноть…
 
- …
 
Комбайны: Tox, Poetry, Hatchling, PDM — используются повсеместно, но чуть ли не хуже именно как проекты сборки (синтаксис сложный).
На примере DoIt
- Архитектура: 
Обновление генератов (зависимость на файлы)
- Есть возможность определять, что такое «новое»
 
Составные задания (зависимость на задания)
 - Позволяет запускать задания на языке командной строки
 - Часто используемые примитивы на python
 Синтаксис Python (это и есть программа на Python)
Всякое: встроенные переменные,
Пример: MooTest
Попробуем обвязать doit-автоматизацией MooTest (см. Makefile).
doit — это сборочная зависимость
Пример: GradeProject2021
В нашем случае нуждается в автоматизации:
- Сборка документации
 - Обновление и компиляция переводов
 - Запуск тестов (в т. ч. проверка стиля)
 - Сборка исходного дистрибутива
 - Сборка бинарного дистрибутива (собственно модуля)
 - (в этом проекте отсутствует, но тоже нужно) Публикация: 
- Бинарного дистрибутива
 - Исходного дистрибутива
 - Документации
 
 
Выводы
В целом те же проблемы: шумно из-за python вместо декларативного синтаксиса, внешние команды и т. п.), зато
- Развесистый workflow
 - python-активности, в т. ч. уже готовые (типа того же rm)
 
 Doit хранит метки выполнения заданий и возраст объектов в файле .doit.db 
Этот файл — генерат, его нельзя хранить в репозитории, самое место ему — в .gitignore
Время от времени он портится или перестаёт соответствовать рабочей копии (например, после git reset):
Можно сказать doit forget что-то (или forget all)
- Можно смело удалить этот файл
 
Д/З
Обеспечить в семестровом проекте (предпочтительно с помощью doit):
- Автоматизацию выгонки целевых генератов (документация, перевод, иное)
 Автоматизация git clean -fdx
