在Ansible词典中查找重复项

时间:2018-09-08 23:06:10

标签: python ansible jinja2

我需要检查两个子词典中没有使用相同的端口。

my_dict:
  first:
    redis:
      port: 1234
  second:
    redis:
      port: 1235
  third:
    redis:
      port: 1234

在任务中,我可以使用以下内容:

- debug:
    msg: '{{ my_dict | dict2items | map(attribute="value.redis.port") | list }}'

这将返回:

['1234', '1235', '1234']

我需要的是一种仅过滤重复项的方法。所以我得到:

['1234', '1234']

退回。

基本上,我需要检查端口是否重复,是否应用了失败任务,该任务将检查并显示导致冲突的项目。

有什么想法吗?

2 个答案:

答案 0 :(得分:0)

@stacksonstacks链接到的过滤器在此特定情况下无济于事,因为端口的数量总是 相同,只是它们的数量发生了变化:set([1,2,2,2]) == set([1,2])始终为{{ 1}}

因此,我们真正想要的是对端口进行分组,并查找长度大于1的子代。然后,我们可以提取导致冲突的键的名称以进行报告他们。

True

答案 1 :(得分:0)

非常感谢您对Matthew的帮助!

我认为事实真是太丑陋了,所以我决定快速制作一个过滤器插件……或更重要的是,在mathstuff.py文件中添加一个内容。

添加:

def duplicate(a):
    if isinstance(a, collections.Hashable):
        c = set(a)
    else:
        s = {}
        c = []

        for x in a:
            if x not in s:
                s[x] = 1
            else:
                if s[x] == 1:
                    c.append(x)
                s[x] += 1
    return c

在文档的主体中,并添加:

'duplicate': duplicate,

进入:

class FilterModule(object):
    ''' Ansible math jinja2 filters '''

    def filters(self):
        filters = {

因此Jinja2了解过滤器。

我会在有空的时候提出请求请求,但是如果有人在此期间找到请求,或者如果您不想/不能更新Ansible,那么以下方法非常有用:

- debug:
    msg: '{{ my_dict | dict2items | map(attribute="value.redis.port") | list | duplicate }}'

返回:

['1234']

我已经对更大的样本进行了一些测试,并且按预期工作。

享受!