🎯 Filtering Data in Ansible: selectattr and map(attribute)

When working with lists of dictionaries in Ansible, filtering and extracting specific values is a common requirement. Jinja2 provides two powerful filters to accomplish this:

  • selectattr → Filters the list based on a condition.
  • map(attribute) → Extracts a specific field from the filtered result.

In this article, you'll learn:

  • ✅ How to filter lists of dictionaries in Ansible using selectattr
  • ✅ How to extract specific values using map(attribute)
  • ✅ How to handle missing values safely using default()

---

📌 Understanding selectattr and map(attribute)

Before jumping into Ansible playbooks, let's break down these Jinja2 filters.

✅ selectattr('name', 'equalto', search_name')

  • Filters a list of dictionaries to select only the ones where name == search_name.

✅ map(attribute='folder')

  • Extracts the folder field from the filtered result.

✅ Example Syntax

``yaml

{{ variable | selectattr('name', 'equalto', search_name) | map(attribute='folder') | list }}

`

  • selectattr filters the list where name equals search_name.
  • map(attribute='folder') extracts only the folder values.
  • list ensures the result is returned as a list.

---

🔥 Example Use Case

Scenario

You have a list of users and their home directories (folder). You want to search for a specific user and get their folder path.

Example Data

`yaml

variable:

- name: alice

folder: /home/alice

- name: bob

folder: /home/bob

- name: charlie

folder: /home/charlie

`

Using selectattr and map(attribute) in Ansible

`yaml

  • name: Search for a name and get its folder

hosts: localhost

gather_facts: no

vars:

variable:

- name: alice

folder: /home/alice

- name: bob

folder: /home/bob

- name: charlie

folder: /home/charlie

search_name: alice

tasks:

- name: Get folder for a specific user

debug:

msg: "{{ variable | selectattr('name', 'equalto', search_name) | map(attribute='folder') | list }}"

`

---

🎯 Expected Output

When search_name: alice, the output will be:

`yaml

TASK [Get folder for a specific user] *

ok: [localhost] => {

"msg": [

"/home/alice"

]

}

`

When search_name: bob, the output will be:

`yaml

TASK [Get folder for a specific user] *

ok: [localhost] => {

"msg": [

"/home/bob"

]

}

`

---

🔹 Getting a Single Value Instead of a List

By default, the output is a list with one value. If you need only the string value, add .0:

`yaml

  • name: Get a single folder for a user

debug:

msg: "{{ (variable | selectattr('name', 'equalto', search_name) | map(attribute='folder') | list).0 }}"

`

📌 Expected Output

``yaml

TASK