數據庫分庫分表策略,如何分庫,如何分表?

  導語:隨着線下店業務發展,線下店開店數越來越多,價格系統的數據增長非常快速,部分單表已達到3億之多,爲了適應業務的發展,考慮對價格系統進行分庫分表,因此特別瞭解了一下分庫分表的相關知識,根據相關資料,再次複習一下。
  大家知道,隨着流量和數據增長,關係型數據庫本身往往容易成爲系統的瓶頸點,讀寫分離能緩減讀寫壓力,卻並不能分散存儲壓力,當數據達到一定量以後,單臺數據庫服務器會成爲瓶頸,主要體現在以下幾個方面:

  • 數據量太大,讀寫的性能會下降,即使有索引,索引也會變得很大,性能同樣會降下。
  • 數據庫文件會得很大,數據庫備份和恢復需要耗時很長。
  • 數據庫文件越大,極端情況下丟失數據的風險越高。
      因此,當流量越來越大時,且單機容量達到上限時,此時需要考慮對其進行切分,切分的目的就在於減少單機數據庫的負擔,將由多臺數據庫服務器一起來分擔,縮短查詢時間。

切分策略

  數據切分分爲兩種方式,縱向切分和水平切分

  1. 縱向切分
      常見有縱向分庫縱向分表兩種。
    1). 縱向分庫就是根據業務耦合性,將關聯度低的不同表存儲在不同的數據庫,做法與大系統拆分爲多個小系統類似,按業務分類進行獨立劃分。與“微服務治理”的做法相似,每個微服務使用單獨的一個數據庫。
    2). 垂直分表是基於數據庫中的列進行,某個表字段較多,可以新建一張擴展表,將不經常用或者字段長度較大的字段拆出到擴展表中。在字段很多的情況下,通過大表拆小表,更便於開發與維護,也能避免跨頁問題,MYSQL底層是通過數據頁存儲的,一條記錄佔用空間過大會導致跨頁,造成額外的開銷。另外,數據庫以行爲單位將數據加載到內存中,這樣表中字段長度越短且訪問頻次較高,內存能加載更多的數據,命中率更高,減少磁盤IO,從而提升數據庫的性能。
  • 垂直切分的優點:
    • 解決業務系統層面的耦合,業務清晰
    • 與微服務的治理類似,也能對不同業務的數據進行分級管理,維護,監控,擴展等。
    • 高併發場景下,垂直切分一定程度的提升IO,數據庫連接數,單機硬件資源的瓶頸。
  • 垂直切分的缺點
    • 部分表無法join,只能通過接口聚合方式解決,提升了開發的複雜度。
    • 分佈式事處理複雜
    • 依然存在單表數據量過大的問題。
  1. 水平切分
      當一個應用難以再細粒度的垂直切分或切分後數據量行數依然巨大,存在單庫讀寫,存儲性能瓶頸,這時候需要進行水平切分。
      水平切分爲庫內分表和分庫分表,是根據表內數據內在的邏輯關係,將同一個表按不同的條件分散到多個數據庫或多表中,每個表中只包含一部分數據,從而使得單個表的數據量變小,達到分佈式的效果。
      庫內分表只解決單一表數據量過大的問題,但沒有將表分佈到不同機器的庫上,因些對於減輕mysql的壓力來說幫助不是很大,大家還是競爭同一個物理機的CPU、內存、網絡IO,最好通過分庫分表來解決。
  • 水平切分優點
    • 不存在單庫數據量過大、高併發的性能瓶頸,提升系統穩定性和負載能力。
    • 應用端改造較小,不需要拆分業務模塊。
  • 水平切分缺點
    • 跨分片的事務一致性難以保證
    • 跨庫的join關聯查詢性能較差
    • 數據多次擴展維度和維護量極大。
      #路由規則
        水平切分後同一張表會出現在多個數據庫或表中,每個庫和表的內容不同,對於水平分表後分庫後,如何知道哪條數據在哪個庫裏或表裏,則需要路由算法進行計算,這個算法會引入一定的複雜性。
  • 範圍路由

  選取有序的數據列,如時間戳作爲路由的條件,不同分段分散到不同的數據庫表中,以最常見的用戶ID爲例,路由算法可以按照1000000的範圍大小進行分段,1 ~ 9999999放到數據庫1的表中,10000000~199999999放到數據庫2的表中,以此累推。
  範圍路由設計的複雜點主要體現在分段大小的選取上,分段太小會導致切分後子表數量過多增加維護複雜度,分段太大可能會導致單表依然存在性能問題,按一般大老們的經驗,分段大小100W至2000W之間,具體需要根據業務選 取合適的分段大小。

  • 範圍路由的優點
    • 可以隨着數據的增加平滑地擴充新的表或庫,原有的數據不需要動。
    • 單表大小可控
    • 使用分片字段進行範圍查找時,連續分片可快速定位查詢,有效避免分片查詢的問題。
  • 熱點數據成爲性能瓶頸,連續分片可能存在數據熱點,例如按時單字段分片,有些分片存儲最近時間內的數據,可能會被頻繁讀寫,而有些歷史數據則很少被查詢。
  • hash算法

  選取某個列或幾個列的值進行hash運算,然後根據hash的結果分散到不同的數據庫表中,以用ID爲例,假如我們一開始就規劃10個數據庫表,路由算法可以簡單地用id % 10的值來表示數據所屬的數據庫編號,ID爲985的用戶放到編號爲5的子表中。ID爲10086編號放到編號爲6的表中。
  Hash路由設計的複雜點主要體現 在初始表數量的選取上,表數量太多維護比較麻煩,表數量太小又可能導致單表性能存在問題。而用Hash路由後,增加字表數量是非常麻煩的,所有數據都要重新分佈。
  Hash路由的優缺點與範圍路由相反,Hash路由的優點是表分佈比較均勻,缺點是擴容時很麻煩,所有數據均需要重新分佈。

  • 路由配置

  配置路由就是路由表,用一張獨立的表來記錄路由信息。同樣以用戶ID爲例,我們新增一張ROUTER表,這個表包含table_Id兩列,根據user_id就可以查詢對應的修改路由表就可以了。
配置路由設計簡單,使用起來非常靈活,尤其是在擴充表的時候,只需要遷移指定的數據,然後修改路由表就可以了。
其缺點就是必須多查詢一次,會影響整體性能,而且路由表本身如果太大,性能會成爲瓶頸點,如果我們再將路由表分庫分表,則又面臨一個死循環。

分庫分錶帶來的問題

  • join操作

水平分表後,雖然物理上分散在多個表中,如果需要與其它表進行join查詢,需要在業務代碼或者數據庫中間件中進行多次join查詢,然後將結果合併。

  • COUNT(*)操作

水平分表後,某些場景下需要將這些表當作一個表來處理,那麼count(*)顯得沒有那麼容易 了。

  • order by 操作

分表後,數據分散到多個表中,排序操作無法在數據庫中完成,只能由業務代碼或數據中間件分別查詢每個子表中的數據,然後彙總進行排序。

  • 事務問題

解決事務問題通常有兩種方法:一是使用分部式事務,另一種由應用程序和數據庫一起控制,這兩個方法各有優勢。
1、使用分佈式事務
優點:由數據庫本身來管理,較爲簡單
缺點:當shard越來越多時,性能代價高特別高
2、應用程序和數據庫共同控制
將多個分佈式事務拆到小事務上,並由各個應用程序來控制,這樣帶來的好處,性能較高,而缺點是需要應用程序在事務控制上做靈活設計

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章