如何在mongodb中查询索引对象列表?

时间:2014-06-05 08:41:57

标签: mongodb mongodb-query

我在"公司"以这种方式构建的集合:

[
    {
        "company_name": "Company 1",
        "contacts": {
            "main": {
                "email": "main@company1.com",
                "name": "Mainuser"
            },
            "store1": {
                "email": "store1@company1.com",
                "name": "Store1 user"
            },
            "store2": {
                "email": "store2@company1.com",
                "name": "Store2 user"
            }
        }
    },
    {
        "company_name": "Company 2",
        "contacts": {
            "main": {
                "email": "main@company2.com",
                "name": "Mainuser"
            },
            "store1": {
                "email": "store1@company2.com",
                "name": "Store1 user"
            },
            "store2": {
                "email": "store2@company2.com",
                "name": "Store2 user"
            }
        }
    }
]

我试图检索将store1@company2.com作为联系人的文档但无法找到如何查询"索引的特定属性的特定值"对象列表。

我的感觉是联系人列表不应该被编入索引,导致以下结构:

{
    "company_name": "Company 1",
    "contacts": [
        {
            "email": "main@company1.com",
            "name": "Mainuser",
            "label": "main"
        },
        {
            "email": "store1@company1.com",
            "name": "Store1 user",
            "label": "store1"
        },
        {
            "email": "store2@company1.com",
            "name": "Store2 user",
            "label": "store2"
        }
    ]
}

这样我可以通过以下请求检索匹配的文档:

db.company.find({"contacts.email":"main@company1.com"})

但是,无论如何使用之前的结构对文档做出类似的请求?

非常感谢您的回答!

P.S。 :以这种方式构建的文档的相同问题:

    {
        "company_name": "Company 1",
        "contacts": {
            "0": {
                "email": "main@company1.com",
                "name": "Mainuser"
            },
            "4": {
                "email": "store1@company1.com",
                "name": "Store1 user"
            },
            "1": {
                "email": "store2@company1.com",
                "name": "Store2 user"
            }
        }
    }

2 个答案:

答案 0 :(得分:0)

简短回答:是的,他们可以被查询,但可能不是你想要的,而且效率不高。

第一个和第三个块中的文档结构基本相同 - 您有一个嵌入式文档。唯一的区别是contacts对象中键的名称。

要使用这种结构查询文档,您必须执行以下查询:

db.company.find({ $or : [
   {"contacts.main.email":"main@company1.com"},
   {"contacts.store1.email":"main@company1.com"},
   {"contacts.store2.email":"main@company1.com"}
]});

此查询效率不高,尤其是keys对象中有大量contacts时。此外,创建查询将是不必要的困难且容易出错。

具有嵌入对象数组的第二个文档结构是最佳的。您可以在contacts数组上创建multikey index,这样可以加快查询速度。奖金是您可以使用简短的查询。

答案 1 :(得分:-1)

我认为最简单的方法是使用第二个示例中描述的结构来塑造您的文档:(我还没有修复JSON)

{
 "company_name": "Company 1",
 "contacts":{[
   {"email":"main@company1.com","name":"Mainuser", "label": "main", ...}
   {"email":"store1@company1.com","name":"Store1 user", "label": "store1",...}
   {"email":"store2@company1.com","name":"Store2 user", "label": "store2",...}
  ]}

}

像这样,您可以轻松地在电子邮件中查询“标签”。

因此,如果你真的想要使用其他结构,(但你也需要修复JSON),你将不得不编写更复杂的代码/聚合管道,因为我们在查询时不知道属性的名称和数量。系统。开发人员可能很难独立于MongoDB查询使用这些结构。

由于不清楚,让我展示我的想法

db.company.save(
  {
     "company_name": "Company 1",
     "contacts":[
        {"email":"main@company1.com","name":"Mainuser", "label": "main"},
        {"email":"store1@company1.com","name":"Store1 user", "label": "store1"},
        {"email":"store2@company1.com","name":"Store2 user", "label": "store2"}
      ]
  }
);

db.company.save(
  {
    "company_name": "Company 2",
    "contacts":[
      {"email":"main@company2.com","name":"Mainuser", "label": "main"},
      {"email":"store1@company2.com","name":"Store1 user", "label": "store1"},
      {"email":"store2@company2.com","name":"Store2 user", "label": "store2"}
    ]
  }
); 

db.company.ensureIndex( { "contacts.email" : 1  } );

db.company.find( { "contacts.email" : "store1@company2.com" } );

这允许您存储许多电子邮件,并使用索引进行查询。