Search code examples
javascriptnode.jsnodes

delete the JSON object from one json object by comparing the id from another json object if id is not present in javascript/ node js


let data = getData();
let anotherObj = getAnotherObj();

let res = data.reduce((acc, curr) => {
  if (!acc[curr.system.name]) {
    acc[curr.system.name] = {};
  }

  let detailsObj = {};
  Object.keys(curr.DataDetails).forEach(key => {
    let values = curr.DataDetails[key];

    // special handling to flatten single attribute objects
    if (values.length === undefined || values.length === 0) {
      let keys = Object.keys(values);
      if (keys.length == 1 && typeof values[keys[0]] !== 'object') {
        detailsObj[key] = values[keys[0]];
        return;
      }
    }

    // clone values to output
    detailsObj[key] = !Array.isArray(values) ? Object.assign({}, values) : [...values];

    // find and replace ids
    let ids = jsonpath.query(detailsObj[key], '$..id');
    ids.forEach((id, i) => {
      if (id in anotherObj) {
        if (Array.isArray(detailsObj[key]))
          detailsObj[key].splice(i, 1, anotherObj[id]);
        else
          detailsObj[key] = anotherObj[id];
      }
    });
  });

  acc[curr.system.name][curr.system.id] = {
    title: curr.system.id,
    uid: curr.system.id,
    url: `/${curr.system.name}/${curr.system.id}`,
    ...detailsObj,
  };
  return acc;
}, {});

document.body.insertAdjacentHTML('beforeend', `<pre>${JSON.stringify(res, undefined, 1)}</pre>`);
console.log(res);



function getData() {
  return [{
      system: {
        id: "4gSSbjCFEorYXqrgDIP2FA",
        type: "Entry",
        name: "User"
      },
      DataDetails: {
        shortOption: {
          "en-us": "some value"
        },
        mediaFile: [{
            sys: {
              type: "Link",
              link: "Asset",
              id: "7kRzyt4PFo",
            },
          },
          {
            sys: {
              type: "Link",
              link: "Asset",
              id: "2OspeCtNK0s",
            },
          },
        ],
        mediaGalary: [{
            sys: {
              type: "Link",
              link: "Asset",
              id: "gHcw3Z1Ko",
            },
          },
          {
            sys: {
              type: "Link",
              linkType: "Asset",
              id: "h2cPiuU9jIz",
            },
          },
        ],
        
      },
    },
    {
      system: {
        id: "1aBOO8tu3lUsjtICuIbUM5",
        type: "Entry",
        name: "User"
      },
      DataDetails: {
        short: {
          "en-us": "details of shorts"
        },
        shortSlugOption: {
          "hi-In": "options"
        },
        booleanField: {
          kl: "true"
        },
      },
    },
    {
      system: {
        id: "2pOUGnI1oRD7nsrYs600HA",
        type: "Entry",
        name: "Dummy"
      },
      DataDetails: {
        testingNewValue: [{
            sys: {
              type: "Link",
              link: "Entry",
              id: "66rzYr2BpWL",
            },
          },
          {
            sys: {
              type: "Link",
              link: "Entry",
              id: "1VTBHdLTdSW",
            },
          },
        ],
      },
    },
    {
      system: {
        id: "66rzYr2BpWL1VTBHdLTdSW",
        type: "Entry",
        name: "new"
      },
      DataDetails: {
        oneReference: {
          sys: {
            type: "Link",
            linkType: "Asset",
            id: "h2cPiuU9jIz",
          },
        },
        multiReference: [{
            sys: {
              type: "Link",
              link: "Asset",
              id: "gHcw3Z1Ko",
            },
          },
          {
            sys: {
              type: "Link",
              link: "Asset",
              id: "h2cPiuU9jIz",
            },
          },
        ],
      },
    },
    {
      system: {
        id: "cIb5mqEBRWDD6hrNmFmFE",
        type: "Entry",
        name: "new"
      },
      DataDetails: {
        testingNewValue: {
          "hi-IN": "jksdsdo"
        }
      },
    },
    {
      system: {
        id: "7kRzyt4PFrX13gHcw3Z1Ko",
        type: "Entry",
        name: "Dummy"
      },
      DataDetails: {
        testingNewValue: {
          "en-us": "kknksdo"
        }
      },
    }
  ];
}


function getAnotherObj() {
  return {
    "h2cPiuU9jIz": {
      status: true,
      tag: [],
      filename: "wallpapers-6.jpg",
      is_dir: false,
      parent_uid: null,
    },
    
    
    "2OspeCtNK0s": {
      status: true,
      tag: [],
      filename: "mediaFile1.jpg",
      is_dir: false,
      parent_uid: null,
    },
    "66rzYr2BpWL": {
      type: 'entry',
      tag: [],
      entry_details: "this is first entry ***",
      is_secret: false,
    },
    "1VTBHdLTdSW": {
      type: 'entry',
      tag: [],
      entry_details: "some other entry ***",
      is_secret: true,
    },
  };
}
<script src="https://cdn.jsdelivr.net/npm/[email protected]/jsonpath.min.js"></script>

I am trying to put two object data in one output but by reading the link which is Asset

but in the multiple Array list the output is displaying as I want but the problem is while comparing the output from the anotherObj if the Id with that Obj is present it showing me the expected value which is data Asset replaced by the anotherObj

But I want to remove the value which is not matched with the object which are present inside the anotherObj

for eg:-

"mediaGalary": [
        {
          "sys": {
            "type": "Link",
            "link": "Asset",
            "id": "gHcw3Z1Ko"
          }
        },
        {
          /**id:c**/
          "status": true,
          "tag": [],
          "filename": "wallpapers-6.jpg",
          "is_dir": false,
          "parent_uid": null
        }
      ]

and

"mediaFile": [
    {
     "sys": {
      "type": "Link",
      "link": "Asset",
      "id": "7kRzyt4PFo"
     }
    },
    {
     "status": true,
     "tag": [],
     "filename": "mediaFile1.jpg",
     "is_dir": false,
     "parent_uid": null
    }
   ]

look like this here "id": "gHcw3Z1Ko" is not present inside the anotherObj so I want to remove all the object with that id

    {
     "sys": {
      "type": "Link",
      "link": "Asset",
      "id": "7kRzyt4PFo"
     }
    }

and

    {
     "sys": {
      "type": "Link",
      "link": "Asset",
      "id": "7kRzyt4PFo"
     }

as this id object is not present so I want to remove it and I wanted my expected output be like this it should only remove the Object which is not present inside the anotherObj

"mediaGalary": [
        {
          /**id:c**/
          "status": true,
          "tag": [],
          "filename": "wallpapers-6.jpg",
          "is_dir": false,
          "parent_uid": null
        }
      ]
and


"mediaFile": [
    {
     "status": true,
     "tag": [],
     "filename": "mediaFile1.jpg",
     "is_dir": false,
     "parent_uid": null
    }
   ]

Solution

  • After we are done replacing items in data, whichever items remain with property id are not replaced, hence they are not in anotherObj.
    So we can find them and remove them like this:

    // find items with `id` proerty
    let objs = jsonpath.nodes(acc, '$..[?(@.sys.id)]');
    
    // delete the items
    objs.forEach(function(node) {
      let key = node.path.pop();
      let parent = jsonpath.value(acc, jsonpath.stringify(node.path));
      if (Array.isArray(parent))
        parent.splice(key, 1);
      else
        delete parent[key];
    }, this);
    

    Demo:

    let data = getData();
    let anotherObj = getAnotherObj();
    
    let res = data.reduce((acc, curr) => {
      if (!acc[curr.system.name]) {
        acc[curr.system.name] = {};
      }
    
      let detailsObj = {};
      Object.keys(curr.DataDetails).forEach(key => {
        let values = curr.DataDetails[key];
    
        // special handling to flatten single attribute objects
        if (values.length === undefined || values.length === 0) {
          let keys = Object.keys(values);
          if (keys.length == 1 && typeof values[keys[0]] !== 'object') {
            detailsObj[key] = values[keys[0]];
            return;
          }
        }
    
        // clone values to output
        detailsObj[key] = !Array.isArray(values) ? Object.assign({}, values) : [...values];
    
        // find and replace ids
        let ids = jsonpath.query(detailsObj[key], '$..id');
        ids.forEach((id, i) => {
          if (id in anotherObj) {
            if (Array.isArray(detailsObj[key]))
              detailsObj[key].splice(i, 1, anotherObj[id]);
            else
              detailsObj[key] = anotherObj[id];
          }
        });
      });
    
      acc[curr.system.name][curr.system.id] = {
        title: curr.system.id,
        uid: curr.system.id,
        url: `/${curr.system.name}/${curr.system.id}`,
        ...detailsObj,
      };
    
      // find items which were not replaced
      let objs = jsonpath.nodes(acc, '$..[?(@.sys.id)]');
    
      // delete the items
      objs.forEach(function(node) {
        let key = node.path.pop();
        let parent = jsonpath.value(acc, jsonpath.stringify(node.path));
        if (Array.isArray(parent))
          parent.splice(key, 1);
        else
          delete parent[key];
      }, this);
    
      return acc;
    }, {});
    
    
    
    document.body.insertAdjacentHTML('beforeend', `<pre>${JSON.stringify(res, undefined, 1)}</pre>`);
    console.log(res);
    
    function getData() {
      return [{
          system: {
            id: "4gSSbjCFEorYXqrgDIP2FA",
            type: "Entry",
            name: "User"
          },
          DataDetails: {
            shortOption: {
              "en-us": "some value"
            },
            mediaFile: [{
                sys: {
                  type: "Link",
                  link: "Asset",
                  id: "7kRzyt4PFo",
                },
              },
              {
                sys: {
                  type: "Link",
                  link: "Asset",
                  id: "2OspeCtNK0s",
                },
              },
            ],
            mediaGalary: [{
                sys: {
                  type: "Link",
                  link: "Asset",
                  id: "gHcw3Z1Ko",
                },
              },
              {
                sys: {
                  type: "Link",
                  linkType: "Asset",
                  id: "h2cPiuU9jIz",
                },
              },
            ],
    
          },
        },
        {
          system: {
            id: "1aBOO8tu3lUsjtICuIbUM5",
            type: "Entry",
            name: "User"
          },
          DataDetails: {
            short: {
              "en-us": "details of shorts"
            },
            shortSlugOption: {
              "hi-In": "options"
            },
            booleanField: {
              kl: "true"
            },
          },
        },
        {
          system: {
            id: "2pOUGnI1oRD7nsrYs600HA",
            type: "Entry",
            name: "Dummy"
          },
          DataDetails: {
            testingNewValue: [{
                sys: {
                  type: "Link",
                  link: "Entry",
                  id: "66rzYr2BpWL",
                },
              },
              {
                sys: {
                  type: "Link",
                  link: "Entry",
                  id: "1VTBHdLTdSW",
                },
              },
            ],
          },
        },
        {
          system: {
            id: "66rzYr2BpWL1VTBHdLTdSW",
            type: "Entry",
            name: "new"
          },
          DataDetails: {
            oneReference: {
              sys: {
                type: "Link",
                linkType: "Asset",
                id: "h2cPiuU9jIz",
              },
            },
            multiReference: [{
                sys: {
                  type: "Link",
                  link: "Asset",
                  id: "gHcw3Z1Ko",
                },
              },
              {
                sys: {
                  type: "Link",
                  link: "Asset",
                  id: "h2cPiuU9jIz",
                },
              },
            ],
          },
        },
        {
          system: {
            id: "cIb5mqEBRWDD6hrNmFmFE",
            type: "Entry",
            name: "new"
          },
          DataDetails: {
            testingNewValue: {
              "hi-IN": "jksdsdo"
            }
          },
        },
        {
          system: {
            id: "7kRzyt4PFrX13gHcw3Z1Ko",
            type: "Entry",
            name: "Dummy"
          },
          DataDetails: {
            testingNewValue: {
              "en-us": "kknksdo"
            }
          },
        }
      ];
    }
    
    
    function getAnotherObj() {
      return {
        "h2cPiuU9jIz": {
          status: true,
          tag: [],
          filename: "wallpapers-6.jpg",
          is_dir: false,
          parent_uid: null,
        },
    
    
        "2OspeCtNK0s": {
          status: true,
          tag: [],
          filename: "mediaFile1.jpg",
          is_dir: false,
          parent_uid: null,
        },
        "66rzYr2BpWL": {
          type: 'entry',
          tag: [],
          entry_details: "this is first entry ***",
          is_secret: false,
        },
        "1VTBHdLTdSW": {
          type: 'entry',
          tag: [],
          entry_details: "some other entry ***",
          is_secret: true,
        },
      };
    }
    <script src="https://cdn.jsdelivr.net/npm/[email protected]/jsonpath.min.js"></script>