3
votes

I'm using MongoDB aggregation framework trying to transform each document:

{
  "all": [
    {
      "type": "A",
      "id": "1"
    },
    {
      "type": "A",
      "id": "1"
    },
    {
      "type": "B",
      "id": "2"
    },
    {
      "type": "A",
      "id": "3"
    }
  ]
}

into this:

{
  "unique_type_A": [ "3", "1" ]
}

(final result is a collection of n documents with unique_type_A field)

The calculation consists of returning in an array all the uniques types of entities of type A.

I got stuck with $group step, anyone knows how to do it?

1

1 Answers

2
votes

To apply this logic to each document, you can use the following;

db.collection.aggregate([
  {
    $unwind: "$all"
  },
  {
    $match: {
      "all.type": "A"
    }
  },
  {
    $group: {
      _id: {
        "type": "$all.type",
        "oldId": "$_id"
      },
      unique_type_A: {
        $addToSet: "$all.id"
      }
    }
  },
  {
    $project: {
      _id: 0
    }
  }
])

Where we first $unwind, to be able to filter and play with each member of all array. Then we just filter the non type:"A" members. The $group stage has the difference with a complex _id, where we utilize the _id of $unwind result, which refers back to the original document, so that we can group the results per original document. Collecting the id from all array with $addToSet to keep only unique values, and voilà!

And here is the result per document;

[
  {
    "unique_type_A": [
      "3",
      "1"
    ]
  },
  {
    "unique_type_A": [
      "4",
      "11",
      "5"
    ]
  }
]

Check the code interactively on Mongoplayground