user2023
user2023

Reputation: 478

How ansible can call multiple files under path option as a variable

I am just learning ansible and trying to understand how can i include multiple file in the path option in ansible replace module.

I have three files where i need to replace a old hostname with new hostanme.

Files are :

 - /etc/hosts
 - /etc/hosts.custom
 - /etc/hosts-backup

Below Simple Play works fine:

- name: Replace string in hosts file
  hosts: all
  gather_facts: false
  tasks:
    - name: Replace string in host file
      replace:
        path: /etc/hosts
        regexp: "171.20.20.16   fostrain.example.com"
        replace: "171.20.20.16   dbfoxtrain.example.com"
        backup: yes

However, after lot of googling i see this can be done as follows, but in case i have multiple files and those needs to be called as a variable in different modules, How we can define then in such a way so as to call them by variable name.

Below is Just what i am trying to understand..

- name: Replace string in hosts file
  hosts: all
  gather_facts: false
  tasks:
    - name: Checking file contents
      slurp:
        path: "{{ ?? }}"  <-- How to check these three files here
      register: fileCheck.out

    - debug:
        msg: "{{ (fileCheck.out.content | b64decode).split('\n') }}"

    - name: Replace string in host file
      replace:
        path: "{{ item.path }}"
        regexp: "{{ item:from }}"
        replace: "{{ item:to }}"
        backup: yes
     loop:
       - { path: "/etc/hosts", From: "171.20.20.16   fostrain.example.com", To: "171.20.20.16   dbfoxtrain.example.com"}
       - { Path: "/etc/hosts.custom", From: "171.20.20.16   fostrain.example.com", To: "171.20.20.16   dbfoxtrain.example.com"}
       - { Path: "/etc/hosts-backup", From: "171.20.20.16   fostrain.example.com", To: "171.20.20.16   dbfoxtrain.example.com"}

I will appreciate any help.

Upvotes: 0

Views: 2067

Answers (1)

Moon
Moon

Reputation: 3037

Create couple of variables; a list with all the files, from and to replacement strings or divide them by ip and domain. Then loop over all the files using the file list variable and use from and to replacement variables for each file. If multiple ip and domain mapping is required then you need to adjust the structure further. So recommend going through ansible documentation on using variables and loops for more details.

Playbook may look like below. Have used a minor regex and you can adjust as required.

- name: Replace string in hosts file
  hosts: all
  gather_facts: false
  vars:
    files:
      - /etc/hosts
      - /etc/hosts.custom
      - /etc/hosts-backup
    from_ip: "171.20.20.16"
    from_dn: "fostrain.example.com"
    to_ip: "171.20.20.16"
    to_dn: "dbfoxtrain.example.com"
  tasks:
    - name: Replace string in host file
      replace:
        path: "{{ item }}"
        regexp: "{{ from_ip }}\\s+{{ from_dn }}"
        replace: "{{ to_ip }} {{ to_dn }}"
      loop: "{{ files }}"

If you want to see the contents of each file then slurp and debug modules can be used like below:

    - slurp:
        path: "{{ item }}"
      loop: "{{ files }}"
      register: contents
    
    - debug:
        msg: "{{ (item.content | b64decode).split('\n') }}"
      loop: "{{ contents.results }}"

Upvotes: 1

Related Questions