You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Ansible中匹配两个字典值并规范输出格式?

Ansible字典匹配结果格式优化问题

现有字典数据

small_d 字典

"small_d": {
    "cluster-c8836": [
        "aaaa-111",
        "bbbb-222",
        "cccc-222"
    ]
}

big_d 字典

"big_d": {
    "2cc5b2fbe6c6": [
        "dddd-asda",
        "aaaa-111",
        "ddd-2411",
        "bbbb-222",
        "dddd-76543",
        "cccc-222",
        "dddd-66666"
    ],
    "0a722267a5bd": [
        "dddd-2468"
    ]
}

需求说明

遍历small_d中的所有节点ID,检查每个节点是否存在于big_d的某个列表中,最终输出big_d的键及其对应的匹配节点列表,预期格式如下:

"2cc5b2fbe6c6": ["aaaa-111", "bbbb-222", "cccc-222"]

尝试的Jinja2模板代码

- name: try Jinja2 filtering
  set_fact:
    worth_a_try: |
      {% for cluster_id, node_ids in small_d.items() %}
      {% for node_id in node_ids %}
      {% for group_id, member_ids in big_d.items() %}
      {% if node_id in member_ids %}
        - {{group_id}}:
            {{node_id}}
      {% endif %}
      {% endfor %}
      {% endfor %}
      {% endfor %}
- debug: var=worth_a_try

当前输出结果

上述代码得到的输出为多个独立字典条目,不符合预期格式:

"worth_a_try|from_yaml": [
    {
        "2cc5b2fbe6c6": "aaaa-111"
    },
    {
        "2cc5b2fbe6c6": "bbbb-222"
    },
    {
        "2cc5b2fbe6c6": "cccc-222"
    }
]

优化方案

方案1:Jinja2构建字典后输出

通过初始化空字典,将匹配到的节点ID逐一添加到对应分组的列表中,最后统一输出完整字典:

- name: 生成匹配结果字典
  set_fact:
    matched_result: |
      {% set result = {} %}
      {% for _, node_ids in small_d.items() %}
        {% for node_id in node_ids %}
          {% for group_id, member_ids in big_d.items() %}
            {% if node_id in member_ids %}
              {% if group_id not in result %}
                {% set _ = result.__setitem__(group_id, []) %}
              {% endif %}
              {% set _ = result[group_id].append(node_id) %}
            {% endif %}
          {% endfor %}
        {% endfor %}
      {% endfor %}
      {{ result | to_nice_yaml }}
- debug:
    var: matched_result | from_yaml

方案2:使用Ansible过滤器实现(更简洁)

利用Ansible内置过滤器,通过字典推导式直接生成目标结果:

- name: 用过滤器生成匹配结果
  set_fact:
    matched_result: >-
      {{
        big_d | dict2items 
        | selectattr('value', 'intersect', small_d.values() | flatten) 
        | map('combine', {'value': item.value | intersect(small_d.values() | flatten)}) 
        | items2dict
      }}
- debug:
    var: matched_result

两种方案最终都能得到符合预期的输出格式:

"matched_result": {
    "2cc5b2fbe6c6": [
        "aaaa-111",
        "bbbb-222",
        "cccc-222"
    ]
}

内容的提问来源于stack exchange,提问作者piercjs

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.30 09:53:19