Деплой монолита на .NET Framework 4.8 и Oracle с помощью Ansible
Рассказываем, как мы настроили деплой монолитного приложения на Ansible и поделились фишками, статьями и скриптами, которые помогут в работе
2К открытий6К показов
Павел Кузнецов
В статье расскажу, как настроить деплой монолита на Ansible, как перейти с PowerShell и как ускорить развёртывание приложения и базы данных. А ещё поделюсь полезными фишками, статьями и скриптами, которые помогут в работе.
- Почему Ansible, а не PowerShell
- Как настроить деплой приложения
- Как деплоить базу данных Oracle
- Деплой бэкенда и фронтенда приложения
- И пара лайфхаков
Почему Ansible, а не PowerShell
- Один подход написания плейбуков для Windows и Linux-серверов. То есть у нас есть единая среда автоматизации. И если ты умеешь писать под Linux, то сможешь и под Windows.
- Достаточно декларативный язык. Мы указываем, что хотим получить на выходе, и Ansible своим движком выдаёт результат.
- Ansible позволяет хранить всю инвентаризацию серверов и стендов (а только в нашей системе их порядка десяти, плюс различные настройки приложения для разных стендов).
- Огромное количество модулей для работы с различными фреймворками, программным обеспечением и железом.
- Есть полная поддержка Redhat.
Тем, у кого планируется большой объём автоматизации на Ansible или других скриптах и требуется комплексное управление всем этим процессом, стоит посмотреть в сторону opensource проектов AWX или Rundeck.
Как настроить деплой приложения
Подготовить серверы
Сперва открываем сетевые проходы от Linux-агентов в TeamCity до управляемых серверов. Это порты 5985/tcp, 5986/tcp для Windows и 23/tcp в Linux для SSH.
Затем добавляем учётную запись, под которой мы будем подключаться и управлять конечными серверами в локальную группу Администраторы. Включаем службу WinRM — настройки по умолчанию будет достаточно — и аутентификацию CredSSP (другие виды аутентификации либо сложно настроить в компании, либо вовсе нельзя).
После остаётся только подготовить инструменты для работы с самим Ansible. Я использую Git, VS Code и набор плагинов: GitLens, Redhat Ansible, Redhat XML и Prettier — Code formatter.
Создать репозиторий для деплоя
В Bitbucket создаём отдельный репозиторий, где будем хранить всё, что связано с деплоем на Ansible. Это нужно, чтобы отделить скрипты деплоя от репозитория проекта системы, тем самым ограничив права доступа к ним. Доступ должен быть только у DevOps-инженеров и прикладных администраторов. Мало ли кто случайно поправит конфиг-файл для продуктивного сервера — и после деплоя получим неработающее приложение.
Подготовить билд конфигурации в TeamCity для запуска Ansible
Сначала готовим отдельную build configuration (далее — билд), которая собирает Ansible плейбуки для конкретной задачи. Этот билд подключается в build chain общего процесса деплоя, после того как все артефакты прошли проверки ИБ и загружены в хранилище Nexus.
Это позволяет параллельно использовать билд Ansible для разных веток проекта.
Допустим, в проекте требуется создать новый Windows-сервис. Разработчики создают отдельную ветку для этой задачи и разрабатывают сервис. Но нам надо уже готовить деплой для будущего сервиса: установить сервис, настроить файлы конфигурации. Чтобы ничего не ломать в текущем деплое, в Ansible-проекте создаём ветку с аналогичным названием под разработку этой новой фичи и тестируем их параллельно.
После того как сервис будет готов и протестирован вместе с нашим изменённым деплоем, делаем Pull Request в master-ветку Ansible. И получаем master-деплой, уже скорректированный под новый сервис.
Как деплоить базу данных Oracle
- Разработчики готовят изменения в БД в виде SQL-запросов и помещают в changeset Liquibase, которые применяются в процессе обновления.
- Liquibase артефакты проходят проверку синтаксиса и проверку на безопасность, после чего загружаются в Nexus.
- Ansible в виде плейбука запускает процесс применения миграций.
- После обновления БД, Ansible проверяет логи Liquibase, была ли успешной миграция. Если всё хорошо, он переходит к следующей схеме, если нет — выводит сообщение об ошибке.
Liquibase можно запускать напрямую из агентов TeamCity, в виде команды liquibase —changelog-file=master.changelog.xml update-sql, но мы поместили его запуск в Ansible, чтобы весь процесс деплоя был в плейбуке и не хранился в билдах TeamCity.
Зелёным цветом подсвечиваем успешные выполнения задач, а красным то что выполняется с ошибкой.
Иногда миграция БД завершается ошибкой, чаще всего из-за неверных SQL-скриптов. Такие ошибки передаются специалисту, который занимался их разработкой.
Почему Liquibase
В нашем проекте, в БД хранятся не только данные, но логика приложения (да-да, так тоже бывает, когда приложению более 10 лет).
И так как у нас есть множество стендов (Dev/Test/Prod и другие), то нужно контролировать процесс миграции схемы базы данных. Запускать файлы с SQL-скриптами для можно, но процесс требует человеческого контроля. А где человек — там потенциальные ошибки: не доглядел, забыл, не проверил. В итоге через какое то время БД на разных стендах будет отличаться. Поэтому для управления процессом миграции схем мы используем Liquibase. Кроме того, он:
- позволяет хранить все изменения, которые мы вносим в базу данных в виде кода;
- позволяет делать ревью миграции;
- лучше контролирует процесс изменения схемы БД;
- разрешён к использованию внутри компании.
Деплой бэкенда и фронтенда приложения
Ansible из коробки управляет файлами и фаерволом, создаёт сайты и пулы приложений в IIS, настраивает порты, привязывает SSL-сертификаты и многое другое.
Это ускоряет создание деплоя. Мы можем взять пустой сервер с ОС Windows, запустить установку фронтенда или бэкенда и Ansible настроит всё за нас:
проверит папку приложения и SSL-сертификат;
- загрузит файлы приложения из Nexus и скопирует на сервер в нужную папку;
- настроит пул приложений и сайт и привяжет порты и SSL-сертификата;
- настроит XML-файлы конфигурации приложения — об этом подробнее ниже;
- настроит аутентификацию для приложения;
- проверит, что все всё запущено и работает;
- настроит сервис Windows.
На выходе мы получаем готовый бэкенд, фронтенд или интеграционный сервис. Все настройки приложения хранятся в файлах инвентаризаций для стендов. А для каждого сервера есть переопределения имен, путей к папкам, сертификатов, конфигурационных параметров и прочее.
Кстати, мы используем и сокращённую версию деплоя, которая пропускает половину задач: останавливает сервис, обновляет файлы и конфигурацию и запускает сервис в работу. Делается это при выполнения плейбука Ansible с помощью тэгов. Такой подход ускоряет деплой примерно на 30%, используется при разворачивании фич на тестирование.
Отдельное внимание стоит обратить на файлы конфигураций
В .NET Framework 4.8 и ниже конфигурация приложения хранится в XML-файлах web.config или app.config (далее — конфиг-файл). Из-за этого возникают проблемы:
- надо заботиться об информационной безопасности — то есть в файлах конфигураций не должно быть паролей, токенов и всего что запрещено регламентами ИБ;
- при автоматизации деплоя, нужно оставить возможность откатиться на предыдущую версию;
- кто-то из сотрудников может случайно изменить конфигурацию при коммите; и приложение может перестать работать
- сложно динамически переопределить некоторые параметры конфигурации для стендов.
В .NET версий, 5.0 и выше всё чуть проще: можно хранить конфиги внутри проекта с переопределением для конкретных стендов, а также использовать app secrets и dotnet_environment. В другом проекте, мы уже используем именной такой подход.
Есть два варианта решения.
Использовать механизм трансформации конфиг-файлов msbuild
Мы делаем несколько конфиг-файлов под разные стенды или серверы. И в момент сборки, указываем в Configuration Manager, для какой среды собираем проект: Test, Dev или Prod. Затем msbuild через схему XDT меняет конфиг и помещает его в папку с остальными артефактами приложения
У такого подхода есть несколько минусов:
- все настройки и схема изменения хранятся внутри проекта;
- конфиг собирается в момент сборки, хранится в артефактах приложения и уже в готовом виде попадает на стенд в процессе деплоя;
- изменениями конфиг-файлов занимаются разработчики;
- хранение паролей в открытом виде в Git и артефактах.
Да, есть механизм шифрования секций конфигурационных файлов. Но он не снимает проблемы с хранением в Git — и достаточно сложный в эксплуатации. Лучше доработать приложение, чтобы оно взаимодействовало с ПО HashiCorp Vault или Cyberark.
Шаблонизировать конфиг-файлы в Ansible
В Git по умолчанию хранится конфигурационный файл с базовыми настройками. Так, разработчикам удобнее работать на локальных машинах.
В Ansible хранится файл вида app.config.xdt.j2, в котором хранится шаблонизированная схема XDT для модификации эталонного файла. Звучит странно, но это самый гибкий, безопасный и удобный в эксплуатации способ.
Первичные затраты времени на подготовку таких xdt.j2-файлов, сводятся к сравнению эталонного конфиг-файла с тем что есть на стенде. С этим помогает утилита FatAntelope, которая сравнивает файлы и готовит XDT-схему для модификации. Схему мы помещаем в Jinja-файл и шаблонизируем конкретные параметры.
То есть в процессе деплоя приложения мы делаем следующее:
- формируем схему: xdt.j2 -> XDT-схема;
- применяем её к эталонному конфигу: Git config + XDTсхема
- gолучаем .config-файл для стенда
Минусы:
- тратится время на модификацию xdt.j2-файлов
И пара лайфхаков
Ускоряем Ansible
Когда мы использовали PowerShell для деплоя приложения, запуск скрипта и обновление файлов занимали 20–30 секунд. Но плейбуки на Ansible занимали по 1–2 минуты. Мы начали искать способы ускорить работу.
Сперва оптимизировали запуск самого PowerShell. В чём суть? Библиотеки, связанные с PowerShell, лежат не в машинных кодах, а выполняют JIT-компиляцию каждый раз в момент запуска PowerShell. Это тормозит запуск любого скрипта Ansible.
Чтобы такого не было, достаточно выполнить скрипт, который предлагают сами разработчики Ansible, один раз на всех серверах.
Так, выполнение плейбуков на Windows ускорится на 20–30%.
Затем мы выяснили, что в Ansible начиная с версии 2.7 добавлена поддержка протокола PSRP. Это ускоряет работу плейбуков ещё на 30%. Из минусов — протокол не так просто включить в нашем случае, так как нужно скачать несколько пакетов и установить их на агентах в TeamCity, где используется Ansible. Для большинства же, всё просто: pip install pypsrp.
Третий способ — установить OpenSSH 8-й версии на Windows Server и подключаться к нему по SSН-протоколу, а не WinRM. Это тоже ускорит работу, но фактические замеры мы не делали.
Добавляем статистику
В Teamcity логи Ansible красиво подсвечены, и в конце есть статистика скорости выполнения плейбука и конкретных задач. Это включается добавлением в корень проект деплоя Ansbile конфига anisible.cfg.
Линтинг скриптов Ansible
Мы достаточно много времени тратим на разработку деплоя. И хорошо бы перед его запуском проверять общее качество кода, синтаксические ошибки. Для этого используйте линтер Anisble, который установлен на агентах TeamCity.
Нужно установить триггер в TeamCity на появление нового коммита или Pull Request в проекте деплоя. И после автоматом проверяете код на потенциальные ошибки.
Тестируем деплой
Обычно стенды Dev/Test/Prod отличаются друг от друга. На Dev стенде всё устанавливается на одном сервере, а в продуктиве всё разнесено по разным серверам и используется балансировка.
Мы часто меняем и рефакторим деплой приложений. И чтобы быть уверенными, что на всех стендах от отработает корректно, необходимо тестировать его после каждого изменения.
Самое простое — запускать его на стенды. Но если это не получается сделать, например, они все заняты тестировщиками и разработчиками, можно добавить параметр —check во время запуска плейбука. Тогда плейбук отработает всю логику, но без фактического применения на сервере, и вы убедитесь, что всё работает корректно. Для удобства можно сделать кнопку «Тестовый запуск».
Важно! Не все модули корректно работают в режиме –check. Если вы сначала загружаете файл артефакта, а потом распаковываете его, даже при тестовом запуске он будет реально искать файл для распаковки. А не найдя его выдаст ошибку. Решается это с помощью параметра check_mode: no.
На этом всё, если будут вопросы пишите. А если что-то заинтересует, расскажем подробнее.
2К открытий6К показов