Starting with an array similar to this:
const arr = [
{id: "id_0", owner: "owner_0", state: "accepted"},
{id: "id_1", owner: "owner_1", state: "denied"},
{id: "id_2", owner: "owner_1", state: "accepted"},
{id: "id_3", owner: "owner_1", state: "accepted"},
{id: "id_4", owner: "owner_2", state: "pending"},
]
I need to group the data by owner and format the ids. The ids need to be a comma separated string. The state data need not be returned.
const formattedArr = {
owner_0: {ids: "id_0"},
owner_1: {ids: "id_1, id_2, id_3"}
owner_2: {ids: "id_4"}
}
I've been using _.groupBy(arr, 'owner')
but not sure how to use a callback or some other map or reduce to format the ids and join them into a string.
Something along the lines of this but preferably using the least amount of loops:
_.chain(arr)
.groupBy('owner')
.reduce(group => {
//format the ids here
return *formatted ids*
}
.value()
CodePudding user response:
So, you actually don't need groupBy in this case. Reduce can easily solve your problem.
const result = arr.reduce((acc, { id, owner }) => {
if (!acc[owner]) {
acc[owner] = {ids: id};
return acc;
}
acc[owner].ids = `, ${id}`;
return acc;
}, {});
If you prefer lodash it would look almost the same.
_.reduce(arr, (acc, { id, owner }) => {
if (!acc[owner]) {
acc[owner] = {ids: id};
return acc;
}
acc[owner].ids = `, ${id}`;
return acc;
}, {});
Good luck.
CodePudding user response:
This should do the trick:
_.chain(arr)
.groupBy('owner')
.map(o => ({
owner: o[0].owner,
ids: o.reduce((acc, curr) => [...acc, curr.id], []).join(', ')
}))
.value();
JS Fiddle: https://jsfiddle.net/z3mks4n6/