Data Partitioning Guidance

在很多大規模的解決方案中,數據都是分成單獨的分區,可以分別進行管理和訪問的。而分割數據的策略必須仔細的斟酌才能夠最大限度的提高效益,同時最大限度的減少不利影響。數據的分區可以極大的提升可擴展性,降低爭用以及優化性能。

爲何進行數據分區

絕大多數的雲應用和雲服務都會將存儲和檢索數據作爲其業務的一部分。而應用所使用的數據倉庫的設計對於系統的性能,吞吐,擴展性都有着非常重要的影響。其中在大規模系統中常用的一種技術,就是對數據進行分區。

本文中所提到的數據分區,指的是物理上將數據分割成不同的數據倉庫。這並不同於SQL Server 表的拆分,這兩者完全是兩種不同的概念。

對數據進行分區包含了很多的好處,如下:

  • 分區可以提升擴展性,僅僅使用單一數據庫系統遲早會觸及物理硬件的極限的,而對數據進行多個分區(使用不同的Host)的訪問,理論上,是允許系統無限地擴展的。
  • 分區可以提升性能。數據訪問操作每次只是訪問一小部分數據,卻會獨佔IO,當對數據進行了分區,數據的訪問就被分割到不同的Host上面了,性能會極大的提高。獲取數據的信息可以並行的進行。並且,每個分區可以在地裏位置上距離對應的應用服務器很近,極大的降低網絡延時對性能所產生的影響。
  • 分區可以提升可用性。將數據分割成多個不同的部分可降低單端點的錯誤對整體的影響。如果一個分區的服務掛掉了,其它服務的數據請求仍然是可以繼續的,只有掛掉分區中的數據是不可用的。針對於其他數據的服務仍然是正常的。增加分區的數量可以減少單機錯誤對服務整體可用性的影響。而對每個數據分區進行復制可以進一步降低單個分區錯誤所造成的影響。同時,數據分區可以將必須持續保證高可用的關鍵數據和一些低值數據(比如日誌文件)分離。
  • 分區可以增強安全性。根據數據的一些特性,以及分區的特點,可以將敏感數據和非敏感數據分割到不同的分區。之後,針對不同的服務器和數據倉庫進行安全性處理和優化。
  • 分區可以提供操作性彈性擴展。數據分區爲很多操作的適配提供更多的選擇,可以最大化管理效率,減少消耗。不同的分區可以定義不同的策略來管理,監控,備份和恢復,以及針對數據重要性的不同而進行的管理任務。
  • 分區可以使用合適的數據倉庫來匹配其使用場景。數據分區可以讓不同的存儲使用不同的類型的數據倉庫,完全可以根據數據倉庫的特性來進行選擇。例如,大的二進制數據可以存儲在blob數據倉庫,而結構化數據可以存儲在文檔數據庫。想了解更多的信息,可以參考MSDN上面的文章Using SQL, NoSQL, and Polyglot Persistence on MSDN.

設計分區

數據分區可以採用不同的方式:橫向,豎向,根據功能這三種。開發者可以根據其使用場景和需求選擇合適的策略來進行數據分區。

本文中描述的數據分區的體系和數據倉庫使用的一些技術是彼此獨立的。數據分區完全可以使用不同的數據倉庫,包括關係型數據庫和NoSQL類型的數據庫。

分區策略

常見的三種分區策略如下:

  • 橫向分區(通常稱作sharding),在這個策略中,每個分區本身都是一個數據存儲區,但所有分區都有相同的模式。每個分區被稱爲碎片並持有一個特定的數據集,例如在一個電子商務應用一組特定客戶的訂單。
  • 縱向分區。該策略中,每個分區擁有數據倉庫的某些部分數據域(舉例來說就是一個數據的某些表分發到不同的數據庫上面)。這些數據域可以根據其使用的場景來進行分區。比如說,將經常訪問的一些數據庫置於一個數據倉庫,而不常訪問的數據倉庫置於另一個數據倉庫。
  • 功能性分區。該策略中,數據是根據其在系統中如何使用或者聚合的方式來進行分區的。例如,在一個電商系統中,爲發票和管理產品的庫存實現了業務分離功能,可能將發票數據置於一個分區,而產品庫存信息置於另一個分區。

需要注意的是,以上描述的三種不同的策略是可以聯合使用的。他們並不是互斥的,開發者可以在考慮數據分區的時候同時考慮。舉例來說,開發者可以將數據區分成不同的shard然後使用縱向分區策略來將每個shard中的內容分區。類似地,可以通過功能性分區來講shard中的數據繼續分區等。

然後,每個策略不同的需求也會引起一系列的衝突問題,開發者必須在這設計分區的時候進行權衡,才能滿足系統對數據處理的性能要求。下面將針對每個策略的細節進行具體的描述。

橫向分區(Sharding)

圖1展示了橫向分區(sharding)的概覽圖。在這個例子當中,產品庫存數據基於產品的key被區分成不同的shard(每個shard包含了連續返回的shard key,以字母順序管理)

這裏寫圖片描述

圖1.橫向分區(sharding),基於key來分割數據

Sharding可以讓應用承載更多的計算機,減少爭用,以及提升性能。開發者可以輕易的通過增加shard和服務器來擴展系統。

實現橫向分區策略最關鍵的一個點就是sharding的key。在系統運行後,想要更改key就很困難了。Key必須保證數據在正確的分區,並且足夠的平均,這樣才能令工作負載平攤。同時,確保單個shard的訪問沒有超過其數據倉庫能承受的性能上限也非常重要。

同時,shard的結構也避免創建hotspots(過度訪問的分區),因爲那樣可能影響性能以及可用性。舉個例子,使用基於客戶Id的哈希而非客戶名字的首字母進行分片,可以有效防止因爲字母頻率不同所引起的不平衡。這是一種典型的用來幫助數據進行平均分區的技術。

開發者選擇的sharding key應該儘量減小將來繼續分片,將一些分片合併成大分區或者修改數據倉庫的描述等需求。這些操作將非常耗時,並且可能會需要很多分片臨時下線才能完成這些操作。如果shard複製了,當其他分片在執行分片,合併或者重新配置的時候,儘量保證一些拷貝是在線的,當進行這些處理的時候,系統可能需要限制對這些被操作的分片的訪問。例如,處於拷貝中的數據可能需要被標記爲只讀,以限制寫操作所帶來的不一致性。

想了解更多的關於實現Sharding和橫向分區的實踐技術和所需要考慮的問題,可以參考Sharding模式來了解更多信息。

縱向分區

使用縱向分區最常見的場景就是爲了減少由應用最頻繁訪問數據的條目數。圖2展示了縱向分區的一個概覽圖,數據的不同的屬性處於不同的分區之中。

這裏寫圖片描述

圖2.縱向分區根據其場景來組織數據

在上面的例子中,應用最頻繁請求的是產品的名字以及描述和價格信息,並將這些信息展示給客戶。而庫存級別以及產品上一次從廠家預定的日期就被放在了不同的分區,因爲通常情況下,這兩種數據是一起使用的。這種情況下進行的數據分區會有一個額外的優勢,就是相對來說,變化較少的數據(比如產品名字,描述,以及價格等)數據和很容易和一些動態數據(庫存,預定日期)等分離開來。應用可以選擇性的去緩存那些很少改變的數據到內存中來最大化性能。

另一種典型的應用場景就是爲了分離敏感數據,來增加對敏感數據的保護。舉個例子,可以將信用卡的卡號和其對應的安全驗證碼分離到不同的分區中。

垂直分區還可以減少數據所需的併發訪問量。

垂直分區在數據存儲區內的實體級別上運行,部分地將包含多個字段的實體規範化爲多個實體,並用更少的字段。

功能分區

有些系統可以爲每個不同的業務領域或服務的應用程序識別有界的上下文,功能分區爲這類系統的隔離和數據訪問性能的提高提供了技術支持。圖3展示了功能分區的一個概覽圖,其中庫存數據和客戶數據是進行了分離的。

這裏寫圖片描述

圖3 功能性分區通過上下文和子域來進行數據分區

功能分區策略可以幫助減少系統不同部分之間的訪問衝突。

爲擴展性設計分區

考慮每個分區的負載和大小,並且平衡他們是必不可少的,只有這樣才能最大化擴展性。同時,開發者必須對數據進行分區,使其不超過單個分區存儲區的物理限制。

在考慮設計分區擴展性的時候,可以遵循如下的一些步驟:

  1. 分析應用來理解數據的訪問模式,每次的請求的大小,訪問頻率以及內在的等待時間,和一些計算處理需求比如存儲過程。在很多情況下,都是少量實體需要大量的處理資源。
  2. 基於對應用的分析,判斷當前以及未來的規模目標。比如數據大小以及工作負載,並且對數據進行分區來達到對應的規模目標。在橫向分配策略中,選擇合適的shard key是非常重要的,只有這樣才能將數據儘可能均等的分區。關於更多的信息,可以參考Sharding模式.
  3. 分區的時候需要確保每個分區所需要的資源足夠,能夠在吞吐和大小上達到需求值。例如,某個分區的節點在存儲空間,處理能力,網絡帶寬上都存在限制。如果數據存儲和處理需求很容易就超過這些限制的話,重新選擇新的分區策略或者分割數據就是十分必要的了。比如,一個擴展的方法可能會通過使用分離數據倉庫的方式來分離核心應用的日誌數據和應用特性相關的數據來防止服務器上數據存儲超過了單個節點的容量上限。如果數據倉庫的總數超過了節點限制,使用分離的數據節點就十分必要了。
  4. 監控使用中的系統來驗證數據如預期的那樣工作,並且分區可以處理相應的負載。有可能分區的使用量和分析的並不是十分的一致的,如果需要的話,可以針對系統部分不合適的地方進行重新設計來儘可能的平衡各個分區的負載以達到性能和擴展性的需求。

需要注意的是,一些雲環境中分配資源的時候會涉及到基礎設施的限制,開發者應該確保自己選擇的限制能夠預留足夠的空間以應對數據量的增長,包括磁盤空間,處理能力,帶寬等。舉個例子,如果開發者使用Windows Azure表存儲,頻繁的shard可能需要更多的資源來處理一個單表的請求(單表在指定時間內處理請求的數量是存在限制的)。在這種情況下,分片可能需要分割成多個表來分散負載。如果這些表的總大小超過了一個存儲賬戶的容量,就需要創建額外的存儲賬戶來分散負載。如果賬戶的數量超過了一個subscription中的賬戶上限,就需要使用多個subscription了。

爲請求性能設計分區

通常可以通過使用小的數據集合和並行請求執行來增加查詢性能。每個分區都包含全部數據的一部分,這樣可以有效提高查詢的性能。然而,分區並不是提高性能的唯一選擇,還要看數據庫是否配置正確。比如說,在使用關係型數據庫的時候,是否配置了必要的索引來提高性能。

在爲了提高查詢性能而設計分區的時候可以參考如下的一些步驟:

  1. 分析應用來識別出:
    • 那些執行緩慢的請求。
    • 那些關鍵的而且必須快速執行的請求。
  2. 將性能緩慢的數據進行分區。必須確保如下方面:
    • 限制每個分區的大小,這樣請求響應時間才能達到目標。
    • 在實現橫向分區的時候,設計shard key的計算方式,讓應用可以輕易找到正確的分區。這樣可以防止請求掃描全部分區。
    • 考慮一個分區的位置對查詢性能的影響。如果可能的話,嘗試將數據保存在地理上接近應用程序和訪問它的用戶的分區中。
  3. 如果實體有吞吐和請求性能需求,使用基於實體的功能性分區。如果仍然無法滿足需求,也應用橫向分區來解決問題。在絕大多數場景下,單獨使用一種分區策略就足夠了,但是在某些場景下,需要考慮多種策略配合使用來進行分區。
  4. 跨分區的查詢請求可以通過並行查詢來增強性能。

爲可用性設計分區

分區數據通過確保整個數據集不會因爲一個端點的錯誤而影響全部的業務以及獨立管理每個分區的數據集來提升應用的可用性。當設計和實現分區時,可以考慮如下影響可用性的因素:

  • 如何管理分區。設計分區,以支持獨立的管理和維護提供了幾個優點。例如:。
    • 如果某個分區失敗了,可以在不影響應用實例的情況下,直接訪問其他的分區。
    • 不同地域的數據支持配置定時管控任務,可以在非高峯時期進行數據的同步工作。確保分區不太大,以防止任何計劃的維護完成在此期間。
  • 業務操作是如何使用關鍵數據的。 有些數據是包含一些敏感的業務信息的,比如發票細節或者銀行事務等。其他的數據可能就並非業務相關的數據了,比如說日誌文件,性能分析等。在判斷了數據的類型之後,可以考慮:
    • 將關鍵的數據放在高度可靠的分區,並且有一些備份的方案。
    • 對於不同重要性的數據集合,建立不同的監控和管理機制。將相同重要級別的數據放到同一個分區,這樣可以以更爲合適的頻率來對分區的數據進行備份操作。舉個例子,那些存放了銀行事務的分區的備份頻率顯然應該高於那些存放了日誌數據的分區。
  • 考慮是否跨分區複製關鍵數據。這樣的策略可以提供可用性和性能,當然了,也會引入一些一致性的問題。同步不同分區中的數據是需要不少時間的,在同步的這端時間內,就會出現不一樣的數據值了。

問題和顧慮

在設計數據分區的時候會有如下的一些顧慮:

  • 如果可以,儘可能的將最常用、通用的數據庫操作的數據放到一個分區當中,來儘可能的減少跨分區的數據訪問操作。跨分區的查詢數據操作會比訪問一個分區要消耗更多的時間。在跨分區查詢不可避免的場景下,爲了最小化跨分區的查詢時間,就只通過在應用內使用並行查詢請求,並且在聚合返回的結果來優化查詢時間了。然而,這種方法在有的時候也是不可用的,比如不同的分區查詢結果存在相互依賴的情況下(需要先從一個分區獲取數據作爲下一個分區的查詢條件)。
  • 如果查詢使用相對變動很小的數據,比如郵政編碼表或者產品列表等,可以考慮所有的分區使用完全複製的分區策略,來減少尋找不同分區的時間。
  • 在可能的情況下,最小化對垂直和功能分區的引用完整性的要求。在這些方案中,應用程序本身負責在數據更新和消耗時保證跨分區的引用完整性。查詢請求必須要跨越多個分區來結合數據,這會比在同一個分區結合數據要慢的多。因爲應用程序通常需要根據鍵和外鍵進行連續查詢。相反,考慮複製或取消相關數據的規範化。若要最小化跨分區連接所需的查詢時間,請在分區上執行並行查詢,並在應用程序中進行數據的結合操作。
  • 考慮分區方案可能對分區之間數據一致性的影響。開發者應該評估強一致性是否是一個必要的需求。相反,雲中的一種常見方法是實現最終一致性。每個分區中的數據分別更新,並且應用程序邏輯可以負責確保所有的更新都能成功完成,以及處理最終一致的操作正在運行時查詢產生的數據不一致。有關實現最終一致性的更多信息,請參見Data Consistency Primer
  • 考慮查詢如何定位數據所在的分區。如果查詢必須掃描所有分區來定位所需的數據,即使使用多個並行查詢,也將顯著的影響性能。使用垂直和功能分區策略的查詢可以自然指定分區。然而,在使用水平分區(sharding)的時候,定位一個元素是很困難的因爲每個斷片都有相同的架構。典型sharding的解決方案是保持映射,令映射可以用來查找數據項的shard的位置。該映射可以在分片邏輯的應用實施,或由數據存儲是否支持透明的碎片。
  • 使用水平分區策略時,需要考慮定期重新平衡碎片分發數據均勻的規模和工作量減少某個分區的過度訪問,最大限度地提高查詢性能以及減少物理存儲的侷限性影響。當然,這是一個較爲複雜的任務,通常需要使用自定義工具或方法來實現。
  • 複製每個分區爲失敗操作提供額外的保護。如果單個副本失敗,則可以將查詢指向其他備份的工作副本。
  • 如果達到分區策略的物理限制,則可能需要將可擴展性擴展到不同級別。例如,如果分區位於數據庫級別,則可能意味着在多個數據庫中定位或複製分區。如果分區已經在數據庫級別,物理限制是一個問題,它可能意味着在多個託管帳戶中定位或複製分區。
  • 避免在多個分區中訪問數據的事務。某些數據存儲會保證數據進行修改的操作的事務一致性和完整性,但僅當它位於單個分區中時。如果需要跨多個分區進行事務性支持,則可能需要將此作爲應用程序邏輯的一部分纔可以實現,因爲大多數分區系統不提供對於跨分區事務的支持。

所有數據存儲需要一些操作管理和監視活動。任務的範圍可以從加載數據,備份和恢復數據,整理數據,並確保系統執行的正確性和有效性。

考慮影響運營管理的以下因素:

  • 考慮執行一個定期任務來定位任何數據完整性問題,或嘗試自動修復這些問題或發出警報。
  • 考慮如何在數據被分區時執行適當的管理和操作任務,如備份和還原、歸檔數據、監視系統以及其他管理任務。例如,在備份和還原操作中保持邏輯一致性在實現上就是一個挑戰。
  • 考慮如何將數據加載到多個分區,以及新的數據如何從其他源插入到不同分區中。一些工具和實用程序可能不支持分片的數據操作,如數據加載到正確的分區,所以這些操作可能需要定製新的工具和實用程序來完成。
  • 考慮如何將數據定期存檔和刪除(也許每月),以防止分區數據的過度增長。有可能還需要轉換數據以匹配不同的歸檔模式。

相關的模式

在應用程序和數據存儲中實現數據分區時,可以考慮參考如下的一些模式或者方案:

  • Sharding模式.Sharding模式可以通過新增分佈的存儲節點來實現數據存儲規的擴展。此模式描述如何將數據存儲分割爲水平分區。
  • Data Consistency Primer.管理和維護跨分區的數據一致性是一個重要的問題,特別是在併發性和可用性可能出現問題。開發者經常需要使用最終一致性模型來而非使用強一致性。Data Consistency Primer討論了兩種一致性模型優點和侷限性的。
  • Data Replication and Synchronization Guidance. 數據可以跨分區在不同的位置複製,並且可能需要對副本進行週期性地同步,以確保所有分區的數據一致。Data Replication and Synchronization Guidance總結了分佈在多個位置的複製數據的相關問題,並描述瞭解決這些問題的解決方案。
  • Index-Table模式.該模式描述瞭如何進行創建索引,以便在分區數據存儲區中實現數據的快速檢索。
  • Materialized-View模式. 此模式描述如何生成預填充視圖,以便彙總數據以支持快速查詢操作。如果需要聚合或者統計的數據分佈在不同的分區中的時候,可以考慮使用該模式。
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章