Могу ли я объединить два запроса mongodb в один запрос, используя golang (mgo)?
Я использую golang
а также mgo
, mongodb version is 3.2.9
Например, у меня есть два документа в одной коллекции:
{"groupId" : 4, "name" : "email", "value" : "11@11.com"}
{"groupId" : 4,"name" : "phoneNumber","value" : "000000000"}
я знаю phoneNumber (value and name)
и мне нужно найти электронную почту (значение). Это может быть просто сделано в двух запросах: сначала по phoneNumber я нашел groupId, а затем по groupId я нашел электронную почту. Можно ли сделать это одним запросом (используя golang и mgo)?
1 ответ
Да, вам нужно запустить конвейер агрегации в форме:
var pipeline = [
{
"$group": {
"_id": "$groupId",
"entries": {
"$push": {
"name": "$name",
"value": "$value"
}
}
}
},
{
"$match": {
"entries.name" : "phoneNumber",
"entries.value" : "000000000"
}
},
{
"$project": {
"item": {
"$arrayElemAt": [
{
"$filter": {
"input": "$entries",
"as": "item",
"cond": { "$eq": [ "$$item.name", "email" ] }
}
}, 0
]
}
}
},
{
"$project": {
"_id": 0,
"email": "$item.value"
}
}
]);
db.collection.aggregate(pipeline);
Пример вывода
{ "email" : "11@11.com" }
из которых следует эквивалентное выражение mGo (не проверено):
pipeline := []bson.D{
bson.M{
"$group": bson.M{
"_id": "$groupId",
"entries": bson.M{
"$push": bson.M{
"name": "$name",
"value": "$value"
}
}
}
},
bson.M{
"$match": bson.M{
"entries.name" : "phoneNumber",
"entries.value" : "000000000"
}
},
bson.M{
"$project": bson.M{
"item": bson.M{
"$arrayElemAt": [
bson.M{
"$filter": bson.M{
"input": "$entries",
"as": "item",
"cond": bson.M{ "$eq":
[]interface{}{ "$$item.name", "email" }
}
}
}, 0
]
}
}
},
bson.M{
"$project": bson.M{
"_id": 0,
"email": "$item.value"
}
}
}
pipe := collection.Pipe(pipeline)
iter := pipe.Iter()