Let's say you have the following playbook which uses the file module to create the /tmp/foo file on the Ansible controller (that's your Ansible system).
---
- hosts: localhost
tasks:
- name: touch /tmp/foo
file:
path: /tmp/foo
state: touch
...
Regardless if the /tmp/foo file does or does not exist, the playbook should show that the /tmp/foo file was changed.
PLAY RECAP
localhost : ok=1 changed=1 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
This occurs because the file module will update the access time (atime), change time (ctime) and modify time (mtime) to the date time that the Ansible playbook was run. This can be seen by using the register parameter and debug module which will show the before and after atime and mtime of the file.
---
- hosts: localhost
tasks:
- name: touch /tmp/foo
file:
path: /tmp/foo
state: touch
register: out
- debug:
var: out
...
Which should return something like this. Notice that the before and after atime and mtime are different. You can also view the atime, ctime and mtime of a file using the stat command on a Linux system.
TASK [debug]
ok: [localhost] => {
"out": {
"changed": true,
"dest": "/tmp/foo",
"diff": {
"after": {
"atime": 1643106093.028099,
"mtime": 1643106093.028099,
"path": "/tmp/foo",
"state": "touch"
},
"before": {
"atime": 1643106067.2300391,
"mtime": 1643106051.5419047,
"path": "/tmp/foo",
"state": "file"
}
}
}
}
The changed_when parameter can be used so that the task is not registered as changed. This will not change the behavior of Ansible. The atime and mtime of the file will still be updated.
---
- hosts: localhost
tasks:
- name: touch /tmp/foo
file:
path: /tmp/foo
state: touch
changed_when: false
...
The play recap should have the following.
PLAY RECAP
localhost : ok=1 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
Did you find this article helpful?
If so, consider buying me a coffee over at