1. 程式人生 > >mysql分片

mysql分片

-type position 復合 中一 更改 一個數據庫 特定 拆分 單獨

mysql向外擴展(橫向擴展或者水平擴展)策略主要有三方面:復制、拆分、數據分片; 水平擴展的最簡單的方式就是通過復制將數據分發到多個服務器上,然後將備庫用於讀查詢。復制技術用於以讀為主的服務效果最好;但是當數據規模比較大時,復制也有一些問題,例如主從同步間隔時間過長。 數據拆分以及分配方式: 1、按功能拆分 按功能拆分或者職責拆分,就是不同的服務節點執行不同的任務,將獨立的服務器或者節點分配給不同的應用,這樣每個節點只包含它的特定應用所需的數據。 技術分享圖片 技術分享圖片 缺點:如果一個功能區域的數據綁定到單個mysql節點,後續就只能對單個節點進行垂直擴展(擴展硬件類似的方式)。 2、數據分片 對於目前的擴展大型Mysql應用來說,數據分片是最通用且成功的方法,它把數據分割為一個小片或者一塊,然後存儲到不同的節點上。 數據分片與按照功能劃分聯合使用時非常有用。大多數分片系統也有一些“全局的”數據不會進行劃分(城市列表或者登陸數據等)。全局數據一般存儲到單個節點上,並且會保存在NoSql類的內存數據庫中以便加速訪問。 數據分片一般會對數據增長的非常龐大的數據進行分片。 大多數應用可能存在多個不同的邏輯數據集,並且數據集的處理方式也會不同,可以將不同的數據集存儲到不同服務器組上,然後以多種方式就行分片。 技術分享圖片
技術分享圖片 可以通過用戶Id對數據進行分片。 采用數據分片的應用通常會有一個數據庫訪問抽象層,用以降低應用與數據庫之間的通訊復雜度。 3、選擇分區鍵 數據分片的最大挑戰是查找和獲取數據:如何查詢數據取決於如何進行分片; 分片的目標是針對於那些最重要並且頻繁查詢的數據減少分片,因為需要避免多個節點之間的交互。 跨多個分片的查詢比單個分片的查詢性能要差,但是只要不涉及到過多的分片性能不會差太多。 一個好的分區鍵通常是數據庫中一個非常重要的實體主鍵,例如用於Id或者客戶端ID等。 確定分區鍵的一個比較好的辦法是用實體-關系圖,看是否可以根據分區鍵拆分出耦合關系簡單的實體-關系圖。 選擇分區鍵時盡量避免那些會進行跨分區查詢的,但是也要讓分片足夠小,以避免過大的數據分片導致的問題。分區鍵要選擇可以把數據平均分片到各個分區的鍵。 4、多個分區鍵 復雜的數據模型會使數據分片更加復雜。 例如博客應用的數據按照用戶ID和文章ID進行分片,因為使用兩者查詢數據比較平常,針對這種情況建議把用戶ID和文章ID一起分片到一個分片中,避免跨分片查詢。 5、跨分片查詢 大多數應用或多或少會有一些跨分片查詢的情況,例如對數據的進行聚合或者關聯操作。 跨分片查詢可以利用匯總表來執行,可以遍歷所有分片來生成匯總表並將結果在每個分片上進行冗余;如果每個分片都冗余匯總表太過浪費,可以把匯總表放到一個單獨的數據存儲中,這樣就只需要一份存儲了。 跨分片查詢並不是數據分片面臨的唯一問題,維護數據一致性同樣困難,外鍵無法在分片間工作,因此需要有應用來檢查參考一致性,或者只在分片內使用外鍵,因為分片的內部一致性可能會很重要。 6、分配數據、分片與節點 分片與節點並不一定要一對一對應,最好是一個節點下存儲多個分片; 保持的分片足夠小更容易管理,這會是數據的備份和恢復更容易;如果表很小,那麽像更改表結構這樣的操作會更加容易; 小一點的分片也便於轉移,這有助於重新分配容量,平衡各個節點的分片,轉移分片的效率一般都不高。通常需要將受影響的分片設置為只讀模式,提取數據,然後轉移到另一個節點。 7、在節點上部署分片 一般的分為以下幾種方式:
  • 每個分片使用單一數據庫,並且數據庫名要相同;這種方式在部署多個應用實例,並且每個應用實例對應一個分片時很有用;
  • 將多個分片的表放在一個數據庫中,在每個表名上包含分片號,例如:db.book_0023、db.user_0023;這種配置下,單個數據庫可以支持多個數據分片;
  • 為每個分片使用一個數據庫,並在數據庫中包含所有應用需要的表。在數據庫名中包含分片號,例如:db0023.book、db0023.user;當應用鏈接到單個數據庫並且不再查詢中指定數據庫名時,這種做法很常見,其優點就是無須為每個分片專門編寫查詢,也便於對只使用單個數據庫的應用進行分片;
  • 每個分片使用一個數據庫,並在數據庫名和表名中包含分片名,例如:db0023.book_0023;
  • 在每個節點上運行多個Mysql實例,每個實例上有一個或者多個分片,可以使用上面提到的方式的任意組合來安排分片;
為已有應用增加分片支持的結果往往是一個節點對應一個分片,這種簡化的設計可以減少對應用查詢的修改。 8、固定分配 將數據分配到分片中由兩種主要的方式:固定分配與動態分配;兩種方式都需要一個分區函數,使用行的分區鍵做為輸入,返回存儲該行的分片; 固定分配使用的分區函數僅僅依賴於分區鍵的值;哈希函數或者取模運算就是很好的例子;優點是簡單、開銷低、甚至可以在應用中直接硬編碼; 固定分配的缺點:
  • 如果分片很大並且數量不多,就很難平衡不同分片的負載;
  • 固定分配的方式無法自定義數據放到哪個分片上;
  • 修改分片策略通常比較困難,因為需要重新分配已有的數據;
正是由於以上的缺點,我們盡可能選擇動態分配的方式; 9、動態分配 使用動態分配可以將每個數據單元映射到一個分片上; 動態分配增加了分區函數的開銷,因為需要額外調用一次外部資源,例如目錄服務器(存儲映射關系的數據存儲節點)。 動態分配的最大好處是可以對數據存儲位置做細粒度的控制;這使得均衡分配數據到分片更容易,並且提供適應未知改變的靈活性; 動態映射可以在簡單的鍵-分片映射的基礎上建立多層次的分片策略; 使用動態分配策略可以生成不均衡的分片,對於不同服務器處理能力的不同,可以定制分配分片數據的大小; 動態分配有助於減輕規模擴大而帶來的跨分片查詢問題,例如當一個跨分片查詢需要跨4個節點時,如果使用固定分配時,任何給定的查詢可能需要訪問所有分片,但動態分配策略則可能只需要在問其中三個節點上運行同樣的查詢,當節點規模從4個增長到400個時,動態分配策略的優勢就體現出來了,使用動態分配策略依然只訪問3個,而固定分配則需要訪問所有的節點; 10、混合動態分配與固定分配 可以混合使用動態分配和固定分配。 11、顯示分配 第三種策略是在應用插入新的數據時顯示的選擇目標分片。這種策略在已有的數據上很難做到,所有在為應用增加分片時很少使用,但在某些情況下會很有用; 顯示分配的確定是分片方式固定,很難做到分片間的負載均衡; 12、重新均衡分片數據 可以通過分片間移動數據來實現負載均衡。 重新均衡分片數據會影響用戶使用,因此應該避免此操作; 一個比較好的方式是使用動態分配策略,並將新數據隨機分配到分片中,當一個分片快滿時,可以設置一個標誌位,告訴應用不要在往裏放數據了。 13、生成全局唯一ID 當希望一個現有系統轉換為分片數據存儲時,經常會需要在多臺機器上生成全局唯一主鍵ID;單一機器使用AUTO_INCREMENT列來獲取唯一ID,但是涉及到多臺機器時就不奏效了,有以下幾種方式生成全局唯一主鍵ID:
  • 使用auto_increment_increment與auto_increment_offset這兩個服務器變量可以讓mysql以期望的值和偏移量來增加AUTO_INCREMENT列的值,例如,有兩臺服務,可以配置兩臺服務器的自增量為2,其中一臺服務器的偏移量為1,另一臺服務器的偏移量為2,這樣一臺服務器的ID為偶數,另一臺服務器的ID為奇數;
  • 全局節點中創建表,在一個全局數據庫節點中創建一個包含AUTO_INCREMENT列的表,應用可以通過這個表來生成唯一數字;
  • 使用NoSql中自動的遞增函數,例如memcache或者redis的自動函數;
  • 批量分配數字,應用可以從一個全局節點請求一批數字,用完再申請;
  • 使用復合值,可以通過一個復合值來做唯一ID,例如分片號+自增數的組合;
  • 使用GUID

mysql分片