如要最佳化效能並擴充 Firebase Realtime Database 中的資料,最佳做法是將資料分散到多個 Realtime Database 執行個體,也就是資料庫分片。除了負載平衡和效能最佳化之外,資料分割功能還能讓您彈性擴充,突破個別資料庫執行個體的限制。
分割資料的時機
如果您使用 Realtime Database,且符合下列任一情境,可能需要將資料分散到多個資料庫:
- 您想擴大規模,但已達到單一資料庫執行個體的 20 萬個並行連線、每秒 1,000 次寫入作業,或任何其他限制。
- 您有多個不連續的資料集,並想提升效能 (例如,為不同獨立使用者群組提供服務的即時通訊應用程式)。
- 您想要平衡多個資料庫的負載,以提升正常運作時間,並降低單一資料庫執行個體過載的風險。
如何將資料分片
如要將資料分片,請按照下列步驟操作 (詳情請見下文):
- 根據應用程式的特定需求,將資料對應至多個資料庫。
- 建立多個資料庫執行個體。
- 設定應用程式,使其連線至每個資料集所需的 Realtime Database 執行個體。
對應資料
將資料對應至多個資料庫時,請盡量滿足下列條件:
- 每項查詢只會針對單一資料庫執行個體執行。Realtime Database 不支援跨資料庫執行個體的查詢。
- 資料庫執行個體之間不會共用或複製資料 (或共用/複製的資料量極少)。
- 每個應用程式執行個體在任何時間點都只會連線至一個資料庫。
對應資料時,請考慮套用下列策略:
建立「主分片」
儲存資料在資料庫執行個體中的儲存方式對應表。這樣一來,您就能以程式輔助方式,查詢與連線用戶端對應的資料庫執行個體。請注意,與需要時直接連線至特定資料庫執行個體相比,這可能會有更多額外負擔。
依類別或客戶將資料分組
將資料儲存在獨立的資料庫執行個體中,並依使用者或資料類型分組。 舉例來說,如果您建構的即時通訊應用程式服務多個機構,可以為每個機構建立資料庫執行個體,並將所有即時通訊資料儲存在專屬的資料庫執行個體中。
在這種情況下,機構 A 和機構 B 不會共用資料,資料庫中也沒有任何重複資料,您只會針對單一資料庫執行個體執行查詢。此外,各機構的使用者在使用即時通訊應用程式時,只會連線至所屬機構的資料庫。
然後預先建立多個資料庫執行個體,並使用機構 ID 將團隊對應至資料庫執行個體。舉例來說,機構 A 對應至 Realtime Database A。
應用程式的資料對應方式取決於特定用途,但上述條件和策略可協助您定義適合資料的方式。
建立多個 Realtime Database 執行個體
如果採用 Blaze 定價方案,您可以在同一個 Firebase 專案中建立最多 1,000 個資料庫執行個體。
Firebase 控制台,資料庫區段中顯示內容選單" />
- 在 Firebase 控制台中,前往「Develop」(開發) >「Database」(資料庫) 區段的「Data」(資料) 分頁。
- 在「Realtime Database」專區的選單中,選取「建立新資料庫」。
- 自訂「資料庫參照」和「安全性規則」,然後按一下「我知道了」。
重複上述程序,視需要建立多個資料庫執行個體。每個資料庫執行個體都有自己的 Firebase Realtime Database Security Rules,因此您可以微調資料存取權。
您可以在 Firebase 控制台或使用 Realtime Database Management REST API 建立及管理資料庫執行個體。
使用 CLI 管理特定執行個體並與之互動
您可以使用 Firebase CLI 管理特定 Realtime Database 執行個體並與之互動。
根據預設,CLI 指令會與預設資料庫執行個體互動。不過,您可以使用 --instance DATABASE_NAME
舉例來說,您可以使用下列指令,為名為 my-example-shard.firebaseio.com 的資料庫執行個體執行剖析器:
firebase database:profile --instance "my-example-shard"
下列指令支援 --instance 旗標:
firebase database:getfirebase database:profilefirebase database:pushfirebase database:removefirebase database:setfirebase database:update
編輯及部署每個執行個體的 Realtime Database Security Rules
請確認您已Realtime Database Security Rules為專案中的每個資料庫執行個體授予適當存取權。每個資料庫都有一組專屬規則,您可以透過 Firebase 控制台編輯及部署規則,也可以使用 Firebase CLI 部署目標。
如要透過 Firebase 控制台編輯及部署規則,請按照下列步驟操作:
- 前往「開發」>「資料庫」部分中的「規則」分頁。
- 選取要編輯的資料庫,然後修改規則。
如要透過 Firebase CLI 編輯及部署規則,請按照下列步驟操作:
- 修改資料庫執行個體規則檔案中的規則 (例如
foo.rules.json)。 - 建立及套用部署目標,以關聯使用相同規則檔案的資料庫。例如:
firebase target:apply database main my-db-1 my-db-2
firebase target:apply database other my-other-db-3
使用部署目標更新
firebase.json設定檔:{ "database": [ {"target": "main", "rules": "foo.rules.json"}, {"target": "other", "rules": "bar.rules.json"} ] }執行部署指令:
firebase deploy
- 修改資料庫執行個體規則檔案中的規則 (例如
請務必從同一處編輯及部署規則。從 Firebase CLI 部署規則會覆寫您在 Firebase 控制台中進行的任何編輯作業,而直接在 Firebase 控制台中編輯規則,則會覆寫您透過 Firebase CLI 部署的任何近期變更。
將應用程式連結至多個資料庫執行個體
使用資料庫參照存取儲存在次要資料庫執行個體中的資料。 您可以透過網址或應用程式取得特定資料庫執行個體的參照。如果未指定網址,系統會取得應用程式預設資料庫執行個體的參照。
Web
import { initializeApp } from "firebase/app"; import { getDatabase } from "firebase/database"; const app1 = initializeApp({ databaseURL: "https://testapp-1234-1.firebaseio.com" }); const app2 = initializeApp({ databaseURL: "https://testapp-1234-2.firebaseio.com" }, 'app2'); // Get the default database instance for an app1 const database1 = getDatabase(app1); // Get a database instance for app2 const database2 = getDatabase(app2);
Web
const app1 = firebase.initializeApp({ databaseURL: "https://testapp-1234-1.firebaseio.com" }); const app2 = firebase.initializeApp({ databaseURL: "https://testapp-1234-2.firebaseio.com" }, 'app2'); // Get the default database instance for an app1 var database1 = firebase.database(); // Get a database instance for app2 var database2 = firebase.database(app2);
Swift
// Get the default database instance for an appvar ref: DatabaseReference! ref = Database.database().reference()
Objective-C
// Get the default database instance for an app@property (strong, nonatomic) FIRDatabaseReference *ref; self.ref = [[FIRDatabase database] reference];
Kotlin
// Get the default database instance for an app val primary = Firebase.database.reference // Get a secondary database instance by URL val secondary = Firebase.database("https://testapp-1234.firebaseio.com").reference
Java
// Get the default database instance for an app DatabaseReference primary = FirebaseDatabase.getInstance() .getReference(); // Get a secondary database instance by URL DatabaseReference secondary = FirebaseDatabase.getInstance("https://testapp-1234.firebaseio.com") .getReference();
最佳化每個資料庫的連線
如果每個用戶端在工作階段期間需要連線至多個資料庫,您可以只在必要時連線至每個資料庫執行個體,藉此減少每個資料庫執行個體的並行連線數。
取得更多建議
如需更多協助,將資料分片到多個資料庫執行個體,請透過 Slack 頻道或 Stack Overflow 聯絡 Firebase 專家。