簡體   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