Ansible Galaxy: готовые роли и коллекции
Урок 17 - не пишем всё с нуля: берём готовые роли и коллекции из Ansible Galaxy.
«Зачем писать роль для PostgreSQL, если её уже написали, протестировали и поддерживают сотни людей?»
Ansible Galaxy - публичный реестр готовых ролей и коллекций. Там есть проверенные временем решения для типовых задач: базы данных, веб-серверы, Docker, мониторинг. Вместо изобретения велосипеда ты подключаешь готовое и настраиваешь под себя переменными.
Роли и коллекции
Различай два типа единиц: роль - то, что мы изучали (одна задача автоматизации). Коллекция - более крупная упаковка: набор модулей, плагинов и ролей под общим пространством имён (например, community.postgresql). FQCN-имена модулей вроде ansible.builtin.apt - это как раз коллекции.
requirements.yml - список зависимостей
Правильный способ управлять внешними ролями и коллекциями - файл requirements.yml с зафиксированными версиями. Тогда вся команда воспроизводит одинаковое окружение.
---
roles:
- name: geerlingguy.postgresql
version: "3.5.2" # пин версии - важно!
collections:
- name: community.docker
version: "3.10.2"
- name: community.general
version: ">=8.0.0,<9.0.0"
# Установить всё из requirements.yml
ansible-galaxy install -r requirements.yml # роли
ansible-galaxy collection install -r requirements.yml # коллекции
Как работает под капотом
Ansible Galaxy CLI читает requirements.yml, для каждой записи скачивает указанную версию из реестра и распаковывает её в локальный каталог ролей/коллекций. Команда ansible-galaxy role install обрабатывает только секцию roles, а collection install - только collections. Пины версий гарантируют, что завтра ты получишь ровно тот же код, что и сегодня - это воспроизводимость.
Смоделируем разбор requirements.yml и применение пинов версий.
# Разбор requirements и проверка пинов версий
requirements = {
"roles": [
{"name": "geerlingguy.postgresql", "version": "3.5.2"},
{"name": "geerlingguy.nginx"}, # без пина - риск!
],
"collections": [
{"name": "community.docker", "version": "3.10.2"},
],
}
for kind in ("roles", "collections"):
for item in requirements[kind]:
ver = item.get("version")
status = f"=={ver}" if ver else "ЛЮБАЯ (не воспроизводимо!)"
print(f"{kind[:-1]}: {item['name']:30} -> {status}")
Попробуй сам ▶ Видно, что роль без версии помечена как невоспроизводимая: завтра выйдет новая версия - и поведение может измениться. Пины версий - основа надёжных деплоев.
Частые ошибки
- Не пинить версии. Без
versionзавтра прилетит новая версия роли и сломает то, что вчера работало. - Путать команды для ролей и коллекций.
role installчитает только секцию roles,collection install- только collections. - Слепо доверять чужой роли. Перед использованием прочитай её код и README, особенно для прод-окружений.
Best practices
- Все внешние зависимости - в
requirements.ymlс пинами версий, под git. - Используй проверенные роли (например, авторов вроде geerlingguy) как основу, настраивая переменными.
- Не смешивай свои роли и внешние в одном каталоге - разнеси, чтобы обновлять внешние независимо.
В реальной работе
Galaxy экономит огромное количество времени, но требует дисциплины. Чужую роль перед использованием в проде читают: что именно она делает, какие права требует, нет ли в ней сомнительных команд. Версии пинят строго - обновление внешней роли проводят осознанно, прогнав тесты, а не автоматически. Многие компании поднимают приватный Galaxy (Automation Hub или pulp), чтобы не зависеть от публичного реестра и хранить там как проверенные внешние роли, так и собственные. А разделение своих и внешних ролей по разным каталогам (через roles_path в конфиге) позволяет обновлять зависимости одной командой, не задевая свой код. Так requirements.yml становится аналогом package.json или requirements.txt - манифестом воспроизводимого окружения.
Итоги
Galaxy экономит время: готовые роли и коллекции подключаются через requirements.yml с пинами версий для воспроизводимости. Различай роли (одна задача) и коллекции (набор модулей/ролей). Дальше - как безопасно хранить секреты в Vault.