Files
dev-conventions/conventions/stack/ansible/app-directories.md
T
av 59a1c23f55 язык: заведён блок ПРИМЕРЫ
- пятая, необязательная часть правила: код парой «плохо → хорошо» после
  обоснования; метка добавлена в словарь (EXAMPLES) и в строку о версии
  языка во всех тринадцати файлах
- сказано, чем примеры не являются: требований в блоке нет, дословным
  сниппетом он не служит, при расхождении с нормой правят пример
- READING.md обновлён по META-30, в машинные проверки добавлен порядок
  блоков, в читательские — что примеры норму не расширяют
2026-07-26 16:09:58 +03:00

8.4 KiB

topic, prefix, extends
topic prefix extends
app-directories ANSD arch/app-directories.md

Категории директорий: реализация в Ansible

Как категории из базового слоя раскладываются на сервере плейбуком.

Ключевые слова ДОЛЖЕН, НЕ ДОЛЖЕН, СЛЕДУЕТ, НЕ СЛЕДУЕТ, ДОПУСКАЕТСЯ и метки ПОЧЕМУ, ПРИМЕРЫ, МЕХАНИЗИРОВАНО и СНЯТО толкуются как описано в языке конвенций версии 1 — тогда и только тогда, когда написаны заглавными.

Область действия

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

Правила

ANSD-1. Каждая директория объявлена переменной *_dir

ДОЛЖЕН. Директория приложения объявляется переменной плейбука внутри base_dir, имя оканчивается на _dir. Для случая «одна директория на категорию» это config_dir, data_dir, cache_dir; когда категория состоит из нескольких директорий, имя даётся по содержимому (media_dir, uploads_dir, dumps_dir).

ПОЧЕМУ. Переменная — единственная ссылка, которую разделяют задача создания директории и список бэкапа (ANSD-4). Литерал пути в одном из этих мест означает, что переименование директории молча разойдётся с бэкапом, и обнаружится это при восстановлении.

ANSD-2. Директории создаются одной задачей циклом по списку

СЛЕДУЕТ. Список директорий в единственной задаче создания.

ПОЧЕМУ. Этот список — единственное место, где декларировано всё, что приложение пишет на диск. Разнесённое по нескольким задачам создание отвечает на вопрос «какие директории есть у приложения» только чтением всего плейбука, а именно этот вопрос задают при заведении бэкапа и при разборе места на диске.

ANSD-3. Владелец директорий — пользователь, от имени которого работает приложение

ДОЛЖЕН. Конкретная модель — выделенный пользователь на приложение (app_owner_uid == app_owner_gid) или общий primary_user — выбирается на репозиторий и фиксируется ниже.

ПОЧЕМУ. Правило про соответствие владельца рантайму, а не про конкретную модель: приложение в контейнере пишет от определённого uid, и если директория принадлежит другому, отказ произойдёт не при деплое, а при первой записи — то есть после того, как плейбук отчитался об успехе. Выбор же модели — свойство репозитория: сервер с одним пользователем и сервер с изоляцией по приложениям решают разные задачи, и навязывать одну модель обоим значит гарантировать вечное отступление.

ANSD-4. Список бэкапа собирается из тех же переменных

ДОЛЖЕН. Плейбук кладёт в base_dir файл backup-targets, строки которого ссылаются на переменные *_dir из ANSD-1, а не на литеральные пути.

ПОЧЕМУ. Правило вывода списка механическое (ANSD-5), но применяет его человек или шаблон — то есть ошибиться можно. Общая переменная делает целый класс ошибок невозможным: переименовал директорию — переименовалось в обоих местах. Независимо набранный список расходится тихо и проявляется в единственный момент, когда это уже неисправимо.

ANSD-5. В список бэкапа идут только данные

ДОЛЖЕН. Директории категории «данные», включая директорию дампов, — в списке; конфигурация и кеш — нет.

ПОЧЕМУ. Реализация правила базовой конвенции. Кеш раздувает снапшот без пользы, а конфигурация содержит отрендеренные секреты — бэкап уезжает в облако, и источником истины для секретов остаётся vault, а не снапшот.

ANSD-6. Конфигурация монтируется только на чтение

СЛЕДУЕТ. В compose конфигурация подключается с :ro.

ПОЧЕМУ. Плейбук — источник истины для конфигурации, и :ro превращает это из договорённости в свойство системы: приложение, которое втихую переписывает свой конфиг, падает сразу, а не расходится с репозиторием незаметно. Приложение, которому запись в конфиг нужна по устройству, монтируется на запись — это отступление, и оно записывается.

ANSD-7. docker-compose.yml лежит в корне base_dir

ДОЛЖЕН. Файл не переносится во вложенную директорию.

ПОЧЕМУ. Туда смотрит project_src модуля docker_compose_v2. Правило внешнее по происхождению, но нарушается легко — при попытке «навести порядок» и убрать compose в config/, где ему по смыслу категорий было бы место.

ANSD-8. Секреты рендерятся в файл конфигурации

СЛЕДУЕТ. Значения приходят из vault-переменных и попадают в файл, принадлежащий пользователю приложения.

ПОЧЕМУ. Файл под 0600 не наследуется дочерними процессами, не виден в docker inspect и не оседает в compose-файле на диске. Это те же три довода, по которым базовая конвенция конфигурации выбирает файл вместо окружения.

ANSD-9. Когда приложение не умеет файловые секреты — environment под no_log

ДОПУСКАЕТСЯ. Задача рендера идёт с no_log: true.

ПОЧЕМУ. Явное разрешение нужно, чтобы ANSD-8 не читался как запрет на деплой такого приложения. Способ вынужденный: секрет попадает в метаданные контейнера и в compose-файл на диске. Приложение, научившееся читать секреты из файла, переводится на ANSD-8 при ближайшем касании.