Using Conditionals
1. Using When Statements
| Directive | Description | Usage |
|---|---|---|
| when | Conditionally execute a task based on the evaluation of a boolean expression | when: ansible_facts.os_family == 'RedHat' |
Example: Conditional Task Execution
- name: Install Apache on RedHat systems
yum:
name: httpd
state: present
when: ansible_facts.os_family == 'RedHat'
Example: Multiple Conditions
- name: Configure firewall rules
firewalld:
service: ssh
permanent: true
state: enabled
when: ansible_facts.os_family == 'RedHat' and ansible_facts.architecture == 'x86_64'
Note: The
when statement supports all Jinja2 expressions and can include variables, facts, and registered results from previous tasks.
2. Comparing Variables
| Operator | Description | Example | Notes |
|---|---|---|---|
| == | Equal to | {{ item.name }} == 'example' |
Case-sensitive comparison |
| != | Not equal to | {{ item.status }} != 'running' |
Case-sensitive comparison |
| < | Less than | {{ item.count }} < 10 |
Works with numbers and strings (lexicographically) |
| > | Greater than | {{ item.size }} > 1024 |
Works with numbers and strings (lexicographically) |
| <= | Less than or equal to | {{ item.value }} <= 50 |
Works with numbers and strings (lexicographically) |
| >= | Greater than or equal to | {{ item.version }} >= '2.0' |
Works with numbers and string (lexicographically) |
| in | Check if value is in a list or string | {{ item.role }} in ['admin', 'user'] |
Can also check substring in string |
| not in | Check if value is not in a list or string | {{ item.role }} not in ['guest', 'blocked'] |
Can also check substring not in string |
| is defined | Check if a variable is defined | {{ item.variable is defined }} |
Useful for optional variables |
| is not defined | Check if a variable is not defined | {{ item.variable is not defined }} |
Useful for validating required variables |
Example: Comparing Variables in a Loop
- name: Process items based on status
debug:
msg: "Processing item {{ item.name }}"
when: item.status == 'active'
loop:
- name: server1
status: active
- name: server2
status: inactive
Example: Using 'in' Operator
- name: Check if user role is allowed
debug:
msg: "User has admin access"
when: item.role in ['admin', 'superuser']
loop:
- role: admin
- role: user
Note: When comparing strings, lexicographical ordering is used. For example,
'10' < '2' evaluates to false because it compares character-by-character.
3. Checking Variable Existence
| Check | Description | Example |
|---|---|---|
| vars | Check if a variable is defined in the current scope | {{ vars['my_var'] }} |
| hostvars | Check if a variable is defined for a specific host | {{ hostvars['host1']['my_var'] }} |
| groupvars | Check if a variable is defined in group variables | {{ groups['group1']['my_var'] }} |
Example: Using vars to check variable existence
- name: Check if variable exists
debug:
msg: "Variable my_var is set to {{ vars['my_var'] }}"
when: vars['my_var'] is defined
Example: Using hostvars to check variable existence
- name: Check if host variable exists
debug:
msg: "Host var is set to {{ hostvars[inventory_hostname]['my_var'] }}"
when: hostvars[inventory_hostname]['my_var'] is defined
4. Testing Boolean Values
| Operator | Description | Usage | Example |
|---|---|---|---|
| bool | Converts a value to a boolean | {{ value | bool }} |
|
| truthy | Checks if a value is truthy | {{ value | truthy }} |
|
| falsy | Checks if a value is falsy | {{ value | falsy }} |
|
Example: Using Boolean Tests in Conditionals
- name: Check if a variable is truthy
debug:
msg: "Variable is truthy"
when: "{{ my_var | truthy }}"
- name: Check if a variable is falsy
debug:
msg: "Variable is falsy"
when: "{{ my_var | falsy }}"
Note: The
bool filter converts strings like "yes", "true", "1" to true, and "no", "false", "0" to false.
5. Using Logical Operators
| Operator | Description | Example |
|---|---|---|
| and | Logical AND operator. Returns true if both operands are true. | {{ item.value > 5 and item.value < 10 }} |
| or | Logical OR operator. Returns true if at least one operand is true. | {{ item.status == 'active' or item.status == 'pending' }} |
| not | Logical NOT operator. Negates the boolean value. | {{ not item.disabled }} |
Example: Combining Conditions with Logical Operators
- name: Check if user is admin or superuser
debug:
msg: "User has elevated privileges"
when: user.role == 'admin' or user.role == 'superuser'
Example: Complex Condition with Nested Logical Operators
- name: Deploy application if environment is prod and version is stable
deploy:
app_name: myapp
when: >
(ansible_env == 'production' and ansible_version is not defined) or
(ansible_env == 'staging' and ansible_version == 'stable')
6. Checking String Content
| Check | Description | Example |
|---|---|---|
| ansible.builtin.match | Matches a string against a regex pattern | |
| ansible.builtin.search | Searches for a regex pattern in a string | |
| ansible.builtin.regex_search | Searches for a regex pattern in a string and returns match groups | |
| ansible.builtin.regex_replace | Replaces a regex pattern in a string with a replacement value | |
| ansible.builtin.startswith | Checks if a string starts with a specific prefix | |
| ansible.builtin.endswith | Checks if a string ends with a specific suffix | |
| ansible.builtin.contains | Checks if a string contains a substring | |
| ansible.builtin.length | Gets the length of a string | |
7. Using Jinja2 Tests
| Test | Description | Example |
|---|---|---|
| defined | Checks if a variable is defined | {{ var is defined }} |
| undefined | Checks if a variable is not defined | {{ var is undefined }} |
| even | Checks if a number is even | {{ 4 is even }} |
| odd | Checks if a number is odd | {{ 5 is odd }} |
| none | Checks if a variable is None | {{ var is none }} |
| string | Checks if a variable is a string | {{ var is string }} |
| number | Checks if a variable is a number | {{ var is number }} |
| boolean | Checks if a variable is a boolean | {{ var is boolean }} |
| iterable | Checks if a variable is iterable | {{ var is iterable }} |
| mapping | Checks if a variable is a mapping (dict-like) | {{ var is mapping }} |
Example: Using Jinja2 Tests in Conditionals
- name: Check if a variable is defined
debug:
msg: "Variable is defined"
when: "{{ var is defined }}"
- name: Check if a variable is a string
debug:
msg: "Variable is a string"
when: "{{ var is string }}"
- name: Check if a number is even
debug:
msg: "Number is even"
when: "{{ item is even }}"
with_items:
- 2
- 3
- 4
8. Evaluating Registered Results
| Variable | Description | Usage |
|---|---|---|
| ansible_facts | Facts gathered about the target host | Used to access system information like OS version, network interfaces, etc. |
| ansible_env | Environment variables on the target host | Access environment settings such as PATH, HOME, etc. |
| ansible_pkg_mgr | Package manager used on the target host | Determines whether yum, apt, or another package manager is in use |
Example: Using Registered Results in Conditionals
- name: Check if a package is installed
command: dpkg -l nginx
register: nginx_check
ignore_errors: true
- name: Notify if nginx is installed
debug:
msg: "Nginx is installed"
when: nginx_check.rc == 0
- name: Install nginx if not present
apt:
name: nginx
state: present
when: nginx_check.rc != 0
Note: The
rc field in registered results refers to the return code of the command executed. A return code of 0 typically indicates success.
Warning: When using
ignore_errors: true, ensure that your conditional logic properly evaluates the result to avoid unexpected behavior.
9. Checking File States
| State | Description | Usage | Notes |
|---|---|---|---|
| absent | Ensures the file or directory does not exist. | state: absent |
Deletes the file or directory if it exists. |
| file | Ensures the path is a file. | state: file |
Creates an empty file if it does not exist. |
| directory | Ensures the path is a directory. | state: directory |
Creates the directory if it does not exist. |
| hard | Ensures the path is a hard link to the specified file. | state: hard |
Creates a hard link if it does not exist. |
| link | Ensures the path is a symbolic link to the specified file. | state: link |
Creates a symbolic link if it does not exist. |
| touch | Ensures the file exists and updates its timestamp. | state: touch |
Creates the file if it does not exist. |
Example: Check File State
- name: Ensure file exists and is up to date
ansible.builtin.file:
path: /etc/myapp/config.ini
state: touch
mode: '0644'
Example: Delete a File if It Exists
- name: Remove a directory if it exists
ansible.builtin.file:
path: /var/log/myapp
state: absent
10. Using Complex Conditionals
| Operator | Description | Example |
|---|---|---|
| and | Logical AND operator | {{ item.value > 5 and item.value < 10 }} |
| or | Logical OR operator | {{ item.value == 5 or item.value == 10 }} |
| not | Logical NOT operator | {{ not item.value }} |
| | | Filter operator (used in Jinja2 templates) | {{ item.value | lower }} |
| == | Equality operator | {{ item.status == 'running' }} |
| != | Not equal operator | {{ item.status != 'stopped' }} |
| < | Less than operator | {{ item.cpu_usage < 80 }} |
| > | Greater than operator | {{ item.memory > 1024 }} |
| <= | Less than or equal operator | {{ item.count <= 10 }} |
| >= | Greater than or equal operator | {{ item.version >= '2.0' }} |
Example: Complex conditional in a task
- name: Check system status
command: uptime
register: result
when:
- result.rc == 0
- result.stdout | length > 0
- "'load average' in result.stdout"
Example: Using variables with complex conditionals
- name: Configure firewall rules
firewalld:
port: "{{ item.port }}"
protocol: "{{ item.protocol }}"
loop: "{{ firewall_rules }}"
when:
- item.enabled == true
- item.port is defined
- item.protocol in ['tcp', 'udp']
- item.priority <= 5
Note: Complex conditionals in Ansible can involve multiple operators and nested expressions. Use parentheses to group conditions for clarity.
11. Applying Conditionals to Blocks
| Property | Description | Example |
|---|---|---|
| when | Condition to evaluate for block execution | when: ansible_facts.os_family == 'RedHat' |
| loop | Loop over a list or set of items | loop: ['item1', 'item2'] |
Example: Conditional block with loop
- name: Install packages based on OS
yum:
name: "{{ item }}"
state: present
loop:
- httpd
- mod_ssl
when: ansible_facts.os_family == 'RedHat'
Note: The
when clause is evaluated for each item in the loop, allowing conditional execution per iteration.