2017-09-16 40 views
0

我剛開始使用Firebase數據庫,我對如何構建數據庫感到困惑。在下面的例子中,我有一個用戶對象和一個組對象。每個用戶可以是多個組的一部分,每個組可以有多個用戶。根據「Structure Your Database」,建議的數據庫結構如下。列出Firebase數據和關係

{ 
    "users": { 
    "alovelace": { 
     "name": "Ada Lovelace", 
     "groups": { 
     "techpioneers": true, 
     "womentechmakers": true 
     } 
    } 
    }, 
    "groups": { 
    "techpioneers": { 
     "name": "Historical Tech Pioneers", 
     "startDate": "24-04-1820", 
     "members": { 
     "alovelace": true, 
     "ghopper": true, 
     "eclarke": true 
     } 
    } 
    } 
} 

比方說,我要在列表中顯示所有組在我的應用程序,與組名和起始日期。我將如何進行數據庫調用?由於用戶對象只包含組的id,那麼我是否需要爲每個組分別調用一次數據庫才能找出組的名稱和開始日期?如果列表中有很多組,那麼這會變成很多電話。我的團隊也可能包含很多其他信息,因此這對於性能來說似乎不太合適。我可以在一次通話中獲得用戶的羣組列表中的所有羣組嗎?


一個雖然我有是包括名稱和起始日期的組,用戶可以根據對象:

"users": { 
    "alovelace": { 
     "name": "Ada Lovelace", 
     "groups": { 
     "techpioneers":{ 
      "name": "Historical Tech Pioneers", 
      "startDate": "24-04-1820" 
      }, 
     "womentechmakers":{ 
      "name": "Women in Technology", 
      "startDate": "13-10-1823" 
      } 
     } 
    } 
    } 
} 

但這種解決方案似乎增添了不少的重複數據。此外,如果我想更新名稱,我將不得不在多個位置執行此操作。也許我想添加一個贊助組織對象,也包含組,然後想列出它們。然後會有3個地方更新信息。我將如何解決這個問題?

回答

0

然後,您將有兩種可能性,一種是將所需數據(複製它)存儲在每個用戶的組節點中。

另一方面,我會推薦最多的方法是在第一位觀察者(可能是observe(.value),observe(.childAdded)或其他)中添加observeSingleEvent(of: .value)

說你有你的所有組成員的數組,並命名爲APPUSER的對象,表示您的應用程序用戶:

var groupMembers = [AppUser]() 

要檢測每當一個新成員添加到組,例如,您可以使用例如.childAdded觀察員:

func groupWasAddedObserver(completion: @escaping() ->()) { 

     // Add a .childAdded observer to the group's members node (groupId should be defined somewhere) : 

     groupsRef.child(groupId).child("members").observe(.childAdded, with: { [weak self] (snapshot) in 

       // When you get the snapshot, store its key, which represents the member id : 

       let memberId = snapshot.key 

       // fetch this member's profile information using its id : 

       self?.getUser(memberId, completion: { (groupMember) in 

        // Once you got the profile information of this member, add it to an array of all your members for example : 

        self?.groupMembers.append(groupMember) 

        // Call the completion handler so that you can update the UI or reload a table view somewhere maybe depending on your needs : 

        completion() 

       }) 
     }) 
} 

,第二種方法來獲取用戶數據知道他或她的ID:

func getUser(_ userId: String, completion: @escaping (AppUser) ->()) { 

    // Add the observerSingleEvent observer : 

    usersRef.child(userId).observeSingleEvent(of: .value, with: { (snapshot) in 

      // Get the data you need using the snapshot you get : 

      guard let email = snapshot.childSnapshot(forPath: "email").value as? String else { return } 
      guard let name = snapshot.childSnapshot(forPath: "name").value as? String else { return } 
      guard let picUrl = snapshot.childSnapshot(forPath: "picUrl").value as? String else { return } 

      // Call the completion handler to return your user/member : 

      completion(AppUser(id: snapshot.key, email: email, name: name, picUrl: picUrl)) 

     }) 
} 

正如您所看到的,您可以使用快照鍵獲取每個用戶的memberId,並使用此memberId來獲取此特定用戶數據。