Ansible - 根据仅在一台主机上的结果查找最大值和 运行 操作

Ansible - Find max value and run action based on a result only on one host

我有一组名为 "db" 的主机,其节点数可能会有所不同。每个节点都有一个整数事实 ("seqno")。

我需要在所有主机中比较这个事实并选择最大值,然后 运行 在一个(并且只有一个)具有这个最大值的主机上执行一些操作。如果多个节点具有相同的值,则应选择第一个节点。

我试过这种方法:

- name: find max seqno value
  set_fact: seqno_max={{ [hostvars[groups['db'][0]]['seqno'], hostvars[groups['db'][1]]['seqno']] | max }}

- name: find single hostname to use as a node with max seqno
  set_fact: seqno_max_host={{ hostvars[item]['inventory_hostname'] }}
  with_items: groups['db'][::-1] # reverse list. if two nodes have the same seqno, use first node as starting point.
  when: hostvars[item]['seqno'] == seqno_max

- name: Some actions based on a result of previous tasks
  action: # Run some actions
  when:  seqno_max_host == inventory_hostname

但由于某些原因 "max" 运算符总是 return 第二个值。此外,此方法仅在您具有任意指定数量的主机时才有效 - 我希望有一个适用于任意数量主机的解决方案。

编辑: 结果是 hostvars 将整数转换回字符串,因此对它们的比较给出了意想不到的结果。为 max 过滤器中的每个 hostvars 引用重新应用 int 过滤器有帮助。尽管如此,问题仍然存在如何修复上面的代码以使其适用于任意数量的主机 - 是否可以不编写自定义过滤器或创建临时模板?

我最终得到了一个不漂亮但有效的解决方案。

- shell: "if [ {{ hostvars[inventory_hostname]['seqno'] }} -lt {{ hostvars[item]['seqno'] }} ]; then echo {{ hostvars[item]['seqno'] }}; fi"
  with_items: groups['db']
  register: result_c

- set_fact: seqno_max={{ hostvars[inventory_hostname]['seqno'] }}
  when: result_c.results | map(attribute='stdout') | join('') == ""