繁体   English   中英

One-to-Many Mongoose关系 - 存储引用的位置

[英]One-to-Many Mongoose relationship - Where to store the reference

我正在为一个新项目设计MongoDB集合架构,并且是MongoDB的新手,我有一个关于一对多关系的问题。

为了这个例子,假设关系是数据中心到服务器,这意味着一个数据中心可以有多个服务器(数千个,不限于应用程序),服务器只能属于一个数据中心。

Servers._datacenter引用Datacenter._id最好吗? 或者Datacenter.servers 数组来存储服务器ID?

如果您建议在Datacenter文档中使用一个数组来引用与之关联的服务器ID ...那么,当您拥有服务器ID时,有没有办法找出服务器所属的Datacenter? (有点像where serverId in Datacenter.servers查询where serverId in Datacenter.servers快速查询),无需查询每个数据中心,然后检查每个Datacenter.servers数组中的ID

如果您建议在Servers文档中有一个元素来引用它所属的Datacenter,那么有没有办法查询Datacenter,并返回虚拟Documents.servers数组中的所有相关Server文档?

我不太清楚最好的路线是什么,因为每个数据中心可能有非常大量的服务器,我认为在每个数据中心文档中没有这么大的数组可能更好......但是然后,如果我设置它,以便每个服务器文档都有其中引用的父数据中心,这使得查询相当困难(或者不是?也许这是一个非常简单的方法,我只是没有发现,我说我是Mongo的新手)

我正在阅读这篇文章 ,它展示了如何设置参考方向,并指出:

要避免可变的增长数组,请将发布者引用存储在book文档中

所以这让我觉得最好在服务器文档中引用数据中心ID。那么如果是这样的话,有没有办法将所有服务器文档作为数组内部文档中的数组返回? 或者我是否必须查询数据中心,然后使用该Datacenter._id查询所有服务器,然后返回合并对象。

这取决于访问模式。 你如何计划编码为null1941说。

如果服务器的数量是10或数百,我猜这将是一对一的关系,而不是一对多,所以你可以继续将数据中心嵌入到服务器中。 这意味着您将获得一次性和单个查询所需的所有信息。 如果您可以保证一致性,这种方法可以工作,但如果在一个数据中心中存在许多服务器,您将最终得到重复。 因此数据中心文档可以在许多服务器文档中复制。 如果您可以再次保证一致性并且数据中心可能几乎没有关于它们的信息,则此方法可以起作用。 这种方法的唯一优势是您只进行一次查询。 通常不推荐这种方法; 此外,如果您希望将数据中心视为单独的文档,以便您希望在其上运行某些操作,而不是避免使用此方法。

如果你决定采用这种方法; 将数据中心嵌入为数组您可以使用$ all$ in在数组内部进行搜索。

例:

{
"_id" : ObjectId("63546464sad65s4ad3654"),
"name" : "Server1",
"datacenter" : ["gamma", "500"]          

}

查询:

db.users.find({ "datacenter": { $in: [ "gamma", "delta" ] } } )

如果你决定将服务器作为文档嵌入(你可以嵌入数据中心文档以及内部服务器都可以工作)。 因此,对于在数据中心文档中嵌入服务器,您可以使用点表示法在嵌入文档内部进行搜索。 示例:(服务器是字典,name是服务器内的属性):

{
"_id" : ObjectId("63546464sad65s4ad3654"),
"name" : "gamma",
"servers" : [
            {
              "title" : "server1",
              "speed" : "3.2GHZ",
              "ram"   : "200GB"
            },
            {
              "title" : "server2",
              "speed" : "3.2GHZ",
              "ram"   : "64GB"
            }
         ]
}

查询:

db.datacenters.find( { "servers.title": "server1" } 

你再次判断。 但是,您决定这样做,mongodb中有一种方法可以检索您需要的信息。

现在请记住,如果您决定在数据中心文档中嵌入服务器,那么在mongodb中,单个文档不应超过16MB。 如果通过嵌入这个大小可能会超过你应该去分裂方法(下面)。

现在, 更好的方法嵌入的情况; 基本上就像gnerkus说的那样。 但请记住,在mongodb中没有外键约束,您必须确保使用该应用程序的一致性。 这样数据中心集合中的server_id可以在服务器集合中找到(反之亦然)。 您还可以将datacenter_id放在服务器集合中; 我决定选择哪一个的方法是我的用例。 例如,如果我的大部分操作都在数据中心上,我将向其添加server_id。 如果我的大多数操作都在服务器集合上,我将向其添加datacenter_id。 在这两种情况下,您将进行两次或更多次查询。 这是一个例子:

数据中心文档示例

 {
     _id : ObjectId("10001000010000"),
     name : 'Gamma',        
     location: 'pluto',
     servers: [      
         ObjectID('1212'),     
         ObjectID('1213') 
              ]    
 }

服务器文档示例:

{
    _id : ObjectId("1212"),
    name : 'Server1',
    ram: '250GB',
    type: 'processing',
    status: 'running' 
}

在这种情况下,您可以查询为:首先,您获得所需的数据中心(假设名称是唯一的)

datacenter = db.datacenter.findOne({name: "Gamma"})

然后,您将查询所需的服务器详细信息; 示例以获取上面给定数据中心中的所有服务器

servers = db.servers.find({_id: { $in : datacenter.servers } } )

在拥有所有服务器之后,您可以遍历每个服务器并检查状态或其他内容。 您将最终在服务器变量中拥有服务器文档。

我希望有所帮助

最好在Server文档中引用Datacenter ID。 要检索具有指定数据中心ID的服务器,您只需查询服务器集合。 查询并不困难,看起来像这样:

var dataID = datacenter._id

db.servercollection.find({ datacenter: dataID }, function(err, servers) {

});

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM