Aldem
Aldem

Reputation: 47

How to iterate over variables in an ansible dictionary

I have a role that should scatter NGINX configs across different servers using Jinja2 templates, referring to the variables specified in defaults/main, please tell me how to write a loop to iterate over these variables correctly, tried it through with_items and with_nested, but nothing happens.
The defaults/main file looks like this:

allservers:
  server1:
    - { src: 'templates/sites-enabled/api.j2',                       dest: '/etc/nginx/sites-enabled/api.conf' }                               
    - { src: 'templates/sites-enabled/citizens.j2',                  dest: '/etc/nginx/sites-enabled/citizens.conf' }
    - { src: 'templates/sites-enabled/control.j2',                   dest: '/etc/nginx/sites-enabled/control.conf' }
    - { src: 'templates/sites-enabled/documents.j2',                 dest: '/etc/nginx/sites-enabled/documents.conf' }
    - { src: 'templates/sites-enabled/orders.j2',                    dest: '/etc/nginx/sites-enabled/orders.conf' }
    - { src: 'templates/sites-enabled/logs.j2',                      dest: '/etc/nginx/sites-enabled/logs.conf' }

  server2:
    - { src: 'templates/sites-enabled/permissions.j2',               dest: '/etc/nginx/sites-enabled/permissions.conf' }
    - { src: 'templates/sites-enabled/documents.j2',                 dest: '/etc/nginx/sites-enabled/documents.conf' }
    - { src: 'templates/sites-enabled/default.j2',                   dest: '/etc/nginx/sites-enabled/default' }
    - { src: 'templates/sites-enabled/orders.j2',                    dest: '/etc/nginx/sites-enabled/orders.conf' }
    - { src: 'templates/sites-enabled/settings.j2',                  dest: '/etc/nginx/sites-enabled/settings.conf' }

Upvotes: 0

Views: 448

Answers (1)

user1098490
user1098490

Reputation: 488

I assume you do not want to change your data structure, and that server1 and server2 refer to hosts in your inventory.

---                                                                             
- hosts: server1:server2                                                        
  remote_user: ansible                                                          
  vars:                                                                         
    allservers:                                                                 
      server1:                                                                  
          - { src: "/tmp/file1", dest: "/tmp"}                                  
          - { src: "/tmp/file2", dest: "/tmp"}                                  
          - { src: "/tmp/file3", dest: "/tmp"}                                  
      server2:                                                                  
          - { src: "/tmp/file4", dest: "/tmp"}                                  
          - { src: "/tmp/file5", dest: "/tmp"}                                  
          - { src: "/tmp/file6", dest: "/tmp"}    


  tasks:
    - name: Copy template
      template:
        src: "{{ item.src }}"
        dest: "{{ item.dest }}"
      when: inventory_hostname in allservers.keys()
      with_items:
        - "{{ allservers[inventory_hostname] }}"

Another solutions is to include a task (copy_template.yml) which you will iterate over using with_dict: allservers.

playbook.yml

---                                                                             
- hosts: server1:server2                                                        
  remote_user: ansible                                                          
  vars:                                                                         
    allservers:                                                                 
      server1:                                                                  
          - { src: "/tmp/file1", dest: "/tmp"}                                  
          - { src: "/tmp/file2", dest: "/tmp"}                                  
          - { src: "/tmp/file3", dest: "/tmp"}                                  
      server2:                                                                  
          - { src: "/tmp/file4", dest: "/tmp"}                                  
          - { src: "/tmp/file5", dest: "/tmp"}                                  
          - { src: "/tmp/file6", dest: "/tmp"}                                  
  tasks:                                                                        
    - include: copy_template.yml                                                
      vars:                                                                     
        server: "{{ item.key }}"                                                
      with_dict:                                                                
        - "{{ allservers }}" 

copy_template.yml

---                                                                             
- debug:                                                                        
    msg: "{{ template.src }}  and  {{ template.dest }}"                         
  loop: "{{ allservers[server] }}"                                  
  when: server == inventory_hostname                                            
  loop_control:                                                                 
    loop_var: template 

Upvotes: 1

Related Questions