completenewb
completenewb

Reputation: 73

Ansible replace code in multiple files in a directory

I'm trying to disable all repos on my server using ansible, so I'm trying to do a replace on multiple files within one directory but can't seem to get it to work any idea appreciated!

tasks:

  - name: get repo names
    raw: find /etc/yum.repos.d/ -type f -name "*.repo"
    register: repos

  - name: disable all repos
    replace: dest={{repos}} regexp="enabled=1" replace="enabled=0"
    with_items: repos.stdout_lines

When I run this I just get an error like it's trying to do them all at once? How would I split them up if that was the case?

/etc/yum.repos.d/CentOS-Debuginfo.repo\r\n/etc/yum.repos.d/epel.repo\r\n/etc/yum.repos.d/CentOS-Base.repo\r\n'} does not exist !",

update:

  - find:
      paths: "/etc/yum.repos.d/"
      patterns: "*.repo"
    register: repos

  - name: disable all repos
    replace: dest={{items}} regexp="enabled=1" replace="enabled=0"
    with_items: repos

The new error is following: "msg": "the field 'args' has an invalid value, which appears to include a variable that is undefined. The error was: 'items' is undefined

Okay Getting closer! getting this error at the disable repo now:

FAILED! => {
    "failed": true,
    "msg": "'dict object' has no attribute 'stdout_lines'"
}

Upvotes: 6

Views: 18246

Answers (4)

Marko Novak
Marko Novak

Reputation: 1

Just to fullfill the answer from AlanSE:

tasks:
- name: Find all of the files inside this directory
  find:
    paths: "/etc/yum.repos.d/"
    patterns: "*.repo"
  register: repos

- name: Replace foo with bar in the files
  replace:
    path: "{{ item.path }}"
    regexp: 'foo'
    replace: 'bar'
  loop: "{{ repos.results | json_query('[*].files') | flatten }}"

This should work perfectly fine.

Upvotes: 0

AlanSE
AlanSE

Reputation: 2775

This question seems to have trailed off without fully completing... at least not with using find. Here is an example of the 2-step process that was sought after. The case for using raw for the first case has been answered. But I find this solution more appealing, even if harder:

tasks:
- name: Find all of the files inside this directory
  find:
    paths: "/etc/yum.repos.d/"
    patterns: "*.repo"
  register: repos

- name: Replace foo with bar in the files
  replace:
    path: "{{ item.path }}"
    regexp: 'foo'
    replace: 'bar'
  with_items: "{{ repos.files }}"

This required some research on the output structure of the find command.

Upvotes: 11

techraf
techraf

Reputation: 68559

It is "trying them all at once", because you are providing the whole output of the previous task as an argument for the dest:

dest={{repos}}

Instead, you should be feeding the items you iterate over:

dest={{item}}

You also don't quote the variable in the with_items.

Second task should look like this:

- name: disable all repos
  replace: dest={{item}} regexp="enabled=1" replace="enabled=0"
  with_items: "{{ repos.stdout_lines }}"

Besides, you can use find module instead of raw command.

Upvotes: 4

Alexandr Kondratiev
Alexandr Kondratiev

Reputation: 13

The error was: 'items' is undefined

this is because u must use "item" instead of items in

 dest=

(dest={{item}})

, but with items

so the proper way is:

- name: disable all repos
  replace: dest={{item}} regexp="enabled=1" replace="enabled=0"
  with_items: repos

Upvotes: 0

Related Questions