I have a requirment of inverting an object keys & values. I have following type of data:
[
"elements": {
"title": "elem_1_6_title",
"sub_title": "elem_1_6_sub_title",
"media": "elem_1_6_media",
"button": "elem_1_6_button",
"give_us_call": "elem_1_6_give_us_call"
},
"elements": {
"title": "elem_1_6_title",
"sub_title": "elem_1_6_sub_title"
},
"elements": {}
]
Expected output:
[
"elements": {
"elem_1_6_title": "title",
"elem_1_6_sub_title": "sub_title",
"elem_1_6_media": "media",
"elem_1_6_button": "button",
"elem_1_6_give_us_call": "give_us_call"
},
"elements": {
"elem_1_6_title": "title",
"elem_1_6_sub_title": "sub_title"
},
"elements": {}
]
Pipeline:
[
{
"$addFields": {
"sec_elems_arr": {
"$objectToArray": "$elements"
}
}
},
{
"$unwind": {
"path": "$sec_elems_arr",
"preserveNullAndEmptyArrays": true
}
},
{
"$addFields": {
"section_elements": {
"$arrayToObject": [
[
{
"k": "$sec_elems_arr.v",
"v": "$sec_elems_arr.k"
}
]
]
}
}
}
]
The above pipeline throws error:
$arrayToObject requires an object keys of 'k' and 'v'. Found incorrect number of keys:0
because one of the above elements object have no key values. But this case can exist in the data. How can I achieve this using MongoDB aggregation pipeline?
CodePudding user response:
I think the problem is more about you are using the $arrayToObject
incorrectly. You can use it with $map
to correctly swap the k-v.
db.collection.aggregate([
{
$addFields: {
elements: {
"$objectToArray": "$elements"
}
}
},
{
"$addFields": {
"elements": {
"$arrayToObject": {
"$map": {
"input": "$elements",
"as": "e",
"in": {
k: "$$e.v",
v: "$$e.k"
}
}
}
}
}
}
])
Here is the Mongo playground for your reference.
CodePudding user response:
Note the answer above can be further optimized by calling $objectToArray
as the input to $map
. This saves a stage -- always a good thing.
db.collection.aggregate([
{
"$addFields": {
"elements": {
"$arrayToObject": {
"$map": {
"input": {"$objectToArray": "$elements"},
"as": "e",
"in": {
k: "$$e.v",
v: "$$e.k"
}
}
}
}
}
}
])