大規模瞭解即時查詢
如要瞭解如何將無伺服器應用程式擴展到每秒數千次作業或數十萬名並行使用者,請參閱這份文件。這份文件包含進階主題,可協助您深入瞭解系統。如果您才剛開始使用 Firestore,請參閱快速入門指南。
Firestore 和 Firebase 行動/網頁 SDK 提供強大的模型,可開發無伺服器應用程式,讓用戶端程式碼直接存取資料庫。用戶端可透過 SDK 即時監聽資料更新。您可以運用即時更新功能建構回應式應用程式,不必使用伺服器基礎架構。雖然要讓應用程式開始運作非常簡單,但瞭解構成 Firestore 的系統限制,有助於確保無伺服器應用程式在流量增加時,仍能順利擴充及維持良好效能。
如需擴展應用程式的建議,請參閱下列各節。
選擇距離使用者較近的資料庫位置
下圖說明即時應用程式的架構:
當使用者裝置 (行動裝置或網路) 上執行的應用程式與 Firestore 建立連線時,連線會傳送至資料庫所在區域的 Firestore 前端伺服器。舉例來說,如果資料庫位於 us-east1
,連線也會前往同樣位於 us-east1
的 Firestore 前端。這些連線會長期保持開啟,直到應用程式明確關閉為止。前端會從基礎 Firestore 儲存系統讀取資料。
使用者實際位置與 Firestore 資料庫位置之間的距離,會影響使用者感受到的延遲。舉例來說,如果印度使用者使用的應用程式會與北美洲 Google Cloud 區域的資料庫通訊,那麼與位於印度或亞洲其他地區的資料庫相比,使用者可能會覺得應用程式速度較慢,反應不夠迅速。
將可靠性納入設計考量
下列主題會改善或影響應用程式的穩定性:
啟用離線模式
Firebase SDK 提供離線資料保存功能。如果使用者裝置上的應用程式無法連線至 Firestore,應用程式仍可使用本機快取資料。即使使用者網路連線不穩,或完全無法連線數小時或數天,也能確保資料存取權。如要進一步瞭解離線模式,請參閱「啟用離線資料」。
瞭解自動重試
Firebase SDK 會負責重試作業,並重新建立中斷的連線。這有助於解決因伺服器重新啟動,或用戶端與資料庫之間的網路問題而導致的暫時性錯誤。
選擇區域或多區域位置
選擇單一區域和多區域位置時,有幾項取捨考量。主要差異在於資料的複製方式。這會影響應用程式的可用性保證。多區域執行個體可提供更強大的服務可靠性,並提高資料耐久性,但代價是費用較高。
瞭解即時查詢系統
即時查詢 (又稱快照監聽器) 可讓應用程式監聽資料庫中的變更,並在資料變更時立即收到低延遲通知。應用程式可以定期輪詢資料庫以取得更新,但通常速度較慢、費用較高,且需要更多程式碼。如需設定及使用即時查詢的範例,請參閱「取得即時更新」。以下各節將詳細說明快照監聽器運作方式,並介紹一些最佳做法,協助您在保留效能的同時,擴充即時查詢。
假設有兩位使用者透過以其中一個行動裝置 SDK 建構的訊息應用程式連線至 Firestore。
用戶端 A 寫入資料庫,在名為 chatroom
的集合中新增及更新文件:
collection chatroom:
document message1:
from: 'Sparky'
message: 'Welcome to Firestore!'
document message2:
from: 'Santa'
message: 'Presents are coming'
用戶端 B 會使用快照監聽器,監聽同一集合中的更新。 每當有人建立新訊息,客戶 B 就會立即收到通知。 下圖顯示快照監聽器背後的架構:
當用戶端 B 將快照監聽器連線至資料庫時,會發生下列事件序列:
- 用戶端 B 開啟 Firestore 連線,並透過 Firebase SDK 呼叫
onSnapshot(collection("chatroom"))
註冊監聽器。這個監聽器可以持續運作數小時。 - Firestore 前端會查詢基礎儲存系統,以啟動資料集。系統會載入相符文件的整個結果集。我們將這類查詢稱為「輪詢查詢」。系統接著會評估資料庫的 Firebase 安全性規則,確認使用者是否可以存取這項資料。如果使用者已獲得授權,資料庫會將資料傳回給使用者。
- 用戶端 B 的查詢隨即進入監聽模式。監聽器會向訂閱處理常式註冊,並等待資料更新。
- 用戶端 A 現在會傳送寫入作業來修改文件。
- 資料庫會將文件變更提交至儲存系統。
- 在交易方面,系統會將相同的更新提交至內部變更記錄。變更記錄會嚴格按照變更發生順序記錄。
- 變更記錄會將更新後的資料傳送至訂閱處理常式集區。
- 系統會執行反向查詢比對器,確認更新後的文件是否與目前已註冊的任何快照監聽器相符。在本例中,文件符合用戶端 B 的快照監聽器。顧名思義,您可以將反向查詢比對器視為一般資料庫查詢,但查詢方向相反。這項功能不會搜尋文件來找出符合查詢條件的文件,而是有效率地搜尋查詢,找出符合傳入文件的查詢。找到相符項目後,系統會將相關文件轉送給快照監聽器。接著,系統會評估資料庫的 Firebase 安全性規則,確保只有獲得授權的使用者能收到資料。
- 系統會將文件更新轉送至用戶端 B 裝置上的 SDK,並觸發
onSnapshot
回呼。如果啟用本機持續性,SDK 也會將更新套用至本機快取。
Firestore 的可擴充性主要取決於從變更記錄到訂閱處理常式和前端伺服器的扇出。透過扇出,單一資料變更就能有效傳播,服務數百萬個即時查詢和連線使用者。在多個可用區 (或多區域部署中的多個區域) 執行所有這些元件的多個副本,Firestore 就能達到高可用性和高延展性。
請注意,從行動和網頁 SDK 發出的所有讀取作業,都會遵循上述模型。這些查詢會執行輪詢查詢,然後進入監聽模式,以確保一致性。這也適用於即時監聽器、擷取文件的呼叫,以及單次查詢。您可以將單一文件擷取作業和單次查詢視為短期快照監聽器,兩者在效能方面有類似的限制。
採用最佳做法,大規模執行即時查詢
請採用下列最佳做法,設計可擴充的即時查詢。
瞭解系統中的高寫入流量
本節說明系統如何因應寫入要求數量增加的情況。
隨著寫入流量增加,驅動即時查詢的 Firestore 變更記錄會自動水平擴展。當資料庫的寫入速率超過單一伺服器的處理能力時,變更記錄會分散到多個伺服器,查詢處理程序也會開始從多個訂閱處理常式 (而非一個) 取用資料。從用戶端和 SDK 的角度來看,這一切都是透明公開的,因此應用程式在發生分割時不需要採取任何動作。下圖說明即時查詢的擴充方式:
自動調度資源功能可讓您無限制地增加寫入流量,但隨著流量增加,系統可能需要一些時間才能回應。請遵循5-5-5 規則的建議,避免建立寫入熱點。 Key Visualizer 是分析寫入熱點的實用工具。
許多應用程式的自然成長可預測,Firestore 無需採取預防措施即可因應。不過,匯入大型資料集等批次工作負載可能會導致寫入速度過快。設計應用程式時,請留意寫入流量的來源。
瞭解寫入和讀取作業如何互動
您可以將即時查詢系統視為連結寫入作業與讀者的管道。每當文件建立、更新或刪除時,變更會從儲存系統傳播至目前已註冊的監聽器。Firestore 的變更記錄結構可確保強烈一致性,也就是說,應用程式收到的更新通知順序,絕對不會與資料庫提交資料變更時的順序不同。這項功能可移除資料一致性相關的極端情況,簡化應用程式開發作業。
這個連線管道表示,造成資源使用率不均或鎖定爭用的寫入作業,可能會對讀取作業造成負面影響。如果寫入作業失敗或受到節流,讀取作業可能會停滯,等待變更記錄提供一致的資料。如果應用程式發生這種情況,您可能會發現寫入作業速度緩慢,且查詢的回應時間也隨之變慢。避免資源使用率不均是解決這個問題的關鍵。
縮小文件和寫入作業
使用快照監聽器建構應用程式時,您通常會希望使用者快速瞭解資料變更。為達成此目標,請盡量保持較小的規模。系統可以非常快速地透過系統推送含有數十個欄位的小型文件。如果文件較大,且有數百個欄位和大量資料,處理時間會較長。
同樣地,請盡量使用簡短快速的提交和寫入作業,以維持低延遲。從寫入者的角度來看,大型批次作業可能會提高輸送量,但實際上可能會增加快照監聽者的通知時間。與其他資料庫系統相比,這通常違反直覺,因為您可能會使用批次處理來提升效能。
使用效率高的監聽器
隨著資料庫的寫入率提高,Firestore 會將資料處理作業分配給多部伺服器。Firestore 的分片演算法會嘗試將相同集合或集合群組的資料,共同放置在同一個變更記錄伺服器上。系統會盡量提高可能的寫入總處理量,同時盡量減少參與查詢處理的伺服器數量。
不過,某些模式仍可能導致快照監聽器出現次佳行為。舉例來說,如果應用程式將大部分資料儲存在一個大型集合中,監聽器可能需要連線至多部伺服器,才能接收所需的所有資料。即使套用查詢篩選器,也依然會發生這種情況。連線至多個伺服器會增加回應速度變慢的風險。
為避免回應速度變慢,請設計結構定義和應用程式,讓系統不必前往多個不同的伺服器,就能為接聽程式提供服務。建議您將資料分成較小的集合,並降低寫入速率。
這與關聯式資料庫中需要完整資料表掃描的效能查詢類似。在關聯式資料庫中,需要完整掃描資料表的查詢,相當於監看高流失率集合的快照監聽器。相較於資料庫可使用更具體索引提供的查詢,這類查詢的執行速度可能會較慢。使用更具體的索引查詢,就像是監看單一文件或較少變更的集合的快照監聽器。您應載入並測試應用程式,以便充分瞭解用途的行為和需求。
快速輪詢查詢
回應式即時查詢的另一個重要部分,是確保用於啟動資料的輪詢查詢快速有效。新的快照監聽器首次連線時,必須載入整個結果集並傳送至使用者的裝置。查詢速度緩慢會導致應用程式回應速度變慢。例如嘗試讀取大量文件的查詢,或未採用適當索引的查詢。
在某些情況下,監聽器也可能會從監聽狀態移回輪詢狀態。這項作業會自動執行,對 SDK 和應用程式而言是透明的。下列情況可能會觸發輪詢狀態:
- 系統會因負載變更而重新平衡變更記錄。
- 熱點會導致資料庫寫入作業失敗或延遲。
- 伺服器暫時重新啟動會暫時影響接聽者。
如果輪詢查詢速度夠快,輪詢狀態對應用程式使用者來說就會是透明的。
優先使用長期監聽器
盡可能長時間開啟並保持監聽器運作,通常是建構使用 Firestore 的應用程式時,最符合成本效益的方式。使用 Firestore 時,系統會針對傳回應用程式的文件收費,而不是針對維持開啟的連線收費。長期存在的快照監聽器只會讀取在整個生命週期中提供查詢所需的資料。包括初始輪詢作業,以及資料實際變更時的通知。另一方面,單次查詢會重新讀取資料,但這些資料可能自應用程式上次執行查詢後就未變更。
如果應用程式必須以高資料速率取用資料,快照監聽器可能就不適用。舉例來說,如果您的用途是透過連線在一段時間內每秒推送大量文件,建議選擇以較低頻率執行的單次查詢。