Compare two json output and merge based on one of the key

Issue

json output1:

    {
        "VMID": "7283949-4658-3i93899-2bb1-36748",
        "VMName": "terra01-dc-domain"
    },
    {
        "VMID": "833bjhds949-42658-3idbj46-2bb1-33bsj",
        "VMName": "terra02-dc-domain"
    }

json output2:

    {
        "GroupName": "default.DC2-external-msw",
        "GRP_Members": [
            7283949-4658-3i93899-2bb1-36748 
        ]
    },
    {
        "GroupName": "default.DC2-external-msw-svr2016-dns",
        "GRP_Members": [
            833bjhds949-42658-3idbj46-2bb1-33bsj
         ]
    },

by taking "VMID" from output1, search in output2 and replace it in output2.

Output Required:

   {
        "GroupName": "default.DC2-external-msw",
        "GRP_Members": [
            terra01-dc-domain 
        ]
    },
    {
        "GroupName": "default.DC2-external-msw-svr2016-dns",
        "GRP_Members": [
            terra01-dc-domain
         ]
    },

pls advise, thanks in advance

Solution

Given the data

    output1:
      - VMID: 7283949-4658-3i93899-2bb1-36748
        VMName: terra01-dc-domain
      - VMID: 833bjhds949-42658-3idbj46-2bb1-33bsj
        VMName: terra02-dc-domain
    output2:
      - GroupName: default.DC2-external-msw
        GRP_Members:
          - 7283949-4658-3i93899-2bb1-36748 
      - GroupName: default.DC2-external-msw-svr2016-dns
        GRP_Members:
          - 833bjhds949-42658-3idbj46-2bb1-33bsj

Create a dictionary from output1

output1_dict: "{{ output1|items2dict(key_name='VMID', value_name='VMName') }}"

gives

output1_dict:
  7283949-4658-3i93899-2bb1-36748: terra01-dc-domain
  833bjhds949-42658-3idbj46-2bb1-33bsj: terra02-dc-domain

Then iterate output2 and replace VMID in the lists with VMName

    - set_fact:
        output: "{{ output|d([]) + [_item] }}"
      loop: "{{ output2 }}"
      vars:
        _members: "{{ item.GRP_Members|map('extract', output1_dict)|list }}"
        _item: "{{ item|combine({'GRP_Members': _members}) }}"

gives

output:
  - GRP_Members:
    - terra01-dc-domain
    GroupName: default.DC2-external-msw
  - GRP_Members:
    - terra02-dc-domain
    GroupName: default.DC2-external-msw-svr2016-dns

Example of a complete playbook

- hosts: localhost
  vars:
    output1:
      - VMID: 7283949-4658-3i93899-2bb1-36748
        VMName: terra01-dc-domain
      - VMID: 833bjhds949-42658-3idbj46-2bb1-33bsj
        VMName: terra02-dc-domain
    output2:
      - GroupName: default.DC2-external-msw
        GRP_Members:
          - 7283949-4658-3i93899-2bb1-36748 
      - GroupName: default.DC2-external-msw-svr2016-dns
        GRP_Members:
          - 833bjhds949-42658-3idbj46-2bb1-33bsj
    output1_dict: "{{ output1|items2dict(key_name='VMID', value_name='VMName') }}"
  tasks:
    - set_fact:
        output: "{{ output|d([]) + [_item] }}"
      loop: "{{ output2 }}"
      vars:
        _members: "{{ item.GRP_Members|map('extract', output1_dict)|list }}"
        _item: "{{ item|combine({'GRP_Members': _members}) }}"
    - debug:
        var: output

Answered By – Vladimir Botka

This Answer collected from stackoverflow, is licensed under cc by-sa 2.5 , cc by-sa 3.0 and cc by-sa 4.0

Leave a Reply

(*) Required, Your email will not be published