node.jsarray-maparrayobject

How to category with properties array object into sub-array object recursively?


I have this map function parameterize with dataObj which is from database execution return.

function(dataObj){
   obj.gateways = dataObj.map((item) => ({
                    gw_name: item.gw_name.toUpperCase(),
                    pm_id: item.pm_uid,
                    pm_name: item.description.toUpperCase(),
                    pm_is_card: item.is_card_pmt ? true : false,
                    device_id: item.pd_uid,
                    device_name: item.pd_name,
                }));
   return obj;
} 

I need to transfer above function return arrayObject into something like this,

gateways: [          
          {
            gw_name: "GATEWAY_1",
            gw_methods: [
               {
                pm_id: "234567",
                pm_name: "DEBIT CARD",
                pm_is_card: true
               },
               {
                pm_id: "123456",
                pm_name: "CREDIT CARD",
                pm_is_card: true
               },
            ],
            gw_devices:[
               {
                device_id: 1234,
                device_name: "Device_1"
               },
               {
                device_id: 56789,
                device_name: "Device_2"
               }
            ]
          },
          {
            gw_name: "GATEWAY_2",
            gw_methods: [
               {
                pm_id: "098763",
                pm_name: "WEB",
                pm_is_card: false
               },
               {
                pm_id: "123456",
                pm_name: "CREDIT CARD",
                pm_is_card: true
               },
            ],
            gw_devices:[               
               {
                device_id: 56789,
                device_name: "Device_2"
               },
               {
                device_id: 8787,
                device_name: "Device_3"
               },
            ]
          },
        ]

I tried many ways, but there is no luck, any suggestion would be really appreciate it. Thanks!


Solution

  • Given the data looks like:

    const data = [
        {
            gw_name: "GATEWAY_1",
            pm_id: "234567",
            pm_name: "DEBIT CARD",
            pm_is_card: true,
        },
        {
            gw_name: "GATEWAY_1",
            pm_id: "123456",
            pm_name: "CREDIT CARD",
            pm_is_card: true,
        },
        {
            gw_name: "GATEWAY_2",
            pm_id: "098763",
            pm_name: "WEB",
            pm_is_card: false,
        },
        {
            gw_name: "GATEWAY_2",
            pm_id: "123456",
            pm_name: "CREDIT CARD",
            pm_is_card: true,
        },
    ];
    

    The following reduce will help you:

    const gateways = data.reduce((memo, item) => {
        let target = memo.find(({ gw_name }) => gw_name === item.gw_name);
        if (!target) {
            target = {
                gw_name: item.gw_name,
                gw_methods: [item],
            };
            return [...memo, target];
        }
        target.gw_methods = [...target.gw_methods, item];
        return memo;
    }, []);