tarun nt
tarun nt

Reputation: 33

how to flatten json file in nodejs using recursion

I have a very complex nested json file and i need to traverse it using recursion
what I need is

  1. assign the value of innermost value to its parent key
  2. remove the innermost key and value
  3. remove empty objects

I have tried many ways and I am new to javascript world and could not come up with the right solution. the json i have is nested as below

      {
         "Changes_Only": {
                "_text": "some value"
              },
              "Legal_Employee_Id": {},
            "EmployeeData": {
              "OBJECT_ACTION_ID": {
               "_text": "some value"
              },
              "Employee": {
                "PersonID": {
                  "_text": "some value"
                },
                "PersonID_OLD": {},
                "PersonNumber": {
                  "_text": "some value"
                },
                "PersonNumber_OLD": {},
                "StartDate": {
                  "_text": "some value"
                },
                "StartDate_OLD": {},
                "PersonType": {
                  "_text": "some value"
                },
                "PersonType_OLD": {},
                "DateofBirth": {
                  "_text": "some value"
                },
                "DateofBirth_OLD": {},
                "HireDate": {
                  "_text": "some value"
                },
                "HireDate_OLD": {},
                "WorkEmail": {
                  "_text": "some value"
                },
                "WorkEmail_OLD": {},
                "FirstName": {
                  "_text": "some value"
                },
                "FirstName_OLD": {},
                "LastName": {
                  "_text": "some value"
                },
                "LastName_OLD": {}
              },
              "NationalIDHT": {
                "NtionalIDData": {
                  "NationalIDValues": {
                    "NationalType": {
                      "_text": "some value"
                    },
                    "NationalIDNumber": {
                      "_text": "some value"
                    }
                  }
                }
              },
              "AssignmentHT": {
                "AssignmentData": {
                  "Assignment": {
                    "PersonNumber": {
                      "_text": "some value"
                    },
                    "PersonNumber_OLD": {},
                    "WorkerNumber": {
                      "_text": "some value"
                    },
                    "WorkerNumber_OLD": {},
                    "Gender": {
                      "_text": "some value"
                    },
                    "Gender_OLD": {},
                    "ActionName": {
                      "_text": "some value"
                    },
                    "ActionName_OLD": {},
                    "HourlySalaried": {
                      "_text": "some value"
                    },
                    "HourlySalaried_OLD": {},
                    "SalaryBasis": {
                      "_text": "some value"
                    },
                    "SalaryBasis_OLD": {},
                    "ManagerPersonNumber": {
                      "_text": "some value"
                    },
                    "ManagerPersonNumber_OLD": {},
                    "ManagerDisplayName": {
                      "_text": "some value"
                    },
                    "ManagerDisplayName_OLD": {},
                    "AssignmentCategory": {
                      "_text": "some value"
                    },
                    "AssignmentCategory_OLD": {},
                    "AsgState": {
                      "_text": "some value"
                    },
                    "AsgState_OLD": {},
                    "JobCode": {
                      "_text": "some value"
                    },
                    "JobCode_OLD": {},
                    "Desgination": {
                      "_text": "some value"
                    },
                    "Desgination_OLD": {},
                    "Grade": {
                      "_text": "some value"
                    },
                    "Grade_OLD": {},
                    "Levele-Grade": {
                      "_text": "some value"
                    },
                    "Levele-Grade_OLD": {},
                    "Department": {
                      "_text": "some value"
                    },
                    "Department_OLD": {},
                    "EmployeeType": {
                      "_text": "some value"
                    },
                    "EmployeeType_OLD": {},
                    "BusinessUnit": {
                      "_text":"some value"
                    },
                    "BusinessUnit_OLD": {},
                    "BaseLocation": {
                      "_text":"some value"
                    },
                    "BaseLocation_OLD": {},
                    "PhysicalWorkAddress": {
                      "_text":"some value"
                    }
                    }
                  }
                }
              }
            }

the json which i need as below also help me remove the empty objects

{
         "Changes_Only":  "some value",
          
            "EmployeeData": {
              "OBJECT_ACTION_ID":  "some value",
              "Employee": {
                "PersonID": "some value",
                "PersonNumber":  "some value",
                "StartDate":  "some value",
                "PersonType":  "some value",
                "DateofBirth":  "some value",
                "HireDate":  "some value",
                "WorkEmail":  "some value",
                "FirstName":  "some value",
                "LastName":  "some value"
              },
              "NationalIDHT": {
                "NtionalIDData": {
                  "NationalIDValues": {
                    "NationalType":  "some value",
                    "NationalIDNumber":  "some value"
                  }
                }
              },
              "AssignmentHT": {
                "AssignmentData": {
                  "Assignment": {
                    "PersonNumber": "some value",
                    "WorkerNumber": "some value",
                    "Gender":  "some value",
                    "ActionName": "some value",
                    "HourlySalaried": "some value",
                    "SalaryBasis": "some value",
                    "ManagerPersonNumber": "some value",
                    "ManagerDisplayName":  "some value",
                    "AssignmentCategory":  "some value",
                    "AsgState":  "some value",
                    "JobCode":  "some value",
                    "Desgination":  "some value",
                    "Grade":  "some value",
                    "Levele-Grade":  "some value",
                    "Department":  "some value",
                    "EmployeeType":  "some value",
                    "BusinessUnit":  "some value",
                    "BaseLocation":  "some value",
                    "PhysicalWorkAddress": "some value"
                    }
                  }
                }
              }
            }
         

Upvotes: 0

Views: 155

Answers (3)

vincent
vincent

Reputation: 2181

Here is an answer that doesn't rely on string manipulation and uses object-scan.

String manipulation has it's place, but here it could cause issues (i.e. pruning objects that become empty after their properties are pruned). So this answer should be preferred over those using string manipulation

// const objectScan = require('object-scan');

const input = {"Changes_Only":{"_text":"some value"},"Legal_Employee_Id":{},"EmployeeData":{"OBJECT_ACTION_ID":{"_text":"some value"},"Employee":{"PersonID":{"_text":"some value"},"PersonID_OLD":{},"PersonNumber":{"_text":"some value"},"PersonNumber_OLD":{},"StartDate":{"_text":"some value"},"StartDate_OLD":{},"PersonType":{"_text":"some value"},"PersonType_OLD":{},"DateofBirth":{"_text":"some value"},"DateofBirth_OLD":{},"HireDate":{"_text":"some value"},"HireDate_OLD":{},"WorkEmail":{"_text":"some value"},"WorkEmail_OLD":{},"FirstName":{"_text":"some value"},"FirstName_OLD":{},"LastName":{"_text":"some value"},"LastName_OLD":{}},"NationalIDHT":{"NtionalIDData":{"NationalIDValues":{"NationalType":{"_text":"some value"},"NationalIDNumber":{"_text":"some value"}}}},"AssignmentHT":{"AssignmentData":{"Assignment":{"PersonNumber":{"_text":"some value"},"PersonNumber_OLD":{},"WorkerNumber":{"_text":"some value"},"WorkerNumber_OLD":{},"Gender":{"_text":"some value"},"Gender_OLD":{},"ActionName":{"_text":"some value"},"ActionName_OLD":{},"HourlySalaried":{"_text":"some value"},"HourlySalaried_OLD":{},"SalaryBasis":{"_text":"some value"},"SalaryBasis_OLD":{},"ManagerPersonNumber":{"_text":"some value"},"ManagerPersonNumber_OLD":{},"ManagerDisplayName":{"_text":"some value"},"ManagerDisplayName_OLD":{},"AssignmentCategory":{"_text":"some value"},"AssignmentCategory_OLD":{},"AsgState":{"_text":"some value"},"AsgState_OLD":{},"JobCode":{"_text":"some value"},"JobCode_OLD":{},"Desgination":{"_text":"some value"},"Desgination_OLD":{},"Grade":{"_text":"some value"},"Grade_OLD":{},"Levele-Grade":{"_text":"some value"},"Levele-Grade_OLD":{},"Department":{"_text":"some value"},"Department_OLD":{},"EmployeeType":{"_text":"some value"},"EmployeeType_OLD":{},"BusinessUnit":{"_text":"some value"},"BusinessUnit_OLD":{},"BaseLocation":{"_text":"some value"},"BaseLocation_OLD":{},"PhysicalWorkAddress":{"_text":"some value"}}}}}};

const rewrite = (data) => {
  objectScan(['**'], {
    breakFn: ({ value, gparent, gproperty }) => {
      if (typeof value === 'string') {
        gparent[gproperty] = value;
      }
    },
    filterFn: ({ value, parent, property }) => {
      if (value instanceof Object && Object.keys(value).length === 0) {
        delete parent[property];
      }
    }
  })(data);
};

console.log(rewrite(input));
// => undefined
console.log(input);
/* => {
  Changes_Only: 'some value',
  EmployeeData: {
    OBJECT_ACTION_ID: 'some value',
    Employee: {
      PersonID: 'some value',
      PersonNumber: 'some value',
      StartDate: 'some value',
      PersonType: 'some value',
      DateofBirth: 'some value',
      HireDate: 'some value',
      WorkEmail: 'some value',
      FirstName: 'some value',
      LastName: 'some value'
    },
    NationalIDHT: {
      NtionalIDData: {
        NationalIDValues: {
          NationalType: 'some value',
          NationalIDNumber: 'some value'
        }
      }
    },
    AssignmentHT: {
      AssignmentData: {
        Assignment: {
          PersonNumber: 'some value',
          WorkerNumber: 'some value',
          Gender: 'some value',
          ActionName: 'some value',
          HourlySalaried: 'some value',
          SalaryBasis: 'some value',
          ManagerPersonNumber: 'some value',
          ManagerDisplayName: 'some value',
          AssignmentCategory: 'some value',
          AsgState: 'some value',
          JobCode: 'some value',
          Desgination: 'some value',
          Grade: 'some value',
          'Levele-Grade': 'some value',
          Department: 'some value',
          EmployeeType: 'some value',
          BusinessUnit: 'some value',
          BaseLocation: 'some value',
          PhysicalWorkAddress: 'some value'
        }
      }
    }
  }
}
*/
.as-console-wrapper {max-height: 100% !important; top: 0}
<script src="https://bundle.run/[email protected]"></script>

Disclaimer: I'm the author of object-scan

Upvotes: 0

Biswa Soren
Biswa Soren

Reputation: 325

Try this I am just correcting @Konstantin Pribluda

const r = { ...} // Input JSON
JSON.parse(JSON.stringify(r).replace(/{\s*"_text":\s*("[^"]*")\s*}/g, "$1").replace(/"[^"]*"\s*:\s*{},/g,""))

Second, replace for empty {}

Upvotes: 0

Konstantin Pribluda
Konstantin Pribluda

Reputation: 12367

Actually you do not need JSON parsing here - you may get away with regex. replacing {"_text": "some value"} with just "some value" will do the trick.

Like this:

str.replace(/{\s*"_text":\s*("[^"]*")\s*}/, "$1")

will take care of

"PersonNumber": { "_text": "some value" },

and

str.replace(/"[^"]*"\s*:\s*{},/,"")

will get rid of empty attributes

Upvotes: 1

Related Questions