如何讓分庫分表真正落地?(下)

分庫分表與讀寫分離

說到分庫分表,我們不得不介紹另一個解決數據訪問瓶頸的技術體系:讀寫分離

這個技術與數據庫的從屬架構有關。我們知道像MySQL這樣的數據庫提供了完善的主從架構,能夠確保主數據庫與數據庫之間的數據同步。基於主從架構,就可以按照操作要求對讀操作和寫操作進行分離,從而就可以提高訪問效率。讀寫分離的基本原理是這樣的:


如何讓分庫分表真正落地?(下)

讀寫分離的基本原理

我們可以看到圖中的數據庫集群中存在一個主庫,也存在一個從庫,主庫和從庫之間通過同步機制實現兩者數據的一致性。在互聯網系統中,普遍認為對數據庫讀操作的頻率要遠遠高於寫操作,所以瓶頸往往出現在讀操作上。通過讀寫分離,就可以把讀操作分離出來,在獨立的從庫上進行。現實中的主從架構,主庫和從庫的數量,尤其從庫的數量都是可以根據數據量的大小進行擴充的。

讀寫分離,主要解決的就是高併發下的數據庫訪問,也是一種常用的解決方案。但是跟提升服務器配置一樣,並不是終極解決方案。終極的解決方案還是前面介紹的分庫分表,按照用戶 ID 等規則來拆分庫或拆分表。但是,請注意,分庫分表與讀寫分離之間的關係並不是互斥的,而是可以相輔相成的,完全可以在分庫分表的基礎上引入讀寫分離機制:


如何讓分庫分表真正落地?(下)

分庫分表解決方案

基於前面對分庫分表的討論,我們可以抽象其背後的一個核心概念,即分片(Sharding)。

因為無論是分庫還是分表,都是把數據劃分成不同的數據片,並存儲在不同的目標對象中。而具體的分片方式涉及到實現分庫分表的不同解決方案。

針對我們上一篇文章討論的問題,實際上已經有很多分庫分表的框架已經解決的很好了,顯然這些框架並不是採用的同一種解決方案。但通過分析這些框架在實現數據分片的方案上的區別,也可以把它們分成三大類型,即客戶端分片、代理服務器、分佈式數據庫

接下來,我們就通過了解這三種方案的原理,來看看它們是怎麼解決分庫分表的問題吧!


客戶端分片

客戶端分片,就是相當於在數據庫的客戶端就實現了分片規則。這種方式將分片處理的工作進行前置,客戶端管理和維護著所有的分片邏輯,並決定每次SQL執行所對應的目標數據庫和數據表。

客戶端分片這一解決方案也有不同的表現形式,其中最為簡單的方式就是應用層分片,也就是說在應用程序中直接維護著分片規則和分片邏輯:


如何讓分庫分表真正落地?(下)

客戶端分片結構

在具體實現上,通常會將分片規則的處理邏輯打包成一個公共 JAR 包,其他業務開發人員只需要在代碼工程中引入這個 JAR 包即可。針對這種方案,因為沒有獨立的服務器組件,所以也不需要專門維護某一個具體的中間件。然而,這種直接在業務代碼中嵌入分片組件的方法也有明顯的缺點:

  • 一方面,由於分片邏輯侵入到了業務代碼中,業務開發人員在理解業務的基礎上還需要掌握分片規則的處理方式,增加了開發和維護成本;
  • 另一方面,一旦出現問題,也只能依賴業務開發人員通過分析代碼來找到原因,而無法把這部分工作抽離出來讓專門的中間件團隊進行完成。

基於以上分析,客戶端分片在實現上通常會進一步抽象,把分片規則的管理工作從業務代碼中剝離出來,形成單獨演進的一套體系。這方面典型的設計思路是重寫 JDBC 協議,也就是說在 JDBC 協議層面嵌入分片規則。這樣,業務開發人員還是使用與 JDBC 規範完全兼容的一套 API 來操作數據庫,但這套 API 的背後卻自動完成了分片操作,從而實現了對業務代碼的零侵入:


如何讓分庫分表真正落地?(下)

客戶端分片結構:重寫JDBC協議

這種解決方案的優勢在於,分片操作對於業務而言是完全透明的,從而一定程度上實現業務開發人員與數據庫中間件團隊在職責上的分離。這樣,業務開發人員只需要理解 JDBC 規範就可以完成分庫分表,開發難度以及代碼維護成本得到降低。

代理服務器分片

代理服務器分片的解決方案也比較明確,就是採用了代理機制,在應用層之後,就可以把分片規則集中維護在這個代理層中,並對外提供與JDBC兼容的API給到應用層。這樣,應用層的業務開發人員就不用關心具體分片規則,而只要完成業務邏輯實現,如圖為代理服務器的分片結構:


如何讓分庫分表真正落地?(下)

代理服務器分片結構

代理服務器分片的優點在於解放了業務開發人員對分片規則的管理工作,而缺點就是添加了一層代理層,所以天生具有代理機制所帶來的一些問題,比方說因為新增了一層網絡傳輸對性能所產生的影響。

分佈式數據庫

相信大家像松鼠一樣,聽到過很多分佈式相關的東西,分佈式的出現,就是為了解決大數據量,高併發的數據處理。因為在技術發展和演進的過程中,關係型數據庫的一大問題在於缺乏分佈式特性,也就是說缺乏分佈式環境下面對大數據量、高併發訪問的有效數據處理機制。舉例來說,我們知道事務是關係型數據庫的本質特徵之一,但在分佈式環境下,如果想要基於 MySQL 等傳統關係型數據庫來實現事務將面臨巨大的挑戰。

幸好,以 TiDB 為代表的分佈式數據庫的興起賦予了關係型數據庫一定程度的分佈式特性。在這些分佈式數據庫中,數據分片及分佈式事務將是其內置的基礎功能,對業務開發人員是透明的。業務開發人員只需要使用框架對外提供的 JDBC 接口,就像在使用 MySQL 等傳統關係型數據庫一樣。使用工具往往比較容易,但理解內涵往往需要花費很多時間和精力,松鼠也在繼續學習的路上。

有的夥伴可能不是很理解集群、分佈式,分佈式集群的概念,在松鼠的的文章裡已經整理過了(《形象理解集群、分佈式、分佈式集群的概念》),感興趣的夥伴,可以去看看。

一款優秀的分庫分表開源框架

前面說了為何要分庫分表、如何分庫分表,以及分庫分表需要解決的問題。那麼接下來就是介紹一個開源的框架,松鼠介紹它的原因其實就擺在了標題上,優秀,又免費學習(咳咳,主要是木有錢)。

像前面提到的客戶端分片結構,典型的中間件包括阿里巴巴的TDDL,但是它並沒有開源,所以我們根本無法知道它究竟是如何實現的客戶端分片。

那麼這個分佈式數據庫中間件 ShardingSphere,是你學習的不二選擇,松鼠覺得有很多原因吧,首先開源,然後分庫分表的三種解決方案,它都是有體現的。

為了顯得嚴謹一點,我將它的優點列出來:

  • 技術權威性,是 Apache 基金會歷史上第一個分佈式數據庫中間件項目,代表著這一領域的最新技術方向;
  • 解決方案完備性
    ,它集客戶端分片、代理服務器,以及分佈式數據庫的核心功能於一身,提供了一套適用於互聯網應用架構、雲服務架構的,完整的開源分佈式數據庫中間件解決方案和生態圈。
  • 開發友好性,提供了友好的集成方式,業務開發人員只需要引入一個 JAR 包就能在業務代碼中嵌入數據分片、讀寫分離、分佈式事務、數據庫治理等一系列功能。
  • 可插拔的系統擴展性:它的很多核心功能均通過插件的形式提供,供開發者排列組合來定製屬於自己的獨特系統。

這些優秀的特性,讓 ShardingSphere 在分庫分表中間件領域佔據了領先地位,並被越來越多的知名企業(比如京東、噹噹、電信、中通快遞、嗶哩嗶哩等)用來構建自己強大而健壯的數據平臺。

說了這麼多,實際上學習起來並沒有那麼容易,也需要由淺入深的學習。

不用擔心,松鼠也才剛剛起步,後面會將自己的學習筆記和學習經歷分享出來。

當然聽到松鼠給大家分享的框架,也可以自己去主動學習然後和我探討。

如果有大牛學習過了,還希望能留言寶貴的建議。

> 文章部分來源於:拉鉤教育網

如果對松鼠的文章感興趣也可以關注我的公眾號:松鼠技術站


分享到:


相關文章: