In Ansible, you can define conditions that you can evaluate before performing a task. When the condition is not met, the task is skipped. This is done with the when keyword, which accepts expressions that are usually based on a variable or a fact.

The following example defines two variables: create_user_file and user. When create_user_file is evaluated to true, a new file is created in the home directory of the user defined by the user variable.

Create a new file named playbook-04.yml in your ansible-practice directory.

nano ~/ansible-practice/playbook-04.yml
Copy the code

Then add the following lines to the new PlayBook file.

~/ansible-practice/playbook-04.yml

---
- hosts: all
  vars:
    - create_user_file: yes
    - user: sammy  
  tasks:
    - name: create file for user
      file:
        path: /home/{{ user }}/myfile
        state: touch
      when: create_user_file
Copy the code

When you have finished editing the contents of the file, save and close the file.

To perform this play on the server in the manifest file, run ansible-Playbook with the same connection parameters that you used to run other plays in this series. Again, we will use an inventory file named Inventory and Sammy user to connect to the remote server.

ansible-playbook -i inventory playbook-04.yml -u sammy
Copy the code

When the condition is met, you will see the changed state in the play output.

Output... TASK [create file for user] ***************************************************************************** changed: [203.0.113.10]...Copy the code

If you change the value of create_user_file to no, the condition will be evaluated as false. In this case, you will see skipping in the playback output, indicating that the task has not been executed.

Output... TASK [create file for user] ***************************************************************************** skipping: [203.0.113.10]...Copy the code

A common use of conditional in the context of Ansible Playbook is to combine it with register, a keyword that creates a new variable and assigns it to the output obtained from a command. In this way, you can use any external command to evaluate the execution of a task.

One thing to note is that by default Ansible will break a game if the command you used to evaluate the condition fails. To do this, you need to include an ignore_errors directive in the task, set to yes, which will cause Ansible to proceed to the next task and continue the game.

The following example will only create a new file in the user’s home directory, in case it doesn’t already exist, we will test it with the ls command. However, if the file exists, we will display a message using the Debug module.

Create a new file named playbook-05.yml in your ansible-practice directory.

nano ~/ansible-practice/playbook-05.yml
Copy the code

Then add the following to the new PlayBook file.

~/ansible-practice/playbook-05.yml

---
- hosts: all
  vars:
    - user: sammy
  tasks:
    - name: Check if file already exists
      command: ls /home/{{ user }}/myfile
      register: file_exists
      ignore_errors: yes

    - name: create file for user
      file:
        path: /home/{{ user }}/myfile
        state: touch
      when: file_exists is failed

    - name: show message if file exists
      debug:
        msg: The user file already exists.
      when: file_exists is succeeded
Copy the code

When finished, save and close the file.

Then, run ansible-Playbook with the same connection parameters as in the previous example. Here, we use an inventory file named Inventory and a user named Sammy, but you should change these values accordingly.

ansible-playbook -i inventory playbook-05.yml -u sammy
Copy the code

The first time you run the game manual, the command will fail because the file does not exist in the path. The task of creating the file will then be executed, and the last task will be skipped.

Output... TASK [Check if file already exists] ********************************************************************* fatal: [the 203.0.113.10] FAILED! = > {" changed ": true," CMD ": [" ls", "/ home/Sammy/myfile"], "delta" : "0:00:00. 004258", "end" : ", "MSG ": "non-zero return code", "rc": 2, "start": "2020-10-22 13:10:12.675816", "stderr": "ls: cannot access '/home/sammy/myfile': No such file or directory", "stderr_lines": ["ls: cannot access '/home/sammy/myfile': No such file or directory"], "stdout": "", "stdout_lines": []} ... ignoring TASK [create file for user] ***************************************************************************** changed: [203.0.113.10] TASK [show message if the file exists] * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * Skipping: [203.0.113.10]...Copy the code

From the output, you can see that the Create File for User task causes changes in the server, which means that the file is created. Now run the game manual again and you’ll get a different result.

ansible-playbook -i inventory playbook-05.yml -u sammy
Copy the code
Output... TASK [Check if file already exists] ********************************************************************* changed: [203.0.113.10] TASK [create the file for user] * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *  skipping: [203.0.113.10] TASK [show message if the file exists] * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * [203.0.113.10] => {" MSG ": "The user file already exists."}...Copy the code

If you want to learn more about using conditional statements in Ansible Playbook, refer to the official documentation.