Cassandra 文件

版本

您正在檢視預發行版本的說明文件。

RDBMS 設計

當您著手建立一個將使用關聯式資料庫的新資料驅動應用程式時,您可能會先將網域建模為一組適當正規化的表格,並使用外來鍵來參照其他表格中的相關資料。

下圖顯示您如何使用關聯式資料庫模型來表示應用程式的資料儲存。關聯式模型包含幾個「聯結」表格,以便實現飯店與景點、房間與設施、房間與可用性,以及旅客與房間(透過預訂)之間的多對多關係。

image

RDBMS 與 Cassandra 之間的設計差異

讓我們花點時間重點說明為 Cassandra 進行資料建模與為關聯式資料庫進行資料建模之間的一些主要差異。

不聯結

您無法在 Cassandra 中執行聯結。如果您已設計資料模型,並發現需要類似聯結的內容,則您必須在用戶端執行工作,或建立一個表示聯結結果的非正規化第二個表格。後一個選項是 Cassandra 資料建模中的首選。在用戶端執行聯結應該是極少見的情況;您真的想要複製(非正規化)資料。

沒有參考完整性

儘管 Cassandra 支援輕量級交易和批次等功能,但 Cassandra 本身沒有跨表格的參考完整性概念。在關聯式資料庫中,您可以在表格中指定外來鍵,以參照另一個表格中記錄的主鍵。但 Cassandra 沒有強制執行這一點。在表格中儲存與其他實體相關的 ID 仍然是常見的設計需求,但無法使用刪除等操作。

非正規化

在關聯式資料庫設計中,您經常會學習到正規化的重要性。這在使用 Cassandra 時並非優點,因為當資料模型非正規化時,Cassandra 的效能最佳。公司最終也會在關聯式資料庫中非正規化資料的情況很常見。這有兩個常見原因。其一是效能。當公司必須對數年的資料進行許多聯結時,他們無法獲得所需的效能,因此他們會沿著已知查詢非正規化。這最終會奏效,但與關聯式資料庫的設計方式背道而馳,並最終讓人質疑在這種情況下使用關聯式資料庫是否為最佳方法。

關聯式資料庫被故意非正規化的第二個原因是需要保留的商業文件結構。也就是說,您有一個包含表格,它參照許多外部表格,而這些表格的資料可能會隨著時間而改變,但您需要保留包含文件作為歷史快照。此處的常見範例是發票。您已經有客戶和產品表格,您會認為您只要建立一個參照這些表格的發票即可。但實際上不應這樣做。客戶或價格資訊可能會變更,然後您將會失去發票文件在發票日期時的完整性,這可能會違反稽核、報告或法律,並造成其他問題。

在關聯式世界中,非正規化會違反 Codd 的正規形式,您會試著避免它。但在 Cassandra 中,非正規化是,嗯,完全正常的。如果您的資料模型很簡單,則不需要它。但不要害怕它。

在過去,Cassandra 中的非正規化需要使用本文件說明中所述的技術來設計和管理多個表格。從 3.0 版本開始,Cassandra 提供了一項稱為實體化檢視 <materialized-views> 的功能,讓您可以根據基本表格設計建立資料的非正規化檢視。Cassandra 會在伺服器上管理實體化檢視,包括讓檢視與表格保持同步的工作。

優先查詢設計

簡單來說,關聯式建模表示您從概念領域開始,然後將領域中的名詞表示在表格中。然後您會指定主鍵和外來鍵來建模關係。當您有許多對多的關係時,您會建立僅表示這些鍵的聯結表格。聯結表格在現實世界中不存在,並且是關聯式模型運作方式的必要副作用。在您規劃好所有表格後,您可以開始撰寫查詢,使用鍵所定義的關係來彙整不同的資料。在關聯式世界中,查詢在很大程度上是次要的。假設只要您適當地建模表格,您總是能取得想要的資料。即使您必須使用幾個複雜的子查詢或聯結陳述式,這通常是正確的。

相反地,在 Cassandra 中,您並非從資料模型開始;您從查詢模型開始。與先建模資料,然後撰寫查詢不同,使用 Cassandra,您可以建模查詢,並讓資料圍繞它們組織。想想您的應用程式將使用的最常見查詢路徑,然後建立您需要支援它們的表格。

批評者建議,先設計查詢會過度限制應用程式設計,更不用說資料庫建模了。但是,期望您應該認真思考應用程式中的查詢,就像您可能會認真思考您的關係域一樣,這是完全合理的。您可能會弄錯,然後您在兩個世界中都會遇到問題。或者您的查詢需求可能會隨著時間而改變,然後您必須努力更新您的資料集。但是,這與在 RDBMS 中定義錯誤的表格或需要額外表格沒有什麼不同。

設計以實現最佳儲存

在關係資料庫中,表格在磁碟上儲存的方式通常對使用者是透明的,而且很少聽說根據 RDBMS 可能在磁碟上儲存表格的方式,而提出的資料建模建議。然而,這在 Cassandra 中是一個重要的考量因素。由於 Cassandra 表格分別儲存在磁碟上的個別檔案中,因此重要的是將相關欄位定義在同一個表格中。

當您開始在 Cassandra 中建立資料模型時,您將會看到的一個主要目標是,將必須搜尋的分區數量減至最少,以滿足特定查詢。由於分區是儲存單位,不會跨節點分割,因此搜尋單一分區的查詢通常會產生最佳效能。

排序是一種設計決策

在 RDBMS 中,你可以使用查詢中的 ORDER BY 輕鬆變更記錄傳回的順序。預設的排序順序無法設定;預設情況下,記錄會按照寫入順序傳回。如果你想變更順序,只要修改查詢,你就可以根據任何欄位清單來排序。

然而,在 Cassandra 中,排序的處理方式不同;這是一個設計決策。查詢中可用的排序順序是固定的,並且完全由你在 CREATE TABLE 指令中提供的叢集欄位選取決定。CQL SELECT 陳述式支援 ORDER BY 語意,但僅支援叢集欄位指定的順序。

摘錄自 Cassandra, The Definitive Guide。由 O’Reilly Media, Inc. 出版。版權所有 © 2020 Jeff Carpenter、Eben Hewitt。保留所有權利。經許可使用。