Ansible
O ansible é uma forma de comunicação superluminica. Ou seja passar uma informação ao mesmo tempo para objetos.
É uma ferramenta opensource que te possibilita realizar comunicação e interação com diversos destinos ao mesmo tempo, tudo de forma automatizada.
- Gerenciamento de mudança
- Provisionamento
- Automação
- Orquestração
Gerenciamento de Mudança
=> Idempotente Executa somente uma vez as alterações, se não houve alteração ele não executa.
=> Pode também criar rotinas automatizadas por versão, exemplo (php7 em uma maquina client, rodo o ansible que está configurado com o php 7.5, ele vai reverter tudo para o 7.5)
Provisionamento
=> Configuração => Instalação => Preparação => Alteração do System State
Automação
=> Execução de tarefas de forma automática => Ordenação de tarefas (tasks) => Realizar decisões => Ad-hoc tasks
Orquestração
=> Múltíiplos servidores => Muliplas aplicações => Diferentes tarefas => Ambiente Hibrido
Por que o Ansible?
De que forma o Ansible é diferente de outras ferramentas?
É fácil - o Ansible usa uma sintaxe simples (YAML) e é fácil para qualquer pessoa (desenvolvedores, administradores de sistemas, gerentes) entender. APIs são simples e úteis.
Sem agente - Ansible usa ssh para conectar e executar comandos. Você não precisa de nenhum agente / software adicional em execução no seu cliente.
Configuração rápida - como você não precisa instalar agentes ou daemons extras, a configuração é muito simples e rápida.
Seguro - uma vez que usa ssh para comunicação, é muito seguro e protegido. Não requer nenhuma porta extra ou daemons vulneráveis em seus servidores.
Arquitetura & funcionamento do Ansible
Como ele funciona?
Desenvolvido em python, versão <3.5 ou Python <2.7
Procura sempre o interpretador em /usr/bin/python –> Variavel: ansible_python_interpreter
Utiliza-se também do serviço SSH para comunicação com os servidores linux, like ou WinRM para comunicação com servidores M$ Windows.
-> Usuário + Senha -> Chave SSH (Para servidores Linux)
Autenticação descentralizada
Pode-se autenticar/conectar-se com LDAP e kerberos.
Instalação do Ansible
Por padrão, o Ansible gerencia as máquinas por meio do protocolo SSH. Depois que o Ansible for instalado, ele não adicionará um banco de dados e não haverá daemons para iniciar ou manter em execução. Você só precisa instalá-lo em uma máquina e ele pode gerenciar uma frota inteira de máquinas remotas a partir desse ponto central. Quando o Ansible gerencia máquinas remotas, ele não deixa o software instalado ou em execução nelas, então não há dúvidas reais sobre como atualizar o Ansible ao mudar para uma nova versão.
A única dependência que o Ansible tem para instalação é o Python. O Ansible pode ser instalado diretamente usando o gerenciador de pacotes do sistema operacional com base no sistema operacional que você está executando e via pip, que é o gerenciador de pacotes do Python.
RHEL / CentOS / Fedora:
Certifique-se de habilitar o repo EPEL antes de executar o comando abaixo para RHEL e CentOS.
sudo yum install ansible
Ubuntu:
$
$ sudo apt-add-repository ppa:ansible/ansible
$ sudo apt-get update
$ sudo apt-get install ansible
Instalação Ansible usando pip
(caso não tenha o pip instalado faça:)
$ sudo apt-get install python3-pip
E depois instale o ansible:
$ sudo pip3 install ansible
Se precisar fazer upgrade
$ sudo pip3 install ansible --upgrade
- instale o ssh
- gere sua chave ssh, ssh-keygen -t rsa
- instale o sshpass
Configurando o Ansible
O principal arquivo de configuração do ansible, é o ansible.cfg
Sua localização padrão é /etc/ansible/ansible.cfg
Alterações e configurações são interpretadas respeitando a seguinte ordem.:
-> Váriavel ANSIBLE_CONFIG -> ansible.cfg no diretorio corrente -> .ansible.cfg diretorio home -> /etc/ansible/ansible.cfg
A primeira coisa a se fazer é fazer uma cópia do ‘ansible.cfg’, que fica dentro do /etc/ansible/
Preservei o original e joguei um arquivo mais resumido com as opções mais utilizadas do ansible.
[defaults]
#--- General settings
forks = 5
log_path = /var/log/ansible.log
module_name = command
executable = /bin/bash
ansible_managed = Ansible managed
#--- Files/Directory settings
inventory = /etc/ansible/hosts
library = /usr/share/my_modules
remote_tmp = ~/.ansible/tmp
local_tmp = ~/.ansible/tmp
roles_path = /etc/ansible/roles
#--- Users settings
remote_user = root
sudo_user = root
ask_pass = no
ask-sudo_pass = no
#--- SSH settings
remote_port = 22
timeout = 10
host_key_checking = False
ssh_executable = /usr/bin/ssh
private_key_file = ~/.ssh/id_rsa
[privilege_scalation]
become = True
become_method = sudo
become_user = root
become_ask_pass = False
[ssh_connection]
scp_if_ssh = smart
transfer_method = smart
retries = 3
Testando na maquina alvo
osboxes@FXSHELL:/etc/ansible$ ansible 192.168.1.151 -u osboxes -k -m ping
[WARNING]: log file at /var/log/ansible.log is not writeable and we cannot create it, aborting
SSH password:
[DEPRECATION WARNING]: Distribution debian 10.0 on host 192.168.1.151 should
use /usr/bin/python3, but is using /usr/bin/python for backward compatibility
with prior Ansible releases. A future Ansible release will default to using the
discovered platform python for this host. See https://docs.ansible.com/ansible
/2.10/reference_appendices/interpreter_discovery.html for more information.
This feature will be removed in version 2.12. Deprecation warnings can be
disabled by setting deprecation_warnings=False in ansible.cfg.
192.168.1.151 | SUCCESS => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": false,
"ping": "pong"
}
osboxes@FXSHELL:/etc/ansible$
[DEPRECATION WARNING]: Distribution debian 10.0 on host 192.168.1.234 should
use /usr/bin/python3, but is using /usr/bin/python for backward compatibility
with prior Ansible releases. A future Ansible release will default to using the
discovered platform python for this host. See https://docs.ansible.com/ansible
/2.10/reference_appendices/interpreter_discovery.html for more information.
This feature will be removed in version 2.12. Deprecation warnings can be
disabled by setting deprecation_warnings=False in ansible.cfg.
192.168.1.234 | SUCCESS => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": false,
"invocation": {
"module_args": {
"data": "pong"
}
},
"ping": "pong"
}
META: ran handlers
META: ran handlers
osboxes@FXSHELL:/etc/ansible$
Podemos também explicitar para ele ignorar a mensagem do python.
basta adicionar no ansible.cfg a linha
interpreter_python = auto_legacy_silent
osboxes@FXSHELL:/etc/ansible$ ansible 192.168.1.234 -u osboxes -k -m ping
[WARNING]: log file at /var/log/ansible.log is not writeable and we cannot create it, aborting
SSH password:
192.168.1.234 | SUCCESS => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": false,
"ping": "pong"
}
osboxes@FXSHELL:/etc/ansible$
Existe um modulo bem interessante chamado ansible facts, varrendo todos os targets montando uma especie de inventário deles.
Para buscar essas informações basta executar o modulo ‘setup’
osboxes@FXSHELL:/etc/ansible$ ansible 192.168.1.234 -u osboxes -k -m setup
Também existe um modulo chamado systemd com o argumento ‘-a’ com “name=ssh state=restarted”
Ficando dessa forma:
osboxes@FXSHELL:/etc/ansible$ ansible 192.168.1.151 -u osboxes -k -b -m systemd -a "name=ssh state=restarted"
osboxes@FXSHELL:/etc/ansible$ ansible 192.168.1.151 -u osboxes -k -b -m systemd -a "name=ssh state=restarted"
[WARNING]: log file at /var/log/ansible.log is not writeable and we cannot create it, aborting
SSH password:
192.168.1.151 | CHANGED => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": true,
"name": "ssh",
"state": "started",
"status": {
"ActiveEnterTimestamp": "Wed 2021-04-07 22:52:06 EDT",
"ActiveEnterTimestampMonotonic": "246017520",
"ActiveExitTimestampMonotonic": "0",
"ActiveState": "active",
"After": "system.slice -.mount network.target auditd.service systemd-journald.socket basic.target sysinit.target",
"AllowIsolate": "no",
"AmbientCapabilities": "",
"AssertResult": "yes",
"AssertTimestamp": "Wed 2021-04-07 22:52:06 EDT",
"AssertTimestampMonotonic": "245980232",
"Before": "multi-user.target shutdown.target",
"BlockIOAccounting": "no",
"BlockIOWeight": "[not set]",
"CPUAccounting": "no",
"CPUQuotaPerSecUSec": "infinity",
"CPUSchedulingPolicy": "0",
"CPUSchedulingPriority": "0",
"CPUSchedulingResetOnFork": "no",
"CPUShares": "[not set]",
"CPUUsageNSec": "[not set]",
"CPUWeight": "[not set]",
"CacheDirectoryMode": "0755",
"CanIsolate": "no",
"CanReload": "yes",
"CanStart": "yes",
"CanStop": "yes",
"CapabilityBoundingSet": "cap_chown cap_dac_override cap_dac_read_search cap_fowner cap_fsetid cap_kill cap_setgid cap_setuid cap_setpcap cap_linux_immutable cap_net_bind_service cap_net_broadcast cap_net_admin cap_net_raw cap_ipc_lock cap_ipc_owner cap_sys_module cap_sys_rawio cap_sys_chroot cap_sys_ptrace cap_sys_pacct cap_sys_admin cap_sys_boot cap_sys_nice cap_sys_resource cap_sys_time cap_sys_tty_config cap_mknod cap_lease cap_audit_write cap_audit_control cap_setfcap cap_mac_override cap_mac_admin cap_syslog cap_wake_alarm cap_block_suspend",
"CollectMode": "inactive",
"ConditionResult": "yes",
"ConditionTimestamp": "Wed 2021-04-07 22:52:06 EDT",
"ConditionTimestampMonotonic": "245980220",
"ConfigurationDirectoryMode": "0755",
"Conflicts": "shutdown.target",
"ControlGroup": "/system.slice/ssh.service",
"ControlPID": "0",
"DefaultDependencies": "yes",
"Delegate": "no",
"Description": "OpenBSD Secure Shell server",
"DevicePolicy": "auto",
"Documentation": "man:sshd(8) man:sshd_config(5)",
"DynamicUser": "no",
"EnvironmentFiles": "/etc/default/ssh (ignore_errors=yes)",
"ExecMainCode": "0",
"ExecMainExitTimestampMonotonic": "0",
"ExecMainPID": "2270",
"ExecMainStartTimestamp": "Wed 2021-04-07 22:52:06 EDT",
"ExecMainStartTimestampMonotonic": "246010909",
"ExecMainStatus": "0",
"ExecReload": "{ path=/bin/kill ; argv[]=/bin/kill -HUP $MAINPID ; ignore_errors=no ; start_time=[n/a] ; stop_time=[n/a] ; pid=0 ; code=(null) ; status=0/0 }",
"ExecStart": "{ path=/usr/sbin/sshd ; argv[]=/usr/sbin/sshd -D $SSHD_OPTS ; ignore_errors=no ; start_time=[Wed 2021-04-07 22:52:06 EDT] ; stop_time=[n/a] ; pid=2270 ; code=(null) ; status=0/0 }",
"ExecStartPre": "{ path=/usr/sbin/sshd ; argv[]=/usr/sbin/sshd -t ; ignore_errors=no ; start_time=[Wed 2021-04-07 22:52:06 EDT] ; stop_time=[Wed 2021-04-07 22:52:06 EDT] ; pid=2269 ; code=exited ; status=0 }",
"FailureAction": "none",
"FailureActionExitStatus": "-1",
"FileDescriptorStoreMax": "0",
"FinalKillSignal": "9",
"FragmentPath": "/lib/systemd/system/ssh.service",
"GID": "[not set]",
"GuessMainPID": "yes",
"IOAccounting": "no",
"IOSchedulingClass": "0",
"IOSchedulingPriority": "0",
"IOWeight": "[not set]",
"IPAccounting": "no",
"IPEgressBytes": "18446744073709551615",
"IPEgressPackets": "18446744073709551615",
"IPIngressBytes": "18446744073709551615",
"IPIngressPackets": "18446744073709551615",
"Id": "ssh.service",
"IgnoreOnIsolate": "no",
"IgnoreSIGPIPE": "yes",
"InactiveEnterTimestamp": "Wed 2021-04-07 22:48:07 EDT",
"InactiveEnterTimestampMonotonic": "5387216",
"InactiveExitTimestamp": "Wed 2021-04-07 22:52:06 EDT",
"InactiveExitTimestampMonotonic": "245983310",
"InvocationID": "6561c69561a14f76842d4a1ce3592f4a",
"JobRunningTimeoutUSec": "infinity",
"JobTimeoutAction": "none",
"JobTimeoutUSec": "infinity",
"KeyringMode": "private",
"KillMode": "process",
"KillSignal": "15",
"LimitAS": "infinity",
"LimitASSoft": "infinity",
"LimitCORE": "infinity",
"LimitCORESoft": "0",
"LimitCPU": "infinity",
"LimitCPUSoft": "infinity",
"LimitDATA": "infinity",
"LimitDATASoft": "infinity",
"LimitFSIZE": "infinity",
"LimitFSIZESoft": "infinity",
"LimitLOCKS": "infinity",
"LimitLOCKSSoft": "infinity",
"LimitMEMLOCK": "65536",
"LimitMEMLOCKSoft": "65536",
"LimitMSGQUEUE": "819200",
"LimitMSGQUEUESoft": "819200",
"LimitNICE": "0",
"LimitNICESoft": "0",
"LimitNOFILE": "524288",
"LimitNOFILESoft": "1024",
"LimitNPROC": "3795",
"LimitNPROCSoft": "3795",
"LimitRSS": "infinity",
"LimitRSSSoft": "infinity",
"LimitRTPRIO": "0",
"LimitRTPRIOSoft": "0",
"LimitRTTIME": "infinity",
"LimitRTTIMESoft": "infinity",
"LimitSIGPENDING": "3795",
"LimitSIGPENDINGSoft": "3795",
"LimitSTACK": "infinity",
"LimitSTACKSoft": "8388608",
"LoadState": "loaded",
"LockPersonality": "no",
"LogLevelMax": "-1",
"LogRateLimitBurst": "0",
"LogRateLimitIntervalUSec": "0",
"LogsDirectoryMode": "0755",
"MainPID": "2270",
"MemoryAccounting": "yes",
"MemoryCurrent": "5312512",
"MemoryDenyWriteExecute": "no",
"MemoryHigh": "infinity",
"MemoryLimit": "infinity",
"MemoryLow": "0",
"MemoryMax": "infinity",
"MemoryMin": "0",
"MemorySwapMax": "infinity",
"MountAPIVFS": "no",
"MountFlags": "",
"NFileDescriptorStore": "0",
"NRestarts": "0",
"Names": "ssh.service",
"NeedDaemonReload": "no",
"Nice": "0",
"NoNewPrivileges": "no",
"NonBlocking": "no",
"NotifyAccess": "main",
"OOMScoreAdjust": "0",
"OnFailureJobMode": "replace",
"Perpetual": "no",
"PrivateDevices": "no",
"PrivateMounts": "no",
"PrivateNetwork": "no",
"PrivateTmp": "no",
"PrivateUsers": "no",
"ProtectControlGroups": "no",
"ProtectHome": "no",
"ProtectKernelModules": "no",
"ProtectKernelTunables": "no",
"ProtectSystem": "no",
"RefuseManualStart": "no",
"RefuseManualStop": "no",
"RemainAfterExit": "no",
"RemoveIPC": "no",
"Requires": "sysinit.target -.mount system.slice",
"RequiresMountsFor": "/run/sshd",
"Restart": "on-failure",
"RestartUSec": "100ms",
"RestrictNamespaces": "no",
"RestrictRealtime": "no",
"Result": "success",
"RootDirectoryStartOnly": "no",
"RuntimeDirectory": "sshd",
"RuntimeDirectoryMode": "0755",
"RuntimeDirectoryPreserve": "no",
"RuntimeMaxUSec": "infinity",
"SameProcessGroup": "no",
"SecureBits": "0",
"SendSIGHUP": "no",
"SendSIGKILL": "yes",
"Slice": "system.slice",
"StandardError": "inherit",
"StandardInput": "null",
"StandardInputData": "",
"StandardOutput": "journal",
"StartLimitAction": "none",
"StartLimitBurst": "5",
"StartLimitIntervalUSec": "10s",
"StartupBlockIOWeight": "[not set]",
"StartupCPUShares": "[not set]",
"StartupCPUWeight": "[not set]",
"StartupIOWeight": "[not set]",
"StateChangeTimestamp": "Wed 2021-04-07 22:52:06 EDT",
"StateChangeTimestampMonotonic": "246017520",
"StateDirectoryMode": "0755",
"StatusErrno": "0",
"StopWhenUnneeded": "no",
"SubState": "running",
"SuccessAction": "none",
"SuccessActionExitStatus": "-1",
"SyslogFacility": "3",
"SyslogLevel": "6",
"SyslogLevelPrefix": "yes",
"SyslogPriority": "30",
"SystemCallErrorNumber": "0",
"TTYReset": "no",
"TTYVHangup": "no",
"TTYVTDisallocate": "no",
"TasksAccounting": "yes",
"TasksCurrent": "1",
"TasksMax": "1138",
"TimeoutStartUSec": "1min 30s",
"TimeoutStopUSec": "1min 30s",
"TimerSlackNSec": "50000",
"Transient": "no",
"Type": "notify",
"UID": "[not set]",
"UMask": "0022",
"UnitFilePreset": "enabled",
"UnitFileState": "enabled",
"UtmpMode": "init",
"WantedBy": "multi-user.target",
"WatchdogSignal": "6",
"WatchdogTimestampMonotonic": "0",
"WatchdogUSec": "0"
}
}
Um modulo muito legal também é o modulo ‘shell’ que posso executar qualquer comando dentro do meu alvo.
osboxes@FXSHELL:/etc/ansible$ ansible 192.168.1.151 -u osboxes -k -b -m shell -a "systemctl status ssh"
[WARNING]: log file at /var/log/ansible.log is not writeable and we cannot create it, aborting
SSH password:
192.168.1.151 | CHANGED | rc=0 >>
● ssh.service - OpenBSD Secure Shell server
Loaded: loaded (/lib/systemd/system/ssh.service; enabled; vendor preset: enabled)
Active: active (running) since Wed 2021-04-07 23:22:56 EDT; 6min ago
Docs: man:sshd(8)
man:sshd_config(5)
Process: 2437 ExecStartPre=/usr/sbin/sshd -t (code=exited, status=0/SUCCESS)
Main PID: 2438 (sshd)
Tasks: 1 (limit: 1138)
Memory: 2.4M
CGroup: /system.slice/ssh.service
└─2438 /usr/sbin/sshd -D
Apr 07 23:22:56 node2 systemd[1]: Starting OpenBSD Secure Shell server...
Apr 07 23:22:56 node2 sshd[2438]: Server listening on 0.0.0.0 port 22.
Apr 07 23:22:56 node2 sshd[2438]: Server listening on :: port 22.
Apr 07 23:22:56 node2 systemd[1]: Started OpenBSD Secure Shell server.
Apr 07 23:26:56 node2 sshd[2446]: Accepted password for osboxes from 192.168.1.168 port 52234 ssh2
Apr 07 23:26:56 node2 sshd[2446]: pam_unix(sshd:session): session opened for user osboxes by (uid=0)
Apr 07 23:29:11 node2 sshd[2478]: Accepted password for osboxes from 192.168.1.168 port 52236 ssh2
Apr 07 23:29:11 node2 sshd[2478]: pam_unix(sshd:session): session opened for user osboxes by (uid=0)
Se eu não tivesse um usuário comum com poderes de elevação de privilégio eu posso usar a flag ‘-K’ maiusculo para solicitar a senha de super usuário para elevação. (isso caso meu usuário comum não tivesse permissões)
osboxes@FXSHELL:/etc/ansible$ ansible 192.168.1.151 -u osboxes -k -K -m shell -a "systemctl status ssh"
[WARNING]: log file at /var/log/ansible.log is not writeable and we cannot create it, aborting
SSH password:
BECOME password[defaults to SSH password]:
192.168.1.151 | CHANGED | rc=0 >>
● ssh.service - OpenBSD Secure Shell server
Loaded: loaded (/lib/systemd/system/ssh.service; enabled; vendor preset: enabled)
Active: active (running) since Wed 2021-04-07 23:22:56 EDT; 8min ago
Docs: man:sshd(8)
man:sshd_config(5)
Process: 2437 ExecStartPre=/usr/sbin/sshd -t (code=exited, status=0/SUCCESS)
Main PID: 2438 (sshd)
Tasks: 1 (limit: 1138)
Memory: 2.4M
CGroup: /system.slice/ssh.service
└─2438 /usr/sbin/sshd -D
Uma outra opção seria também não especificar nenhum modulo, ele vai pegar o modulo command por padrão.
exemplo:
osboxes@FXSHELL:/etc/ansible$ ansible 192.168.1.151 -u osboxes -k -a "pwd"
SSH password:
192.168.1.151 | CHANGED | rc=0 >>
/home/osboxes
=> flag -u, determino usuário
=> flag -k, senha
=> flag -i, inventário que será utilizado
=> flag -K, solicita a elevação de privilégio
=> flag -b, executar elevação de privilégio (especificar no ansible.cfg)
=> flag -m, modulo que será utilizado
=> flag -a, argumento do modulo
para obter ajuda pode fazer também o –help = ajuda.
Posso também dar um comando ‘all’ se meus targets estiverem dentro do arquivo hosts.
root@FXSHELL /e/ansible# cat hosts
192.168.1.151
192.168.1.234
root@FXSHELL /e/ansible# ansible all -m ping -u osboxes -k
SSH password:
192.168.1.151 | SUCCESS => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": false,
"ping": "pong"
}
192.168.1.234 | SUCCESS => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": false,
"ping": "pong"
}
Imagine que eu preciso executar isso em muitos hosts, para facilitar isso existe uma forma de trabalhar com grupos, dentro do arquivo de hosts.
Exemplo, no arquivo hosts:
[servidores_bd]
192.168.1.151
[servidores_web]
192.168.1.234
ansible -i hosts servidores_bd -m ping -u osboxes -k
Também posso colocar um subgrupo, exemplo:
[servidores:children]
servidores_web
servidores_bd
Ele visualizara todos os subgrupos dele e executará os comandos.
Também posso utilizar variáveis para ajudar na identificação dos hosts, como por exemplo.
Posso setar a variavél
mysql ansible_ssh_host=192.168.1.234
Posso aplicar regras também para grupos de servidores como por exemplo:
[servidores_bd:vars]
ansible_ssh+port=22
ansible_ssh_user=osboxes
ansible_ssh_pass=osboxes.org
ansible_become=yes
ansible_become_method=sudo
ansible_become_user=osboxes
ansible_become_pass=osboxes
ansible_connection=ssh
Por padrão o ansible trabalha com o python 2.7, mas é possivel alterar o intepretador coma a váriavel:
ansible_python_interpreter=(localização do python)
Com isso basta eu executar as regras só o comando com o modulo ‘ping’.
root@FXSHELL /e/ansible# ansible -i hosts servidores_web -m ping
192.168.1.234 | SUCCESS => {
"ansible_facts": {
"discovered_interpreter_python": "/usr/bin/python"
},
"changed": false,
"ping": "pong"
}
Oque são Roles
As roles (funções) são um conjunto de intes independentes destinados a provisionar uma determinada aplicação/infraestrutura.
Itens:
=> Variaveis
=> Modulos
=> Modelos
=> Tarefas
=> Ações
Pode-se associar-se roles com projetos.
As roles possuem uma estrutura padrão de diretórios para seus projetos:
playbook.yml
└── roles
└── common
├── defaults
├── files
├── handlers
├── meta
├── tasks
├── templates
└── vars
Tasks => lista de tarefas para serem executadas em uma role.
handlers => são manipuladores/eventos acionados por uma task.
files => arquivos utilizados para deploy dentro de uma role.
templates => modelos para deploy dentro de uma role (permite o uso de variáveis)
vars => variáveis adicionais de uma role.
defaults => variáveis padrão de uma role. Prioridade máxima.
meta => traga dependências de uma role para outra role - primeiro diretório a ser analisado.
Nota: dentro dos diretorios tasks, handlers, vars, defaults e meta, deverá existir um arquivo com o nome de main.yml para que o mesmo seja interpretado.
Dentro do playbook eu preciso ter:
hosts: webserver
roles:
-common
-nginx
-php
-mysql
Nota: O que determina a execução de uma role são as tasks, cadastradas no arquivo ‘tasks/main.yml’.
Variáveis
São utilizadas pelo ansible para lhe ajudar a trabalhar com diferentes tipos de sistemas, arquiteturas e/ou lhe auxiliar no processo de repetição durante a execução de uma role.
O ansible interpreta as variáveis de diferentes arquivos. Para isso o mesmo mantém a seguinte ordem de prioridades (do menor para o maior):
1. role/defaults/main.yml
2. inventory file
3. host_vars/*
4. group_vars/*
5. roles/vars/main.yml
As variáveis são comumente utilizadas pelos SysAdmin para facilitar no provisionamento de seus sistemas/infraestrutura. Entretando, o ansible permite através do modulo setup obter o que chamamos de Systems Facts.
Os Systems Facts são descobertos pelo ansible através do modulo setup, trazendo informações de todo o sistema. Experimente executar o comando:
ansible hostname -m setup
Para separar um pouco mais as regras coloquei minhas variaveis dentro de group_vars, com ordem de prioridade 4.
├── group_vars
│ └── servidores
├── hosts
├── host_vars
└── roles