mongodb $ lookup + regex

时间:2017-01-11 22:46:51

标签: c# mongodb mongodb-query mongodb-.net-driver

Mongo用户,我遇到了问题,感谢您的帮助。

我有三个mongo集合,其行为类似于关系数据库表:

contacts_collecion

{
    "_id" : ObjectId("..."),
    "cid" : "1",
    "email" : "a1@a.aaa"
}
{
    "_id" : ObjectId("..."),
    "cid" : "2",
    "email" : "a2@a.aaa"
}
{
    "_id" : ObjectId("..."),
    "cid" : "3",
    "email" : "a3@a.aaa"
}

groups_collection

{
    "_id" : ObjectId("..."),
    "gid" : "1",
    "group_name" : "group1"
}
{
    "_id" : ObjectId("..."),
    "gid" : "1",
    "group_name" : "group2"
}

contacts_groups_collection

{
    "_id" : ObjectId("..."),
    "cid" : "2",
    "gid" : "1"
}
{
    "_id" : ObjectId("..."),
    "cid" : "3",
    "gid" : "1"
}
{
    "_id" : ObjectId("..."),
    "cid" : "3",
    "gid" : "2"
}

所以我有很多关系 - 每个联系都可以在每个小组中进行。 我想使用mongo equivalnet of sql查询mongodb

SELECT contacts.*
FROM  dbo.contacts INNER JOIN dbo.contacts_groups ON dbo.contacts.cid = dbo.contacts_groups.cid
WHERE dbo.contacts.email LIKE '%a%' AND dbo.contacts_groups.gid = '1'
ORDER BY dbo.contacts.email

1) 我知道如何构建第一个过滤器(WHERE dbo.contacts.email LIKE '%a%')。

db.contacts.find({"email": /a/})

使用“C#/。NET驱动程序版本2.3”我可以使用(我还需要分页,所以我有:

FilterDefinition<ContactSerial> filter = Builders<ContactSerial>.Filter.Regex("Email", "aaa");
List<ContactSerial> contactsList = m_mongoConn.ContactsColl.Find(filter).Skip(0).Limit(5).ToList();

2) 我想如何实现INNER JOIN的等效(不理想)(即使mongo不是关系数据库)。
我找到了$lookupdb.contacts.aggregate([{ $lookup: {from: "contacts_groups", localField: "cid", foreignField: "cid", "as": "details"}}])

使用“C#/。NET驱动程序版本2.3”:mongoConn.ContactsColl.Aggregate().Lookup("contacts_groups", "cid", "cid", "details");
$ lookup会给我<​​/ p>

{
    "_id" : ObjectId("..."),
    "cid" : "1",
    "email" : "a1@a.aaa",
    "details" : [ ]
}
{
    "_id" : ObjectId("..."),
    "cid" : "2",
    "email" : "a2@a.aaa",
    "details" : [
            {
                    "_id" : ObjectId("..."),
                    "cid" : "2",
                    "gid" : "1"
            }
    ]
}
{
    "_id" : ObjectId("..."),
    "cid" : "3",
    "email" : "a3@a.aaa",
    "details" : [
            {
                    "_id" : ObjectId("..."),
                    "cid" : "3",
                    "gid" : "1"
            },
            {
                    "_id" : ObjectId("..."),
                    "cid" : "3",
                    "gid" : "2"
            }
    ]
}


我的问题是:
a) 如何在一个 MongoShell 查询中将正则表达式过滤器(1)与$ lookup(2)结合使用?
如何使用“C#/。NET驱动程序版本2.3”执行此操作
b) 如何在 MongoShell 查询中添加第二个过滤器(AND dbo.contacts_groups.group_id = '1') - 请注意这是来自第二个集合:contacts_gropups不是联系人
如何在“C#/。NET驱动程序版本2.3”
c) 如何添加所有这些(ORDER BY dbo.contacts.email

1 个答案:

答案 0 :(得分:1)

1)要预过滤汇总查询的值,请使用match

db.contacts.aggregate([
  {$match:{email: {"$regex":/a/}}},
  {$lookup: {from: "contacts_groups", localField: "cid", foreignField: "cid", "as": "details"}}])

您可以在c#中使用已经预定义的聚合函数过滤器:

m_mongoConn.ContactsColl
         .Aggregate()
         .Match(filter)
         .Lookup("contacts_groups", "cid", "cid", "details")

2)您需要在查找后执行另一个项目,例如参见:Filter $lookup results

3)要在聚合管道中对输出进行排序,可以使用Sort命令。不是,在你的聚合中,你从macth得到Contacts,但是在查找之后你确实只有Bson。最好在MatchLookUp

之间进行排序
m_mongoConn.ContactsColl
         .Aggregate()
         .Match(filter)
         .Sort(Builders<ContactSerial>.Sort.Ascending(c=>c.email))
         .Lookup("contacts_groups", "cid", "cid", "details")