Como Usar vars_files do Ansible para Gerenciamento de Configuração

AnsibleBeginner
Pratique Agora

Introdução

Este tutorial irá guiá-lo através do uso de vars_files do Ansible para uma gestão de configuração eficiente. Ansible é uma ferramenta de automação poderosa que ajuda a gerir a infraestrutura através de ficheiros YAML simples e legíveis por humanos. A funcionalidade vars_files permite que mantenha os seus dados de configuração separados da sua lógica de automação, tornando os seus projetos Ansible mais organizados e fáceis de manter.

Ao final deste tutorial, você aprenderá como criar e organizar vars_files, incorporá-los em playbooks e aproveitá-los para gerir diferentes ambientes de forma eficaz. Este conhecimento o ajudará a construir uma automação de infraestrutura mais escalável e sustentável.

Instalando o Ansible e Criando o Seu Primeiro vars_file

Neste primeiro passo, vamos instalar o Ansible no nosso sistema e criar o nosso primeiro vars_file para armazenar dados de configuração.

Instalando o Ansible

Vamos começar instalando o Ansible no nosso sistema Ubuntu:

sudo apt update
sudo apt install -y ansible

Após a conclusão da instalação, verifique se o Ansible está instalado corretamente:

ansible --version

Você deve ver uma saída semelhante a esta, mostrando a versão e a configuração do Ansible:

ansible [core 2.12.x]
  config file = /etc/ansible/ansible.cfg
  configured module search path = ['/home/labex/.ansible/plugins/modules', '/usr/share/ansible/plugins/modules']
  ansible python module location = /usr/lib/python3/dist-packages/ansible
  ansible collection location = /home/labex/.ansible/collections:/usr/share/ansible/collections
  executable location = /usr/bin/ansible
  python version = 3.10.x (default, Mar 14 2023, 14:21:35) [GCC 11.3.0]
  jinja version = 3.0.3
  libyaml = True

Criando uma Estrutura de Diretórios do Projeto

Vamos criar uma estrutura de diretórios para o nosso projeto Ansible:

mkdir -p ~/project/ansible-vars-demo/vars
cd ~/project/ansible-vars-demo

Compreendendo os vars_files do Ansible

Os vars_files do Ansible são ficheiros YAML que armazenam definições de variáveis que podem ser importadas para playbooks. Estes ficheiros permitem que você:

  1. Separe os dados de configuração da lógica de automação
  2. Reutilize as mesmas variáveis em múltiplos playbooks
  3. Mantenha diferentes configurações para diferentes ambientes

Criando o Seu Primeiro vars_file

Vamos criar o nosso primeiro vars_file para armazenar as configurações do servidor web. Usando o WebIDE, crie um novo ficheiro em ~/project/ansible-vars-demo/vars/webserver.yml com o seguinte conteúdo:

---
## Web Server Configuration
http_port: 80
server_name: example.com
document_root: /var/www/html
max_clients: 200

Este vars_file define quatro variáveis que podem ser usadas na configuração de um servidor web:

  • http_port: A porta em que o servidor web irá escutar
  • server_name: O nome de domínio para o servidor web
  • document_root: O diretório onde os ficheiros do website serão armazenados
  • max_clients: O número máximo de conexões de clientes simultâneas

Para ajudar a entender como isso se parece no WebIDE, navegue até o explorador de ficheiros no lado esquerdo, expanda a pasta project, depois ansible-vars-demo, depois vars, e você deve ver o seu ficheiro webserver.yml. Clique nele para visualizar ou editar o seu conteúdo.

Criando um Ficheiro de Inventário

Em seguida, precisamos criar um ficheiro de inventário para dizer ao Ansible quais hosts gerenciar. Em um ambiente real, isso conteria endereços de servidor reais, mas para este tutorial, usaremos localhost.

Crie um novo ficheiro em ~/project/ansible-vars-demo/inventory.ini com o seguinte conteúdo:

[webservers]
localhost ansible_connection=local

Este inventário simples define um grupo chamado webservers que inclui apenas a nossa máquina local.

Compreendendo a Estrutura do Projeto

Neste ponto, a sua estrutura do projeto deve ser semelhante a esta:

ansible-vars-demo/
├── inventory.ini
└── vars/
    └── webserver.yml

Esta estrutura básica separa o nosso inventário (quais hosts gerenciar) das nossas definições de variáveis (como configurar esses hosts).

Criando um Playbook Básico com vars_files

Agora que criamos o nosso vars_file, vamos construir um playbook Ansible simples que usa estas variáveis. Isso demonstrará como importar e usar dados de configuração de vars_files.

Compreendendo os Playbooks Ansible

Os playbooks Ansible são ficheiros YAML que definem um conjunto de tarefas a serem executadas em hosts gerenciados. Os playbooks são o núcleo da funcionalidade do Ansible, permitindo que você automatize processos de configuração complexos.

Criando um Playbook Simples

Vamos criar um playbook que simulará a configuração de um servidor web usando as variáveis que definimos no nosso vars_file. Crie um novo ficheiro em ~/project/ansible-vars-demo/webserver_setup.yml com o seguinte conteúdo:

---
- name: Configure Web Server
  hosts: webservers
  vars_files:
    - vars/webserver.yml

  tasks:
    - name: Display web server configuration
      debug:
        msg: "Web server will be configured with: Port={{ http_port }}, ServerName={{ server_name }}, DocumentRoot={{ document_root }}"

    - name: Create a directory for document root
      file:
        path: "/tmp/{{ document_root }}"
        state: directory
        mode: "0755"

    - name: Create a sample index.html file
      copy:
        content: |
          <html>
            <head>
              <title>Welcome to {{ server_name }}</title>
            </head>
            <body>
              <h1>Welcome to {{ server_name }}</h1>
              <p>This server is configured to handle {{ max_clients }} simultaneous connections.</p>
            </body>
          </html>
        dest: "/tmp/{{ document_root }}/index.html"
        mode: "0644"

Vamos entender o que este playbook faz:

  1. hosts: webservers - Especifica que este playbook deve ser executado em todos os hosts no grupo "webservers" do nosso inventário.
  2. vars_files: - vars/webserver.yml - Importa variáveis do nosso vars_file.
  3. A primeira tarefa usa o módulo debug para exibir uma mensagem mostrando as variáveis.
  4. A segunda tarefa cria uma estrutura de diretórios que seria usada para a raiz do documento do servidor web.
  5. A terceira tarefa cria um ficheiro HTML de exemplo que inclui as variáveis do nosso vars_file.

Executando o Playbook

Agora, vamos executar o playbook para vê-lo em ação:

cd ~/project/ansible-vars-demo
ansible-playbook -i inventory.ini webserver_setup.yml

Você deve ver uma saída semelhante a esta:

PLAY [Configure Web Server] ****************************************************

TASK [Gathering Facts] *********************************************************
ok: [localhost]

TASK [Display web server configuration] ****************************************
ok: [localhost] => {
    "msg": "Web server will be configured with: Port=80, ServerName=example.com, DocumentRoot=/var/www/html"
}

TASK [Create a directory for document root] ************************************
changed: [localhost]

TASK [Create a sample index.html file] *****************************************
changed: [localhost]

PLAY RECAP *********************************************************************
localhost                  : ok=4    changed=2    unreachable=0    failed=0    skipped=0    rescued=0    ignored=0

Verificando os Resultados

Vamos verificar se o nosso playbook criou os ficheiros esperados:

ls -la /tmp/var/www/html/
cat /tmp/var/www/html/index.html

Você deve ver a estrutura do diretório e o conteúdo do ficheiro index.html, que deve incluir os valores do nosso vars_file:

<html>
  <head>
    <title>Welcome to example.com</title>
  </head>
  <body>
    <h1>Welcome to example.com</h1>
    <p>This server is configured to handle 200 simultaneous connections.</p>
  </body>
</html>

Compreendendo o Fluxo de Trabalho

Vamos recapitular o que realizamos:

  1. Armazenamos dados de configuração em um vars_file separado (vars/webserver.yml).
  2. Criamos um playbook que importa e usa estes dados de configuração.
  3. Executamos o playbook para executar tarefas que usam as variáveis.

Esta separação de dados de configuração (vars_files) da lógica de automação (playbooks) torna o nosso código Ansible mais fácil de manter e reutilizar. Agora podemos atualizar a configuração editando apenas o vars_file, sem alterar o próprio playbook.

Trabalhando com Múltiplos vars_files

Agora que entendemos os conceitos básicos de vars_files, vamos explorar como usar múltiplos vars_files para gerenciar diferentes ambientes. Esta é uma prática comum em cenários do mundo real, onde você pode ter diferentes configurações para ambientes de desenvolvimento, teste e produção.

Criando vars_files Específicos para o Ambiente

Vamos criar vars_files para diferentes ambientes. Primeiro, vamos criar uma configuração de ambiente de desenvolvimento:

Crie um novo ficheiro em ~/project/ansible-vars-demo/vars/dev_environment.yml com o seguinte conteúdo:

---
## Development Environment Configuration
environment_name: development
debug_mode: true
log_level: debug
backup_frequency: weekly
max_memory: 512MB

Em seguida, vamos criar uma configuração de ambiente de produção:

Crie um novo ficheiro em ~/project/ansible-vars-demo/vars/prod_environment.yml com o seguinte conteúdo:

---
## Production Environment Configuration
environment_name: production
debug_mode: false
log_level: error
backup_frequency: daily
max_memory: 2048MB

Criando um Playbook com Múltiplos vars_files

Agora, vamos criar um playbook que usa tanto a nossa configuração do servidor web quanto as configurações específicas do ambiente. Crie um novo ficheiro em ~/project/ansible-vars-demo/environment_setup.yml com o seguinte conteúdo:

---
- name: Configure Environment
  hosts: webservers
  vars:
    env: dev
  vars_files:
    - vars/webserver.yml
    - "vars/{{ env }}_environment.yml"

  tasks:
    - name: Display environment details
      debug:
        msg: >
          Setting up {{ environment_name }} environment with the following parameters:
          - Web Server: {{ server_name }} on port {{ http_port }}
          - Debug Mode: {{ debug_mode }}
          - Log Level: {{ log_level }}
          - Backup Frequency: {{ backup_frequency }}
          - Max Memory: {{ max_memory }}
          - Max Clients: {{ max_clients }}

    - name: Create environment config file
      copy:
        content: |
          ## Environment Configuration for {{ server_name }}
          ENVIRONMENT={{ environment_name }}
          DEBUG={{ debug_mode }}
          LOG_LEVEL={{ log_level }}
          BACKUP_FREQUENCY={{ backup_frequency }}
          MAX_MEMORY={{ max_memory }}
          HTTP_PORT={{ http_port }}
          MAX_CLIENTS={{ max_clients }}
        dest: "/tmp/{{ environment_name }}_config.env"
        mode: "0644"

Este playbook introduz vários novos conceitos:

  1. Definimos uma variável env: dev dentro do próprio playbook.
  2. Incluímos tanto o nosso vars_file do servidor web quanto um vars_file específico do ambiente.
  3. O caminho do vars_file do ambiente inclui uma variável: "vars/{{ env }}_environment.yml", que avalia para vars/dev_environment.yml.
  4. As tarefas usam variáveis de ambos os vars_files.

Executando o Playbook com Diferentes Ambientes

Vamos executar o playbook primeiro com o ambiente de desenvolvimento (que já é o padrão):

cd ~/project/ansible-vars-demo
ansible-playbook -i inventory.ini environment_setup.yml

Você deve ver uma saída que inclui as configurações do ambiente de desenvolvimento:

TASK [Display environment details] ********************************************
ok: [localhost] => {
    "msg": "Setting up development environment with the following parameters:\n- Web Server: example.com on port 80\n- Debug Mode: True\n- Log Level: debug\n- Backup Frequency: weekly\n- Max Memory: 512MB\n- Max Clients: 200"
}

Agora, vamos executar o mesmo playbook, mas substituir a variável env para usar o ambiente de produção:

ansible-playbook -i inventory.ini environment_setup.yml -e "env=prod"

Você deve ver uma saída que inclui as configurações do ambiente de produção:

TASK [Display environment details] ********************************************
ok: [localhost] => {
    "msg": "Setting up production environment with the following parameters:\n- Web Server: example.com on port 80\n- Debug Mode: False\n- Log Level: error\n- Backup Frequency: daily\n- Max Memory: 2048MB\n- Max Clients: 200"
}

Verificando os Ficheiros de Configuração

Vamos verificar se o nosso playbook criou os ficheiros de configuração do ambiente:

cat /tmp/development_config.env
cat /tmp/production_config.env

Você deve ver dois ficheiros de configuração diferentes, cada um com configurações do respectivo vars_file do ambiente.

Compreendendo a Precedência de Variáveis

É importante entender que, ao usar múltiplos vars_files, o Ansible segue uma ordem específica de precedência para as variáveis. Se o mesmo nome de variável aparecer em vários lugares, o valor definido posteriormente substituirá as definições anteriores.

No nosso exemplo, se tivéssemos definido http_port tanto nos ficheiros webserver.yml quanto dev_environment.yml, o valor de dev_environment.yml teria precedência porque ele é incluído mais tarde na lista vars_files.

Este comportamento permite que você defina padrões comuns em um ficheiro e, em seguida, substitua valores específicos para diferentes ambientes.

Técnicas Avançadas de vars_files

Nesta etapa final, exploraremos algumas técnicas avançadas para trabalhar com vars_files no Ansible, incluindo a organização hierárquica de variáveis e a implementação da organização de variáveis baseada em funções (roles).

Organizando Variáveis Hierarquicamente

Em projetos complexos, é frequentemente útil organizar as variáveis hierarquicamente. Vamos criar uma estrutura onde temos:

  1. Variáveis comuns que se aplicam a todos os ambientes
  2. Variáveis específicas do ambiente
  3. Variáveis específicas da aplicação

Primeiro, vamos criar um ficheiro de variáveis comuns:

Crie um novo ficheiro em ~/project/ansible-vars-demo/vars/common.yml com o seguinte conteúdo:

---
## Common variables for all environments
organization: "Example Corp"
admin_email: "admin@example.com"
timezone: "UTC"

Em seguida, vamos criar variáveis específicas da aplicação:

Crie um novo ficheiro em ~/project/ansible-vars-demo/vars/database.yml com o seguinte conteúdo:

---
## Database application variables
db_port: 3306
db_user: "dbuser"
db_name: "appdb"
db_max_connections: 100

Criando um Playbook Hierárquico

Agora, vamos criar um playbook que demonstra o uso destas variáveis hierárquicas. Crie um novo ficheiro em ~/project/ansible-vars-demo/hierarchical_setup.yml com o seguinte conteúdo:

---
- name: Hierarchical Variable Demo
  hosts: webservers
  vars:
    env: dev
    app: database
  vars_files:
    - "vars/common.yml"
    - "vars/{{ env }}_environment.yml"
    - "vars/{{ app }}.yml"

  tasks:
    - name: Display hierarchical configuration
      debug:
        msg: >
          Configuration for {{ app }} in {{ environment_name }} environment:
          - Organization: {{ organization }}
          - Admin Email: {{ admin_email }}
          - Timezone: {{ timezone }}
          - Debug Mode: {{ debug_mode }}
          - Log Level: {{ log_level }}
          - DB Port: {{ db_port }}
          - DB User: {{ db_user }}
          - DB Max Connections: {{ db_max_connections }}

    - name: Create hierarchical config file
      copy:
        content: |
          ## {{ organization }} Configuration
          ## {{ environment_name }} Environment

          ## Common Settings
          ADMIN_EMAIL={{ admin_email }}
          TIMEZONE={{ timezone }}

          ## Environment Settings
          DEBUG={{ debug_mode }}
          LOG_LEVEL={{ log_level }}
          BACKUP_FREQUENCY={{ backup_frequency }}

          ## {{ app | capitalize }} Settings
          DB_PORT={{ db_port }}
          DB_USER={{ db_user }}
          DB_NAME={{ db_name }}
          DB_MAX_CONNECTIONS={{ db_max_connections }}
        dest: "/tmp/{{ environment_name }}_{{ app }}_config.conf"
        mode: "0644"

Compreendendo as Variáveis de Grupo e Host

Além de vars_files, o Ansible também suporta o armazenamento de variáveis em diretórios especiais chamados group_vars e host_vars. Vamos ver como isso funciona:

Crie uma estrutura de diretórios para variáveis de grupo e host:

mkdir -p ~/project/ansible-vars-demo/group_vars
mkdir -p ~/project/ansible-vars-demo/host_vars

Agora, crie um ficheiro de variáveis de grupo para o grupo 'webservers':

Crie um novo ficheiro em ~/project/ansible-vars-demo/group_vars/webservers.yml com o seguinte conteúdo:

---
## Variables for all webservers
firewall_enabled: true
ssh_port: 22
monitoring_enabled: true

E crie um ficheiro de variáveis de host para 'localhost':

Crie um novo ficheiro em ~/project/ansible-vars-demo/host_vars/localhost.yml com o seguinte conteúdo:

---
## Variables specific to localhost
local_backup_path: "/tmp/backups"
is_development_machine: true

Criando um Playbook com Todos os Tipos de Variáveis

Vamos criar um playbook final que demonstra o uso de todos os tipos de variáveis juntos. Crie um novo ficheiro em ~/project/ansible-vars-demo/complete_setup.yml com o seguinte conteúdo:

---
- name: Complete Variable Demo
  hosts: webservers
  vars:
    env: prod
    app: database
  vars_files:
    - "vars/common.yml"
    - "vars/{{ env }}_environment.yml"
    - "vars/{{ app }}.yml"

  tasks:
    - name: Display complete configuration
      debug:
        msg: >
          Complete configuration for {{ inventory_hostname }}:
          - Organization: {{ organization }}
          - Environment: {{ environment_name }}
          - Debug Mode: {{ debug_mode }}
          - Firewall Enabled: {{ firewall_enabled }}
          - SSH Port: {{ ssh_port }}
          - Monitoring Enabled: {{ monitoring_enabled }}
          - Local Backup Path: {{ local_backup_path }}
          - Is Development Machine: {{ is_development_machine }}

    - name: Create complete config file
      copy:
        content: |
          ## {{ organization }} - {{ environment_name }} Environment
          ## Host: {{ inventory_hostname }}

          ## Common Settings
          ADMIN_EMAIL={{ admin_email }}
          TIMEZONE={{ timezone }}

          ## Environment Settings
          DEBUG={{ debug_mode }}
          LOG_LEVEL={{ log_level }}

          ## Server Settings
          FIREWALL_ENABLED={{ firewall_enabled }}
          SSH_PORT={{ ssh_port }}
          MONITORING_ENABLED={{ monitoring_enabled }}

          ## Host-specific Settings
          LOCAL_BACKUP_PATH={{ local_backup_path }}
          IS_DEVELOPMENT_MACHINE={{ is_development_machine }}

          ## {{ app | capitalize }} Settings
          DB_PORT={{ db_port }}
          DB_USER={{ db_user }}
          DB_NAME={{ db_name }}
        dest: "/tmp/complete_config.conf"
        mode: "0644"

Executando os Playbooks Avançados

Vamos executar o nosso playbook hierárquico:

cd ~/project/ansible-vars-demo
ansible-playbook -i inventory.ini hierarchical_setup.yml

Você deve ver uma saída que inclui variáveis de todos os três vars_files.

Agora, vamos executar o nosso playbook completo:

ansible-playbook -i inventory.ini complete_setup.yml

Desta vez, você deve ver uma saída que inclui variáveis de vars_files, group_vars e host_vars.

Verificando os Ficheiros de Configuração

Vamos verificar os ficheiros de configuração criados pelos nossos playbooks avançados:

cat /tmp/dev_database_config.conf
cat /tmp/complete_config.conf

Compreendendo a Precedência de Variáveis no Ansible

Ao usar múltiplas fontes de variáveis, o Ansible segue uma ordem específica de precedência:

  1. Variáveis da linha de comando (-e ou --extra-vars)
  2. Variáveis definidas no play
  3. Variáveis de ficheiros e funções (roles) incluídas
  4. Fatos do host
  5. Variáveis do host (host vars)
  6. Variáveis do grupo (group vars)
  7. Variáveis do inventário
  8. Variáveis padrão da função (role)

Isso significa que as variáveis definidas em host_vars substituirão as mesmas variáveis definidas em group_vars, que substituirão as mesmas variáveis definidas em vars_files.

Esta estrutura hierárquica oferece uma maneira poderosa de gerenciar a configuração em diferentes ambientes, hosts e aplicações.

Resumo

Neste tutorial, você aprendeu a usar efetivamente vars_files do Ansible para gerenciamento de configuração. Você:

  1. Instalou o Ansible e criou seu primeiro vars_file para armazenar dados de configuração
  2. Criou e executou um playbook básico que usa vars_files para separar a configuração da lógica de automação
  3. Trabalhou com múltiplos vars_files para gerenciar diferentes ambientes
  4. Explorou técnicas avançadas, incluindo organização hierárquica de variáveis e o uso de group_vars e host_vars

Essas habilidades fornecem uma base sólida para construir automação Ansible escalável e sustentável. Ao separar seus dados de configuração da sua lógica de automação, você pode:

  • Tornar seus playbooks mais reutilizáveis em diferentes ambientes
  • Simplificar o processo de atualização dos valores de configuração
  • Gerenciar configurações complexas de forma estruturada
  • Melhorar a colaboração, organizando claramente os dados de configuração

Ao continuar trabalhando com o Ansible, lembre-se de que o gerenciamento eficaz de variáveis é fundamental para construir automação sustentável. As técnicas que você aprendeu neste tutorial o ajudarão a organizar seus projetos Ansible à medida que eles crescem em complexidade.