Reputation: 7080
I have array of objects
{
"work": [{
"_id": "5c80c5c00c253823fc443337",
"start": "2019-01-01T18:30:00.000Z",
"end": "2019-01-02T18:30:00.000Z",
"employee": {
"_id": "5c80c16e0c253823fc44332a",
"status": "active",
"location": "Chennai",
"contact_number": "1234567890"
},
"allocation": 30
},
{
"_id": "5c80c5ef0c253823fc443339",
"start": "2018-12-31T18:30:00.000Z",
"end": "2019-09-30T18:30:00.000Z",
"employee": {
"_id": "5c80c16e0c253823fc44332a",
"status": "active",
"location": "Chennai",
"contact_number": "1234567890"
},
"allocation": 100
},
{
"_id": "5c80c60b0c253823fc44333a",
"start": "2018-12-31T18:30:00.000Z",
"end": "2020-10-07T18:30:00.000Z",
"employee": {
"_id": "5c80c16e0c253823fc44332a",
"status": "active",
"location": "Chennai",
"contact_number": "1234567890"
},
"allocation": 25
},
{
"_id": "5c80c65e0c253823fc44333b",
"start": "2019-01-01T18:30:00.000Z",
"end": "2019-10-04T18:30:00.000Z",
"employee": {
"_id": "5c80c1940c253823fc44332b",
"status": "active",
"location": "Chennai",
"contact_number": "1234567890"
},
"allocation": 50
},
{
"_id": "5c80c7240c253823fc44333f",
"start": "2018-12-31T18:30:00.000Z",
"end": "2019-10-09T18:30:00.000Z",
"employee": {
"_id": "5c80c26e0c253823fc44332e",
"status": "active",
"location": "Chennai",
"contact_number": "1234567890"
},
"allocation": 25
}
]
}
I need to convert them into
[{
"_id": "5c80c16e0c253823fc44332a",
"status": "active",
"location": "Chennai",
"contact_number": "1234567890",
"work": [{
"_id": "5c80c5c00c253823fc443337",
"start": "2019-01-01T18:30:00.000Z",
"end": "2019-01-02T18:30:00.000Z",
"allocation": 30
}, {
"_id": "5c80c5ef0c253823fc443339",
"start": "2018-12-31T18:30:00.000Z",
"end": "2019-09-30T18:30:00.000Z",
"allocation": 100
}, {
"_id": "5c80c60b0c253823fc44333a",
"start": "2018-12-31T18:30:00.000Z",
"end": "2020-10-07T18:30:00.000Z",
"allocation": 25
}]
}, {
"_id": "5c80c1940c253823fc44332b",
"status": "active",
"location": "Chennai",
"contact_number": "1234567890",
"work": [{
"_id": "5c80c65e0c253823fc44333b",
"start": "2019-01-01T18:30:00.000Z",
"end": "2019-10-04T18:30:00.000Z",
"allocation": 50
}]
}, {
"_id": "5c80c26e0c253823fc44332e",
"status": "active",
"location": "Chennai",
"contact_number": "1234567890",
"work": [{
"_id": "5c80c7240c253823fc44333f",
"start": "2018-12-31T18:30:00.000Z",
"end": "2019-10-09T18:30:00.000Z",
"allocation": 25
}]
}]
I have done it by partially using lodash and vanilla js and it works completely fine. but readability wise is completely bad. I want to achieve this using just lodash alone. Any help?
let ids: any = groupBy(this.project.work, function (res) {
return res.employee._id;
});
for (let id in ids) {
let tmp = [];
let employee_added = false;
ids[id].map((work) => {
if (!employee_added) {
tmp = work.employee;
tmp['work'] = [];
employee_added = true;
}
delete work.employee;
tmp['work'].push(work);
})
this.employees.push(tmp);
}
console.log(this.employees);
Upvotes: 4
Views: 7873
Reputation: 4175
Hopefully, this is what you are looking for.
employee_.id
work
(everything apart from employee object)Here is the example below:
let works = [{"_id":"5c80c5c00c253823fc443337","start":"2019-01-01T18:30:00.000Z","end":"2019-01-02T18:30:00.000Z","employee":{"_id":"5c80c16e0c253823fc44332a","status":"active","location":"Chennai","contact_number":"1234567890"},"allocation":30},{"_id":"5c80c5ef0c253823fc443339","start":"2018-12-31T18:30:00.000Z","end":"2019-09-30T18:30:00.000Z","employee":{"_id":"5c80c16e0c253823fc44332a","status":"active","location":"Chennai","contact_number":"1234567890"},"allocation":100},{"_id":"5c80c60b0c253823fc44333a","start":"2018-12-31T18:30:00.000Z","end":"2020-10-07T18:30:00.000Z","employee":{"_id":"5c80c16e0c253823fc44332a","status":"active","location":"Chennai","contact_number":"1234567890"},"allocation":25},{"_id":"5c80c65e0c253823fc44333b","start":"2019-01-01T18:30:00.000Z","end":"2019-10-04T18:30:00.000Z","employee":{"_id":"5c80c1940c253823fc44332b","status":"active","location":"Chennai","contact_number":"1234567890"},"allocation":50},{"_id":"5c80c7240c253823fc44333f","start":"2018-12-31T18:30:00.000Z","end":"2019-10-09T18:30:00.000Z","employee":{"_id":"5c80c26e0c253823fc44332e","status":"active","location":"Chennai","contact_number":"1234567890"},"allocation":25}]
let res = _(works)
.groupBy('employee._id')
.map(g => ({...g[0].employee, work: _.map(g, ({employee, ...rest}) => ({...rest}))}))
.value();
console.log(res)
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.11/lodash.min.js"></script>
Upvotes: 3
Reputation: 193358
You can create a function that uses lodash's _.flow()
that groups by the employee id, and then creates an employee object with work array:
const { flow, partialRight: pr, groupBy, map, head, get, omit } = _
const fn = flow(
pr(groupBy, 'employee._id'),
pr(map, group => ({ // create the employee objects
...get(head(group), 'employee'), // get the employee data and spread it
work: group.map(o => omit(o, 'employee')) // create the work array by removing the employee from each work object
}))
)
const data = {"work":[{"_id":"5c80c5c00c253823fc443337","start":"2019-01-01T18:30:00.000Z","end":"2019-01-02T18:30:00.000Z","employee":{"_id":"5c80c16e0c253823fc44332a","status":"active","location":"Chennai","contact_number":"1234567890"},"allocation":30},{"_id":"5c80c5ef0c253823fc443339","start":"2018-12-31T18:30:00.000Z","end":"2019-09-30T18:30:00.000Z","employee":{"_id":"5c80c16e0c253823fc44332a","status":"active","location":"Chennai","contact_number":"1234567890"},"allocation":100},{"_id":"5c80c60b0c253823fc44333a","start":"2018-12-31T18:30:00.000Z","end":"2020-10-07T18:30:00.000Z","employee":{"_id":"5c80c16e0c253823fc44332a","status":"active","location":"Chennai","contact_number":"1234567890"},"allocation":25},{"_id":"5c80c65e0c253823fc44333b","start":"2019-01-01T18:30:00.000Z","end":"2019-10-04T18:30:00.000Z","employee":{"_id":"5c80c1940c253823fc44332b","status":"active","location":"Chennai","contact_number":"1234567890"},"allocation":50},{"_id":"5c80c7240c253823fc44333f","start":"2018-12-31T18:30:00.000Z","end":"2019-10-09T18:30:00.000Z","employee":{"_id":"5c80c26e0c253823fc44332e","status":"active","location":"Chennai","contact_number":"1234567890"},"allocation":25}]}
const result = fn(data.work)
console.log(result)
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.11/lodash.js"></script>
Upvotes: 2
Reputation: 13993
You can do it succinctly using plain JavaScript with Object.values()
, Array.reduce()
and desctructuring assignment:
const data = {"work":[{"_id":"5c80c5c00c253823fc443337","start":"2019-01-01T18:30:00.000Z","end":"2019-01-02T18:30:00.000Z","employee":{"_id":"5c80c16e0c253823fc44332a","status":"active","location":"Chennai","contact_number":"1234567890"},"allocation":30},{"_id":"5c80c5ef0c253823fc443339","start":"2018-12-31T18:30:00.000Z","end":"2019-09-30T18:30:00.000Z","employee":{"_id":"5c80c16e0c253823fc44332a","status":"active","location":"Chennai","contact_number":"1234567890"},"allocation":100},{"_id":"5c80c60b0c253823fc44333a","start":"2018-12-31T18:30:00.000Z","end":"2020-10-07T18:30:00.000Z","employee":{"_id":"5c80c16e0c253823fc44332a","status":"active","location":"Chennai","contact_number":"1234567890"},"allocation":25},{"_id":"5c80c65e0c253823fc44333b","start":"2019-01-01T18:30:00.000Z","end":"2019-10-04T18:30:00.000Z","employee":{"_id":"5c80c1940c253823fc44332b","status":"active","location":"Chennai","contact_number":"1234567890"},"allocation":50},{"_id":"5c80c7240c253823fc44333f","start":"2018-12-31T18:30:00.000Z","end":"2019-10-09T18:30:00.000Z","employee":{"_id":"5c80c26e0c253823fc44332e","status":"active","location":"Chennai","contact_number":"1234567890"},"allocation":25}]};
const result = Object.values(data.work.reduce((acc, work) => {
const { employee: { _id, ...rest }, ...job } = work;
const jobs = (acc[_id] || {}).work || [];
acc[_id] = { _id, ...rest, work: [...jobs, job] };
return acc;
}, {}));
console.log(result);
Upvotes: 1