Converting An array of object in to an object with different object and array

sorry for the title I don't even know how to explain this problem I'm having without showing it. so down below is the data I'm getting from the database


const data = [{
  "id": 1,
  "patientEmail": "[email protected]",
  "patientFirstname": "Port",
  "patientLastname": "Leipnik",
  "createdAt": "2021-03-13T20:29:24Z",
  "status": "COMPLETED"
}, {
  "id": 2,
  "patientEmail": "[email protected]",
  "patientFirstname": "Dorelia",
  "patientLastname": "Whye",
  "createdAt": "2020-09-04T09:46:42Z",
  "status": "PENDING"
}, {
  "id": 3,
  "patientEmail": "[email protected]",
  "patientFirstname": "Kerwin",
  "patientLastname": "MacMichael",
  "createdAt": "2021-05-29T08:38:39Z",
  "status": "PENDING"
}, {
  "id": 4,
  "patientEmail": "[email protected]",
  "patientFirstname": "Kristien",
  "patientLastname": "Garrand",
  "createdAt": "2021-04-18T22:22:19Z",
  "status": "UNCOMPLETED"
}, {
  "id": 5,
  "patientEmail": "[email protected]",
  "patientFirstname": "Orel",
  "patientLastname": "Gardiner",
  "createdAt": "2021-01-09T20:12:47Z",
  "status": "UNCOMPLETED"
}, {
  "id": 6,
  "patientEmail": "[email protected]",
  "patientFirstname": "Hortensia",
  "patientLastname": "Farreil",
  "createdAt": "2021-04-17T15:34:48Z",
  "status": "COMPLETED"
}, {
  "id": 7,
  "patientEmail": "[email protected]",
  "patientFirstname": "Kassandra",
  "patientLastname": "Keetley",
  "createdAt": "2020-07-19T11:44:19Z",
  "status": "COMPLETED"
}, {
  "id": 8,
  "patientEmail": "[email protected]",
  "patientFirstname": "Jorie",
  "patientLastname": "Janauschek",
  "createdAt": "2021-03-22T04:57:21Z",
  "status": "PENDING"
}, {
  "id": 9,
  "patientEmail": "[email protected]",
  "patientFirstname": "Mattias",
  "patientLastname": "Deporte",
  "createdAt": "2021-01-26T16:12:06Z",
  "status": "UNCOMPLETED"
}, {
  "id": 10,
  "patientEmail": "[email protected]",
  "patientFirstname": "Cal",
  "patientLastname": "Lerwill",
  "createdAt": "2021-02-04T06:07:47Z",
  "status": "UNCOMPLETED"
}, {
  "id": 11,
  "patientEmail": "[email protected]",
  "patientFirstname": "Euphemia",
  "patientLastname": "Gasparro",
  "createdAt": "2021-02-14T09:17:12Z",
  "status": "COMPLETED"
}, {
  "id": 12,
  "patientEmail": "[email protected]",
  "patientFirstname": "Andria",
  "patientLastname": "Mellodey",
  "createdAt": "2020-07-26T04:47:39Z",
  "status": "PENDING"
}, {
  "id": 13,
  "patientEmail": "[email protected]",
  "patientFirstname": "Kerwin",
  "patientLastname": "Ride",
  "createdAt": "2021-04-23T13:00:26Z",
  "status": "UNCOMPLETED"
}, {
  "id": 14,
  "patientEmail": "[email protected]",
  "patientFirstname": "Dodie",
  "patientLastname": "Shotton",
  "createdAt": "2021-04-16T20:18:49Z",
  "status": "PENDING"
}, {
  "id": 15,
  "patientEmail": "[email protected]",
  "patientFirstname": "Estrella",
  "patientLastname": "Myton",
  "createdAt": "2021-05-19T10:01:56Z",
  "status": "COMPLETED"
}, {
  "id": 16,
  "patientEmail": "[email protected]",
  "patientFirstname": "Rosabel",
  "patientLastname": "Riditch",
  "createdAt": "2020-11-06T00:04:51Z",
  "status": "PENDING"
}, {
  "id": 17,
  "patientEmail": "[email protected]",
  "patientFirstname": "Hatti",
  "patientLastname": "Rushford",
  "createdAt": "2020-11-25T11:35:25Z",
  "status": "COMPLETED"
}, {
  "id": 18,
  "patientEmail": "[email protected]",
  "patientFirstname": "Clemmie",
  "patientLastname": "Goldhill",
  "createdAt": "2020-11-07T19:15:11Z",
  "status": "PENDING"
}, {
  "id": 19,
  "patientEmail": "[email protected]",
  "patientFirstname": "Pattie",
  "patientLastname": "Coch",
  "createdAt": "2020-08-23T07:53:19Z",
  "status": "UNCOMPLETED"
}, {
  "id": 20,
  "patientEmail": "[email protected]",
  "patientFirstname": "Aline",
  "patientLastname": "Barnby",
  "createdAt": "2020-12-01T09:54:53Z",
  "status": "PENDING"
}]


I would like to run a function that will convert it to this:


const convertedData = {
    // labels are the createdAt months I will momentjs to pull that out
    labels: ["Jan", "Feb", "Mar", "Apr"],
    datasets: [
      {
        status: "COMPLETED",
        // data is an array of occurrence for each label
        // so this will be Jan -> 3, Feb -> 7 etc
        // for example they were 3 COMPLETED for Jan so the first element of the array will be 3 and
        // 7 for Feb etc...
        // so this goes for the all 3 statuses
        data: [3, 7, 4, 6],
      },
      {
        status: "UNCOMPLETED",
        data: [4, 3, 5, 2],
      },
      {
        status: "PENDING",
        data: [7, 2, 6, 8],
      },
    ],
  }

I have tried every possible solution I could think of and I tried some of that kinda work but they were long and I know there must be an easy solution for this. I'm trying to use the converted data on a chart.

Edit: createdAt was not formated the correct way wouldn't work with momentjs

Upvotes: 1

Views: 57

Answers (1)

Nitheesh
Nitheesh

Reputation: 19986

I have created a logic for grouping the same.

Steps followed.

  1. Find the unique set of values for status.
  2. Group the array with month and push the count of induvidual status into the array.

Please find the working sample below.

const data = [{
  "id": 1,
  "patientEmail": "[email protected]",
  "patientFirstname": "Port",
  "patientLastname": "Leipnik",
  "createdAt": "2021-03-13T20:29:24Z",
  "status": "COMPLETED"
}, {
  "id": 2,
  "patientEmail": "[email protected]",
  "patientFirstname": "Dorelia",
  "patientLastname": "Whye",
  "createdAt": "2020-09-04T09:46:42Z",
  "status": "PENDING"
}, {
  "id": 3,
  "patientEmail": "[email protected]",
  "patientFirstname": "Kerwin",
  "patientLastname": "MacMichael",
  "createdAt": "2021-05-29T08:38:39Z",
  "status": "PENDING"
}, {
  "id": 4,
  "patientEmail": "[email protected]",
  "patientFirstname": "Kristien",
  "patientLastname": "Garrand",
  "createdAt": "2021-04-18T22:22:19Z",
  "status": "UNCOMPLETED"
}, {
  "id": 5,
  "patientEmail": "[email protected]",
  "patientFirstname": "Orel",
  "patientLastname": "Gardiner",
  "createdAt": "2021-01-09T20:12:47Z",
  "status": "UNCOMPLETED"
}, {
  "id": 6,
  "patientEmail": "[email protected]",
  "patientFirstname": "Hortensia",
  "patientLastname": "Farreil",
  "createdAt": "2021-04-17T15:34:48Z",
  "status": "COMPLETED"
}, {
  "id": 7,
  "patientEmail": "[email protected]",
  "patientFirstname": "Kassandra",
  "patientLastname": "Keetley",
  "createdAt": "2020-07-19T11:44:19Z",
  "status": "COMPLETED"
}, {
  "id": 8,
  "patientEmail": "[email protected]",
  "patientFirstname": "Jorie",
  "patientLastname": "Janauschek",
  "createdAt": "2021-03-22T04:57:21Z",
  "status": "PENDING"
}, {
  "id": 9,
  "patientEmail": "[email protected]",
  "patientFirstname": "Mattias",
  "patientLastname": "Deporte",
  "createdAt": "2021-01-26T16:12:06Z",
  "status": "UNCOMPLETED"
}, {
  "id": 10,
  "patientEmail": "[email protected]",
  "patientFirstname": "Cal",
  "patientLastname": "Lerwill",
  "createdAt": "2021-02-04T06:07:47Z",
  "status": "UNCOMPLETED"
}, {
  "id": 11,
  "patientEmail": "[email protected]",
  "patientFirstname": "Euphemia",
  "patientLastname": "Gasparro",
  "createdAt": "2021-02-14T09:17:12Z",
  "status": "COMPLETED"
}, {
  "id": 12,
  "patientEmail": "[email protected]",
  "patientFirstname": "Andria",
  "patientLastname": "Mellodey",
  "createdAt": "2020-07-26T04:47:39Z",
  "status": "PENDING"
}, {
  "id": 13,
  "patientEmail": "[email protected]",
  "patientFirstname": "Kerwin",
  "patientLastname": "Ride",
  "createdAt": "2021-04-23T13:00:26Z",
  "status": "UNCOMPLETED"
}, {
  "id": 14,
  "patientEmail": "[email protected]",
  "patientFirstname": "Dodie",
  "patientLastname": "Shotton",
  "createdAt": "2021-04-16T20:18:49Z",
  "status": "PENDING"
}, {
  "id": 15,
  "patientEmail": "[email protected]",
  "patientFirstname": "Estrella",
  "patientLastname": "Myton",
  "createdAt": "2021-05-19T10:01:56Z",
  "status": "COMPLETED"
}, {
  "id": 16,
  "patientEmail": "[email protected]",
  "patientFirstname": "Rosabel",
  "patientLastname": "Riditch",
  "createdAt": "2020-11-06T00:04:51Z",
  "status": "PENDING"
}, {
  "id": 17,
  "patientEmail": "[email protected]",
  "patientFirstname": "Hatti",
  "patientLastname": "Rushford",
  "createdAt": "2020-11-25T11:35:25Z",
  "status": "COMPLETED"
}, {
  "id": 18,
  "patientEmail": "[email protected]",
  "patientFirstname": "Clemmie",
  "patientLastname": "Goldhill",
  "createdAt": "2020-11-07T19:15:11Z",
  "status": "PENDING"
}, {
  "id": 19,
  "patientEmail": "[email protected]",
  "patientFirstname": "Pattie",
  "patientLastname": "Coch",
  "createdAt": "2020-08-23T07:53:19Z",
  "status": "UNCOMPLETED"
}, {
  "id": 20,
  "patientEmail": "[email protected]",
  "patientFirstname": "Aline",
  "patientLastname": "Barnby",
  "createdAt": "2020-12-01T09:54:53Z",
  "status": "PENDING"
}];
const convertedData = {
  labels: [],
  datasets: [],
}
data.forEach((node) => {
  const month = moment(node.createdAt).format('MMM');
  node.month = month;
});
const uniqueStatus = findUnqueValues(data, 'status');
uniqueStatus.forEach(status => convertedData.datasets.push({
  status,
  data: [],
}))

data.forEach((node) => {
  if (convertedData.labels.indexOf(node.month) === -1) {
    convertedData.labels.push(node.month);
    // Pick up nodes Having same months
    const nodesWithSameMonth = data.filter((item) => item.month === node.month);
    convertedData.datasets.forEach(x => {
        // From the lst of nodes with same month filter out nodes with same status
        const y = nodesWithSameMonth.filter(z => z.status === x.status);
        x.data.push(y.length);
      });
  }
})
console.log(convertedData);

// Refer https://stackoverflow.com/questions/15125920/how-to-get-distinct-values-from-an-array-of-objects-in-javascript
function findUnqueValues(array, key) {
  var flags = [], output = [], l = array.length, i;
  for (i = 0; i < l; i++) {
    if (flags[array[i][key]]) continue;
    flags[array[i][key]] = true;
    output.push(array[i][key]);
  }
  return output;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/moment.js/2.18.0/moment.min.js"></script>

Upvotes: 1

Related Questions