presentations/source/deploying-drupal-ansible-ansistrano/slides.md

949 lines
20 KiB
Markdown
Raw Normal View History

2019-02-05 01:27:13 +00:00
autoscale: true
build-lists: true
2019-11-12 08:01:38 +00:00
code: line-height(1.2)
2019-02-05 01:27:13 +00:00
header-emphasis: #53B0EB
text: alignment(left)
2020-01-30 22:26:34 +00:00
theme: simple, 8
2019-02-05 01:27:13 +00:00
2019-11-12 08:01:38 +00:00
# [fit] **Deploying PHP applications** <br>using Ansible, Ansible Vault <br>and Ansistrano
2019-02-05 01:27:13 +00:00
2020-01-30 22:26:34 +00:00
^ I work primarily with PHP, and there will be some PHP-isms in this talk (LAMP stack, Composer).
Will be using a Drupal 8 application as the example, but the tools are tool and language agnostic.
---
# [fit] **Deploying ~~PHP~~ applications** <br>using Ansible, Ansible Vault <br>and Ansistrano
---
## **What we'll be looking at**
* **Ansible** crash course
* Keeping secrets with **Ansible Vault**
* Deployments with **Ansistrano**
2019-02-05 01:27:13 +00:00
---
[.build-lists: false]
[.header: #111111]
2019-11-12 08:01:38 +00:00
![right 500%](../images/me-phpnw-inviqa.jpg)
2019-02-05 01:27:13 +00:00
2020-01-30 22:26:34 +00:00
- Full Stack Software Developer & System Administrator
2019-11-12 08:01:38 +00:00
- **Senior Software Engineer** at **Inviqa**
2020-01-30 22:26:34 +00:00
- Acquia certified **Drupal 8 Grand Master** and **Cloud Pro**
2019-11-12 08:01:38 +00:00
- Open sourcer
- Drupal 7 & 8 **core contributor**
2019-02-05 01:27:13 +00:00
- @opdavies
- www.oliverdavies.uk
2020-01-30 22:26:34 +00:00
^ Maintain Drupal modules, PHP CLI tools and libraries, Ansible roles
2019-02-05 01:27:13 +00:00
Blog on my website
2020-01-30 22:26:34 +00:00
I work primarily with Drupal and Symfony
I work for Inviqa, but this based on my personal and side projects.
I've been using Ansible for a number of years, initially only for provisioning and setting up my laptop, and later for application deployments
2019-02-05 01:27:13 +00:00
---
2019-11-12 08:01:38 +00:00
![350% inline](images/logo-platformsh.png)
![150% inline](images/logo-acquia.png)
![130% inline](images/logo-pantheon.png)
2019-02-05 01:27:13 +00:00
2019-11-12 08:01:38 +00:00
^ Large, well-known managed hosting companies
Optimised servers for PHP/Drupal applications
Include some sort of deployment system
2020-01-30 22:26:34 +00:00
This workflow doesn't apply to this scenario
2019-02-05 01:27:13 +00:00
---
2019-11-12 08:01:38 +00:00
![100%](images/logo-digital-ocean.png)
![30%](images/logo-linode.png)
2020-01-30 22:26:34 +00:00
![30%](images/logo-vultr.png)
2019-02-05 01:27:13 +00:00
2019-11-12 08:01:38 +00:00
^ More applicable to virtual or dedicated servers with no existing deployment process
Not enough budget for fully-managed, or using internal infrastructure
2020-01-30 22:26:34 +00:00
This is where the this workflow would be useful
2019-02-05 01:27:13 +00:00
---
2019-11-12 08:01:38 +00:00
# **What is Ansible?**
2019-02-05 01:27:13 +00:00
---
2020-01-30 22:26:34 +00:00
## Ansible is an open-source **software provisioning, configuration management, and application-deployment** tool.
2019-02-05 01:27:13 +00:00
2019-11-12 08:01:38 +00:00
![10% right](images/ansible.png)
2019-02-05 01:27:13 +00:00
2020-01-30 22:26:34 +00:00
[.footer: https://en.wikipedia.org/wiki/Ansible_(software)]
2019-02-05 01:27:13 +00:00
---
![10% right](images/ansible.png)
2019-11-12 08:01:38 +00:00
### **What is Ansible?**
2019-02-05 01:27:13 +00:00
2019-11-12 08:01:38 +00:00
* CLI tool
* Written in Python
* Configured with YAML
2020-01-30 22:26:34 +00:00
* Executes ad-hoc remote commands
2019-02-05 01:27:13 +00:00
* Installs software packages
* Performs deployment steps
2019-11-12 08:01:38 +00:00
* Batteries included
2019-02-05 01:27:13 +00:00
2019-11-12 08:01:38 +00:00
^ Written in Python but you don't need to write or know Python to use it
2020-01-30 22:26:34 +00:00
Drupal, Symfony and a lot of other projects use YAML
First-party modules (SSH keys, file and directory management, package repositories, stopping/starting/restarting services, DO/Linode/AWS integration)
2019-02-05 01:27:13 +00:00
2019-11-12 08:01:38 +00:00
---
2019-02-05 01:27:13 +00:00
![10% right](images/ansible.png)
2019-11-12 08:01:38 +00:00
### **What is Ansible?**
2019-02-05 01:27:13 +00:00
2019-11-12 08:01:38 +00:00
* Hosts/Inventories
2019-02-05 01:27:13 +00:00
* Commands
* Playbooks
* Tasks
* Roles
2020-01-30 22:26:34 +00:00
^ Hosts: where your managed nodes/hosts are. Can be static or dynamic.
Commands: run from a control node onto managed nodes
Playbooks and Tasks: YAML representation of a series of commands/steps
2019-02-05 01:27:13 +00:00
---
![10% right](images/ansible.png)
2019-11-12 08:01:38 +00:00
### **Why Ansible?**
2019-02-05 01:27:13 +00:00
* Familiar syntax
* Easily readable
* No server dependencies
* Easy to add to an existing project
* Includes relevant modules (e.g. Composer)
2020-01-30 22:26:34 +00:00
* Idempotency
2019-02-05 01:27:13 +00:00
2019-11-12 08:01:38 +00:00
^ Drupal 8, Symfony, Ansible all use YAML
Runs on any server with Python
Plugins into Drupal via CLI apps like Drush and Drupal Console
2020-01-30 22:26:34 +00:00
Changes are only made when needed (once)
2019-11-12 08:01:38 +00:00
2019-02-05 01:27:13 +00:00
---
2019-11-12 08:01:38 +00:00
# **Hosts / Inventories**
2019-02-05 01:27:13 +00:00
---
```ini
# hosts.ini
2019-11-12 08:01:38 +00:00
[webservers]
2019-02-05 01:27:13 +00:00
192.168.33.10
```
2020-01-30 22:26:34 +00:00
^ Supports wildcards and ranges.
2019-02-05 01:27:13 +00:00
---
2019-11-12 08:01:38 +00:00
```yaml
# hosts.yml
webservers:
hosts:
192.168.33.10:
```
2019-02-05 01:27:13 +00:00
---
2019-11-12 08:01:38 +00:00
# **Commands**
---
2020-01-30 22:26:34 +00:00
# `ansible all -i hosts.yml -m ping`
2019-11-12 08:01:38 +00:00
---
2019-02-05 01:27:13 +00:00
2020-01-30 22:26:34 +00:00
```json
2019-11-12 08:01:38 +00:00
webservers | SUCCESS => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": false,
"ping": "pong"
}
2019-02-05 01:27:13 +00:00
```
---
2020-01-30 22:26:34 +00:00
# `ansible all `<br>`-i hosts.yml `<br>`-m command `<br>`-a 'git pull `<br>`--chdir=/app'`
2019-11-12 08:01:38 +00:00
---
2020-01-30 22:26:34 +00:00
# `ansible all -i hosts.yml`<br>`-m git -a 'repo=https://github.com/opdavies/dransible dest=/app`'
2019-11-12 08:01:38 +00:00
---
# **Tasks and Playbooks**
2019-02-05 01:27:13 +00:00
---
```yaml
# playbook.yml
---
2020-01-30 22:26:34 +00:00
- hosts: webservers # or 'all'
2019-02-05 01:27:13 +00:00
2019-11-12 08:01:38 +00:00
vars:
git_repo: https://github.com/opdavies/dransible
2019-02-05 01:27:13 +00:00
tasks:
- name: Update the code
2019-11-12 08:01:38 +00:00
git:
repo: '{{ git_repo }}'
dest: /app
version: master
update: true
2019-02-05 01:27:13 +00:00
```
---
2020-01-30 22:26:34 +00:00
# `ansible-playbook `<br>`playbook.yml -i hosts.yml`
2019-02-05 01:27:13 +00:00
---
2020-01-30 22:26:34 +00:00
# **Roles: <br>configuring a LAMP stack**
2019-02-05 01:27:13 +00:00
^ Collections of tasks, variables and handlers
---
```yaml
# requirements.yml
---
- src: geerlingguy.apache
- src: geerlingguy.composer
- src: geerlingguy.mysql
- src: geerlingguy.php
- src: geerlingguy.php-mysql
```
2019-11-12 08:01:38 +00:00
^ Provisioning LAMP stack and Composer
2019-02-05 01:27:13 +00:00
---
2020-01-30 22:26:34 +00:00
# `ansible-galaxy -r`<br>`requirements.yml install`
2019-02-05 01:27:13 +00:00
---
```yaml
2020-01-30 22:26:34 +00:00
# provision.yml
2019-02-05 01:27:13 +00:00
---
2020-01-30 22:26:34 +00:00
- hosts: webservers
2019-02-05 01:27:13 +00:00
roles:
- geerlingguy.apache
- geerlingguy.mysql
- geerlingguy.php
- geerlingguy.php-mysql
- geerlingguy.composer
```
^ Role order matters!
---
```yaml
2020-01-30 22:26:34 +00:00
# provision.yml
---
- hosts: webservers
# ...
2019-02-05 01:27:13 +00:00
2020-01-30 22:26:34 +00:00
vars:
apache_vhosts:
- servername: dransible.wip
documentroot: /app/web
2019-02-05 01:27:13 +00:00
```
---
2020-01-30 22:26:34 +00:00
```yaml
# provision.yml
---
- hosts: webservers
# ...
vars:
# ...
php_version: '7.4'
php_packages_extra:
- libapache2-mod-php{{ php_version }}
- libpcre3-dev
```
2019-11-12 08:01:38 +00:00
---
2019-02-05 01:27:13 +00:00
```yaml
2020-01-30 22:26:34 +00:00
# provision.yml
---
- hosts: webservers
# ...
2019-02-05 01:27:13 +00:00
2020-01-30 22:26:34 +00:00
vars:
# ...
mysql_databases:
- name: main
2019-02-05 01:27:13 +00:00
2020-01-30 22:26:34 +00:00
mysql_users:
- name: user
password: secret
priv: main.*:ALL
```
2019-02-05 01:27:13 +00:00
2020-01-30 22:26:34 +00:00
---
# `ansible-playbook provision.yml -i hosts.yml`
---
```
PLAY [Provision the webserver machines] ********************************************************************************
TASK [Gathering Facts] *************************************************************************************************
ok: [webservers]
TASK [geerlingguy.apache : Include OS-specific variables.] *************************************************************
ok: [webservers]
TASK [geerlingguy.apache : Include variables for Amazon Linux.]
skipping: [webservers]
TASK [geerlingguy.apache : Define apache_packages.] ********************************************************************
ok: [webservers]
TASK [geerlingguy.apache : include_tasks] ******************************************************************************
included: /Users/opdavies/.ansible/roles/geerlingguy.apache/tasks/setup-Debian.yml for webservers
TASK [geerlingguy.apache : Update apt cache.] **************************************************************************
changed: [webservers]
2019-02-05 01:27:13 +00:00
```
---
2020-01-30 22:26:34 +00:00
```
TASK [geerlingguy.composer : Ensure composer directory exists.] ********************************************************
ok: [webservers]
2019-02-05 01:27:13 +00:00
2020-01-30 22:26:34 +00:00
TASK [geerlingguy.composer : include_tasks] ****************************************************************************
skipping: [webservers]
TASK [geerlingguy.composer : include_tasks] ****************************************************************************
skipping: [webservers]
RUNNING HANDLER [geerlingguy.apache : restart apache] ******************************************************************
changed: [webservers]
RUNNING HANDLER [geerlingguy.mysql : restart mysql] ********************************************************************
changed: [webservers]
RUNNING HANDLER [geerlingguy.php : restart webserver] ******************************************************************
changed: [webservers]
RUNNING HANDLER [geerlingguy.php : restart php-fpm] ********************************************************************
skipping: [webservers]
PLAY RECAP *************************************************************************************************************
webservers : ok=111 changed=32 unreachable=0 failed=0 skipped=78 rescued=0 ignored=0
```
2019-02-05 01:27:13 +00:00
---
2020-01-30 22:26:34 +00:00
![70%](images/after-provision-1.png)
2019-02-05 01:27:13 +00:00
---
2020-01-30 22:26:34 +00:00
![70%](images/after-provision-2.png)
---
# **Keeping secrets with <br>Ansible Vault**
---
```yaml
# provision.yml
---
- hosts: webservers
# ...
vars:
# ...
mysql_databases:
- name: main
mysql_users:
- name: user
password: secret
priv: main.*:ALL
```
2019-02-05 01:27:13 +00:00
---
2020-01-30 22:26:34 +00:00
[.code-highlight: 11-14]
2019-02-05 01:27:13 +00:00
```yaml
2020-01-30 22:26:34 +00:00
# provision.yml
---
- hosts: webservers
# ...
vars:
# ...
mysql_databases:
- name: main
mysql_users:
- name: user
password: secret
priv: main.*:ALL
```
---
# `ansible-vault create` <br>`vault.yml`
2019-02-05 01:27:13 +00:00
---
2020-01-30 22:26:34 +00:00
```yaml
# vars/vault.yml
---
vault_database_name: main
vault_database_user: user
2019-11-12 08:01:38 +00:00
vault_database_password: secret
2019-02-05 01:27:13 +00:00
```
^ Optional, but easier to see where variables are set
---
2019-11-12 08:01:38 +00:00
```
$ANSIBLE_VAULT;1.1;AES256
36656233323539616336393838396137343939623233393338666530313
73037323366326363306531336333353163643063663335396139363762
39383133330a35636566623262353733373066363837393264616134613
16366376266646437373366373738303931616333626332353839353332
32663432346662613438330a38643539343232376138613733373636343
63864666430313866623539333039363138646331326565386263386666
35306264396230633939346532356665306564626431353936643135376
23834346635366637613235656165643361316663396530383263333064
33326264316235396431666262346637366563376330363238373331373
43533386165366531626462643662666266316639306262666539373236
343662313265376261316636623963353933613366353737363435
```
---
2019-02-05 01:27:13 +00:00
```yaml
2020-01-30 22:26:34 +00:00
# vars/vars.yml
2019-02-05 01:27:13 +00:00
---
2019-11-12 08:01:38 +00:00
database_name: "{{ vault_database_name }}"
database_user: "{{ vault_database_user }}"
database_password: "{{ vault_database_password }}"
2019-02-05 01:27:13 +00:00
```
---
```yaml
2020-01-30 22:26:34 +00:00
# provision.yml
---
mysql_databases:
- '{{ database_name }}'
2019-02-05 01:27:13 +00:00
2020-01-30 22:26:34 +00:00
mysql_users:
- name: '{{ database_user }}'
password: '{{ database_password }}'
priv: '{{ database_name }}.*:ALL'
2019-02-05 01:27:13 +00:00
```
---
2020-01-30 22:26:34 +00:00
# `ansible-vault edit vault.yml`
---
# `ansible-playbook` <br>`-i hosts.yml` <br>`deploy.yml`<br>`--ask-vault-pass`
---
# **Basic deployment**
---
```yaml
# deploy.yml
tasks:
- name: Creating project directory
file:
path: /app
state: directory
- name: Uploading application
synchronize:
src: "{{ playbook_dir }}/../"
dest: /app
- name: Installing Composer dependencies
composer:
command: install
working_dir: /app
```
2019-02-05 01:27:13 +00:00
---
2020-01-30 22:26:34 +00:00
# Disadvantages
* Single point of failure
* No ability to roll back
* Sensitive data stored in plain text
2019-02-05 01:27:13 +00:00
---
2019-11-12 08:01:38 +00:00
# **Better deployments**
2019-02-05 01:27:13 +00:00
---
2019-11-12 08:01:38 +00:00
![full inline](images/ansistrano.png)
2019-02-05 01:27:13 +00:00
2019-11-12 08:01:38 +00:00
^ Just another role, specifically for deployments
Ansible port of Capistrano
2019-02-05 01:27:13 +00:00
---
# Features
* Multiple release directories
* Shared paths and files
* Customisable
* Multiple deployment strategies
* Multi-stage environments
* Prune old releases
* Rollbacks
^ rsync, Git, SVN etc
---
```yaml
2020-01-30 22:26:34 +00:00
# requirements.yml
2019-02-05 01:27:13 +00:00
---
2020-01-30 22:26:34 +00:00
# ...
2019-02-05 01:27:13 +00:00
- ansistrano.deploy
- ansistrano.rollback
```
---
```yaml
2020-01-30 22:26:34 +00:00
# deploy.yml
2019-02-05 01:27:13 +00:00
---
- hosts: all
roles:
- ansistrano.deploy
```
---
```yaml
2020-01-30 22:26:34 +00:00
# deploy.yml
2019-02-05 01:27:13 +00:00
---
2020-01-30 22:26:34 +00:00
# ...
2019-02-05 01:27:13 +00:00
vars:
2020-01-30 22:26:34 +00:00
project_deploy_dir: /app
2019-11-12 08:01:38 +00:00
ansistrano_deploy_to: '{{ project_deploy_dir }}'
2019-02-05 01:27:13 +00:00
ansistrano_deploy_via: git
ansistrano_git_branch: master
2019-11-12 08:01:38 +00:00
ansistrano_git_repo: 'git@github.com:opdavies/dransible'
```
---
2020-01-30 22:26:34 +00:00
# `ansible-playbook` <br>`-i hosts.yml` <br>`deploy.yml`
---
```
PLAY [webservers] ******************************************************************************************************
TASK [Gathering Facts] *************************************************************************************************
ok: [webservers]
TASK [ansistrano.deploy : include_tasks] *******************************************************************************
TASK [ansistrano.deploy : include_tasks] *******************************************************************************
included: /Users/opdavies/.ansible/roles/ansistrano.deploy/tasks/setup.yml for webservers
TASK [ansistrano.deploy : ANSISTRANO | Ensure deployment base path exists] *********************************************
ok: [webservers]
TASK [ansistrano.deploy : ANSISTRANO | Ensure releases folder exists] **************************************************
ok: [webservers]
TASK [ansistrano.deploy : ANSISTRANO | Ensure shared elements folder exists] *******************************************
ok: [webservers]
TASK [ansistrano.deploy : ANSISTRANO | Ensure shared paths exists] *****************************************************
ok: [webservers] => (item=web/sites/default/files)
```
---
```
TASK [ansistrano.deploy : Update file permissions] *********************************************************************
changed: [webservers]
TASK [ansistrano.deploy : include_tasks] *******************************************************************************
TASK [ansistrano.deploy : include_tasks] *******************************************************************************
included: /Users/opdavies/.ansible/roles/ansistrano.deploy/tasks/cleanup.yml for webservers
TASK [ansistrano.deploy : ANSISTRANO | Clean up releases] **************************************************************
changed: [webservers]
TASK [ansistrano.deploy : include_tasks] *******************************************************************************
TASK [ansistrano.deploy : include_tasks] *******************************************************************************
included: /Users/opdavies/.ansible/roles/ansistrano.deploy/tasks/anon-stats.yml for webservers
TASK [ansistrano.deploy : ANSISTRANO | Send anonymous stats] ***********************************************************
skipping: [webservers]
PLAY RECAP *************************************************************************************************************
webservers : ok=33 changed=14 unreachable=0 failed=0 skipped=7 rescued=0 ignored=0
```
2019-11-12 08:01:38 +00:00
---
```bash
vagrant@dransible:/app$ ls -l
total 8
lrwxrwxrwx 1 26 Jul 19 00:15 current -> ./releases/20190719001241Z
drwxr-xr-x 5 4096 Jul 22 20:30 releases
drwxr-xr-x 4 4096 Jul 19 00:00 shared
```
---
```
vagrant@dransible:/app/releases$ ls -l
total 20
drwxr-xr-x 5 4096 Jul 22 20:30 .
drwxr-xr-x 4 4096 Jul 19 00:15 ..
drwxr-xr-x 10 4096 Jul 19 00:02 20190719000013Z
drwxr-xr-x 10 4096 Jul 19 00:14 20190719001241Z
drwxr-xr-x 9 4096 Jul 22 20:30 20190722203038Z
2019-02-05 01:27:13 +00:00
```
---
2020-01-30 22:26:34 +00:00
# `ansible-playbook` <br>`-i hosts.yml` <br>`rollback.yml`
---
2019-02-05 01:27:13 +00:00
2020-01-30 22:26:34 +00:00
```yaml
# rollback.yml
2019-02-05 01:27:13 +00:00
---
- hosts: all
roles:
- ansistrano.rollback
vars:
2019-11-12 08:01:38 +00:00
ansistrano_deploy_to: '{{ project_deploy_dir }}'
2019-02-05 01:27:13 +00:00
```
---
2019-11-12 08:01:38 +00:00
# **Customising Ansistrano: <br>Build Hooks**
---
2019-02-05 01:27:13 +00:00
2019-11-12 08:01:38 +00:00
![inline 140%](images/ansistrano-flow.png)
^ Shared = files directory, logs
Before/after symlink shared = run tests
Symlink = 'current' symlink, site is live
Clean up = remove node_modules, database export, sqlite testing DB
2019-02-05 01:27:13 +00:00
---
```yaml
2020-01-30 22:26:34 +00:00
# deploy.yml
---
# ...
2019-02-05 01:27:13 +00:00
2020-01-30 22:26:34 +00:00
ansistrano_after_symlink_shared_tasks_file: '{{ playbook_dir }}/deploy/after-symlink-shared.yml'
ansistrano_after_symlink_tasks_file: '{{ playbook_dir }}/deploy/after-symlink.yml'
ansistrano_after_update_code_tasks_file: '{{ playbook_dir }}/deploy/after-update-code.yml'
2019-02-05 01:27:13 +00:00
2020-01-30 22:26:34 +00:00
release_web_path: '{{ ansistrano_release_path.stdout }}/web'
release_drush_path: '{{ ansistrano_release_path.stdout }}/vendor/bin/drush'
2019-02-05 01:27:13 +00:00
```
2020-01-30 22:26:34 +00:00
^ Each step has a 'before' and 'after' step
Ansistrano allows us to add more things by providing a path to a playbook and adding additional steps.
2019-02-05 01:27:13 +00:00
---
```yaml
2020-01-30 22:26:34 +00:00
# deploy/after-update-code.yml
2019-02-05 01:27:13 +00:00
---
2019-02-05 01:35:18 +00:00
- name: Install Composer dependencies
composer:
command: install
working_dir: '{{ ansistrano_release_path.stdout }}'
2019-02-05 01:27:13 +00:00
```
---
```yaml
2020-01-30 22:26:34 +00:00
# deploy/after-symlink-shared.yml
2019-02-05 01:27:13 +00:00
---
2019-02-05 01:35:18 +00:00
- name: Run database updates
command: '{{ release_drush_path }} --root {{ release_web_path }} updatedb'
2019-02-05 01:27:13 +00:00
```
---
```yaml
2020-01-30 22:26:34 +00:00
# deploy/after-symlink.yml
2019-02-05 01:27:13 +00:00
---
- name: Clear Drupal cache
command: '{{ release_drush_path }} --root {{ release_web_path }} cache-rebuild'
```
---
2019-11-12 08:01:38 +00:00
![80%](images/drupalcon/site.png)
---
# **Managing data <br>across deployments**
---
```yaml
2020-01-30 22:26:34 +00:00
# deploy.yml
2019-11-12 08:01:38 +00:00
vars:
# ...
ansistrano_shared_paths:
- "{{ drupal_root }}/sites/default/files"
```
---
```
vagrant@dransible:/app/shared/web/sites/default/files$ ls -la
total 28
drwxrwxrwx 6 4096 Jul 19 00:18 .
drwxr-xr-x 3 4096 Jul 19 00:00 ..
drwxrwxr-x 2 4096 Jul 22 21:24 css
-rwxrwxrwx 1 487 Jul 19 00:02 .htaccess
drwxrwxr-x 2 4096 Jul 19 00:19 js
drwxrwxrwx 3 4096 Jul 19 00:18 php
drwxrwxrwx 2 4096 Jul 19 00:03 styles
```
---
2019-02-05 01:27:13 +00:00
2019-11-12 08:01:38 +00:00
```
vagrant@dransible:/app/current/web/sites/default$ ls -la
total 48
dr-xr-xr-x 2 4096 Jul 19 00:14 .
drwxr-xr-x 3 4096 Jan 22 17:30 ..
-rw-r--r-- 1 6762 Jul 19 00:14 default.services.yml
-rw-r--r-- 1 31342 Jul 19 00:14 default.settings.php
lrwxrwxrwx 1 45 Jul 19 00:14 files -> ../../../../../shared/web/sites/default/files
2020-01-30 22:26:34 +00:00
-rw-r--r-- 1 35 Jul 19 00:12 settings.php
2019-11-12 08:01:38 +00:00
```
---
2020-01-30 22:26:34 +00:00
# **Generating settings <br>files per deployment**
2019-11-12 08:01:38 +00:00
---
```yaml
2020-01-30 22:26:34 +00:00
# vars/vault.yml
2019-11-12 08:01:38 +00:00
---
2020-01-30 22:26:34 +00:00
vault_database_name: main
vault_database_user: user
vault_database_password: secret
2019-11-12 08:01:38 +00:00
vault_hash_salt: dfgiy$fd2!34gsf2*34g74
```
---
```yaml
2020-01-30 22:26:34 +00:00
# vars/vars.yml
2019-11-12 08:01:38 +00:00
---
database_name: "{{ vault_database_name }}"
database_password: "{{ vault_database_password }}"
database_user: "{{ vault_database_user }}"
hash_salt: "{{ vault_hash_salt }}"
```
---
```yaml
2020-01-30 22:26:34 +00:00
# vars/vars.yml
2019-11-12 08:01:38 +00:00
---
drupal_settings:
2020-01-30 22:26:34 +00:00
- drupal_root: /app/web
2019-11-12 08:01:38 +00:00
sites:
- name: default
settings:
databases:
default:
default:
driver: mysql
host: localhost
database: '{{ database_name }}'
username: '{{ database_user }}'
password: '{{ database_password }}'
hash_salt: '{{ hash_salt }}'
config_directories:
sync: ../config/sync
```
---
```php
// templates/settings.php.j2
2020-01-30 22:26:34 +00:00
2019-11-12 08:01:38 +00:00
// {{ ansible_managed }}
{% for key, values in item.1.settings.databases.items() %}
{% for target, values in values.items() %}
$databases['{{ key }}']['{{ target }}'] = array(
'driver' => '{{ values.driver|default('mysql') }}',
'host' => '{{ values.host|default('localhost') }}',
'database' => '{{ values.database }}',
'username' => '{{ values.username }}',
'password' => '{{ values.password }}',
);
{% endfor %}
{% endfor %}
{% if item.1.settings.base_url is defined %}
$base_url = '{{ item.1.settings.base_url }}';
{% endif %}
2020-01-30 22:26:34 +00:00
{# ... #}
2019-11-12 08:01:38 +00:00
```
---
```yaml
2020-01-30 22:26:34 +00:00
# tasks/main.yml
---
- name: Ensure directory exists
2019-11-12 08:01:38 +00:00
file:
2020-01-30 22:26:34 +00:00
state: directory
path: '{{ item.0.drupal_root }}/sites/{{ item.1.name|default("default") }}'
2019-11-12 08:01:38 +00:00
with_subelements:
- '{{ drupal_settings }}'
- sites
2020-01-30 22:26:34 +00:00
no_log: true
2019-11-12 08:01:38 +00:00
2020-01-30 22:26:34 +00:00
- name: Create settings files
template:
src: settings.php.j2
dest: '{{ item.0.drupal_root }}/sites/{{ item.1.name|default("default") }}/{{ item.1.filename|default("settings.php") }}'
2019-11-12 08:01:38 +00:00
with_subelements:
- '{{ drupal_settings }}'
- sites
2020-01-30 22:26:34 +00:00
no_log: true
```
---
# **Multiple environments**
## Dev, test, production
---
```yaml
mysql_databases:
- name: production
- name: staging
mysql_users:
- name: production
password: '{{ live_db_password }}'
priv: '{{ live_db_name }}.*:ALL'
- name: staging
password: '{{ staging_db_password }}'
priv: staging.*:ALL
```
---
```yaml
# inventories/live.yml
---
all:
hosts:
webservers:
ansible_ssh_host: 192.168.33.10
ansible_ssh_port: 22
project_deploy_path: /app
git_branch: master
drupal_hash_salt: "{{ vault_drupal_hash_salt }}"
drupal_install: true
drupal_settings:
# ...
2019-11-12 08:01:38 +00:00
```
2020-01-30 22:26:34 +00:00
---
```yaml
# inventories/staging.yml
---
all:
hosts:
webservers:
ansible_ssh_host: 192.168.33.10
ansible_ssh_port: 22
project_deploy_path: /app-test
git_branch: develop
drupal_hash_salt: "{{ vault_drupal_hash_salt }}"
drupal_install: true
drupal_settings:
# ...
```
---
# `ansible-playbook deploy.yml -i inventories/staging.yml`
---
# `ansible-playbook deploy.yml -i inventories/live.yml`
---
# **Questions?**