Карта вложенной коллекции в поиске - PullRequest
1 голос
/ 04 марта 2020

У меня есть две коллекции: предметы и комиссии.

// collection items
{
    _id: ObjectId("5d2b9e2da676e50cb9d061fe"),
    name: 'some name'
}

// collection commisions
{ 
    _id: ObjectId("5d2cb8ad7240251917b18c03"),
    items: [
        {
          item: ObjectId("5d2b9e2da676e50cb9d061fe")
        }
    ]
}

Теперь, используя агрегацию, мне нужно найти элементы с количеством транзакций (во сколько коммитов они появляются). Я пытаюсь с этим:

db.getCollection('items').aggregate([{
        $match: {
            _id: ObjectId("5d2b9e2da676e50cb9d061fe")
        }
    }, {
        $lookup: {
            from: 'commisions',
            let: {
                item: '$_id',
                items: {
                    $map: {
                        input: '$items',
                        as: 'i',
                        in: '$$i.item',
                    }
                }
            },
            pipeline: [{
                $match: {
                    $expr: {
                        $in: ['$item', '$items']
                    }
                }
            }],
            as: 'commisions'
        }
    },
    {
        $project: {
            commisions: 1,
            commisionsSize: { $size: '$commisions' }
    }
},
{
    $limit: 100
}
]) 

Но когда я пытаюсь выполнить этот запрос, я получаю:

"errmsg": "$ in требует массив в качестве второго аргумента, найдено: отсутствует "

Проблема в том, что commision.items не является плоским массивом, но вложен.

1 Ответ

1 голос
/ 04 марта 2020

Я думаю, что вы только что немного запутались с синтаксисом $lookup. В частности, переменная, которую вы определяете в части let, предположительно принадлежит текущей коллекции, а не коллекции, из которой вы собираетесь искать.

Попробуйте:

 db.getCollection('items').aggregate([
    {
        $match: {
            _id: ObjectId("5d2b9e2da676e50cb9d061fe")
        }
    },
    {
        $lookup: {
            from: 'commisions',
            let: {item: '$_id'},
            pipeline: [
                {
                    $match: {
                        $expr: {
                            $in: [
                                '$$item',
                                {
                                    $map: {
                                        input: '$items',
                                        as: 'i',
                                        in: '$$i.item',
                                    }
                                }
                            ]
                        }
                    }
                }],
            as: 'commisions'
        }
    },
    {
        $project: {
            commisions: 1,
            commisionsSize: {$size: '$commisions'}
        }
    },
    {
        $limit: 100
    }
]) 
...