Ansible в действии. Часть 2
В предыдущей статье мы рассмотрели структуру Ansible и определили последовательность действий при создании и запуске Laravel APP. Также создали экземпляр Ubuntu Lightsail, определили роли, добавили SSH-ключи, установили зависимости. Пришла пора закончить начатое.
Устанавливаем PHP-модули
Чтобы в Ansible вызвать обработчик, надо использовать notify: Restart PHP-FPM, причём имена обработчиков должны быть уникальны.
В нашем руководстве php определён как тег, поэтому, к примеру, если захотите запустить из своего playbook лишь эту задачу, надо будет выполнить её с —tags = ”php”, которая станет исполнять лишь её.
--- - name: Install PHP {{php_version}} PPA Repo apt_repository: repo: 'ppa:ondrej/php' tags: - php ## - name: Install PHP {{php_version}} apt: name=php{{php_version}} state=latest ## - name: Install PHP packages become: true apt: name: "{{ item }}" state: latest with_items: - php{{php_version}}-curl - php{{php_version}}-fpm - php{{php_version}}-intl - php{{php_version}}-mysql - php{{php_version}}-xml - php{{php_version}}-mbstring notify: Restart PHP-FPM tags: - php
Устанавливаем Nginx
- name: Install Nginx web server apt: name: nginx state: latest notify: Restart Nginx tags: - nginx ### - name: Update nginx config files become: true template: src: templates/nginx.conf dest: "/etc/nginx/sites-available/default" tags: - nginx notify: Restart Nginx ### - name: link nginx config become: true file: src: "/etc/nginx/sites-available/default" dest: "/etc/nginx/sites-enabled/default" state: link tags: - nginx notify: Restart Nginx
Добавляем default-конфигурацию Nginx
server { listen 80 default_server; listen [::]:80 default_server ipv6only=on; server_name {{ server_name }}; root {{ app_work_dir }}public; location / { try_files $uri $uri/ /index.php?$args; index index.php index.html index.htm; } if (!-d $request_filename) { rewrite ^/(.*)/$ /$1 permanent; } location =https://cdn.tproger.ru/favicon.ico { access_log off; log_not_found off; } location ~ \.php$ { try_files $uri $uri/ /index.php?$args; index index.php index.html index.htm; fastcgi_pass unix:/var/run/php/php{{php_version}}-fpm.sock; fastcgi_index index.php; fastcgi_param SCRIPT_FILENAME {{app_work_dir}}public$fastcgi_script_name; fastcgi_param APPLICATION_ENV testing; fastcgi_param PATH /usr/bin:/bin:/usr/sbin:/sbin; fastcgi_intercept_errors on; include fastcgi_params; } }
Теперь vars.yml
--- ##@ref https://docs.ansible.com/ansible/latest/user_guide/playbooks_best_practices.html#variables-and-vaults ansible_ssh_user: "ubuntu" current_user: "ubuntu" server_name: "app_name" repo_git_url: "app_github_url" ansible_ssh_private_key_file: "ssh_dir" php_version: 7.2 app_work_dir: /var/www/app_name/ #mysql config mysql_host: "mysql_host" mysql_db: app_name mysql_user: sql_user mysql_pass: sql_pass #other config cache_driver: file session_driver: file app_env: production app_debug: false app_key: "your_app_key" app_name: "app_name" app_url: "your_app_url"
Тут следует отметить, что для шифрования и дешифрования переменных рекомендуется использовать ansible-vault.
Применение Ansible-Vault
Для использования Ansible-Vault нужно создать секретный файл хранилища, в котором будет ключ шифрования, шифрующий ваши переменные.
touch .vault_pass.txt echo 'YOUR_CONFIG_PASS' > .vault_pass.txt
Для того, чтобы зашифровать переменные:
ansible-vault encrypt group_vars/vars.yml --vault-password-file .vault_pass.txt
Для того, чтобы расшифровать:
ansible-vault decrypt group_vars/vars.yml --vault-password-file .vault_pass.txt
Создаём БД MySql, имя пользователя и пароль
- mysql_user: name: "{{mysql_user}}" password: "{{mysql_pass}}" priv: '*.*:ALL' state: present tags: - mysql-db ## - name: Create APP DB database mysql_db: name="{{mysql_db}}" state=present login_user="{{mysql_user}}" login_password="{{mysql_pass}}"
Обратите внимание, что mysql_user и mysql_pass определены внутри vars.yml.
Клонируем кодовую базу
- name: update repo - pull the latest changes git: repo: "{{repo_git_url}}" dest: "{{app_work_dir}}" update: yes version: master accept_hostkey: yes key_file: /home/{{current_user}}/.ssh/id_rsa tags: - code-deploy
Тут app_work_dir и repo_git_url определены внутри vars.yml.
Генерируем .env
Для доступа к переменным и динамических выражений Ansible использует шаблонизатор Jinja2. Создаём файл env.conf:
APP_ENV={{app_env}} APP_DEBUG={{app_debug}} APP_KEY={{app_key}} APP_URL={{app_url}} APP_NAME={{app_name}} DB_HOST={{mysql_host}} DB_DATABASE={{mysql_db}} DB_USERNAME={{mysql_user}} DB_PASSWORD={{mysql_pass}} CACHE_DRIVER={{cache_driver}} SESSION_DRIVER={{session_driver}}
Теперь нужно определить role, дабы переместить данный шаблон в директорию приложения.
--- - name: Copy lara env file become: true template: src: templates/env.conf dest: "{{app_work_dir}}/.env" tags: - env-file
Создаём playbook
--- - hosts: aws #common options between modules sudo: yes gather_facts: no vars_files: - ./group_vars/vars.yml roles: - misc - php - mysql - redis - nginx - bootstrap-app - code-deploy ### handlers: - include: handlers/main.yml
Нами был определён aws как хост для playbook, а sudo yes даёт возможность выполнять команду как sudo-пользователю. Также у нас есть vars_files, где хранятся наши vars. Ещё мы установили roles, а каждая role выполняет конкретную задачу. Кроме того, у нас есть handlers, содержащие все обработчики проекта.
Запускаем playbook
#ansible-playbook playbookName ansible-playbook code-deploy.yml # Запуск с конкретными тегами ansible-playbook playbook.yml --tags="env-files,php" # Если вы используете ansible-valut ansible-playbook code-deploy.yml --vault-password-file .vault_pass.txt
Посмотрим на полную структуру проекта
├── ansible.cfg ├── code-deploy.yml ├── files │ └── dump.sql ├── group_vars │ └── vars.yml ├── handlers │ └── main.yml ├── hosts.ini ├── logs │ └── ansible-log.log ├── roles │ ├── bootstrap-app │ │ └── tasks │ │ └── main.yml │ ├── code-deploy │ │ ├── tasks │ │ │ ├── config-files.yml │ │ │ └── main.yml │ │ └── templates │ │ └── env.conf │ ├── misc │ │ └── tasks │ │ └── main.yml │ ├── mysql │ │ └── tasks │ │ ├── config.yml │ │ └── main.yml │ ├── nginx │ │ ├── tasks │ │ │ └── main.yml │ │ └── templates │ │ └── nginx.conf │ ├── php │ │ └── tasks │ │ └── main.yml │ └── redis │ └── tasks │ └── main.yml ├── scripts │ ├── install_composer.sh │ └── startup.sh └── site.yml
Полезные материалы
Если захотите повторить всё шаг за шагом, вам помогут следующие материалы: • исходный код на GitHub; • запущенный с его помощью сайт; • советы для работы с Ansible playbooks; • Описание Ansible-архитектуры.
Источник — «Ansible In Action».