數據庫中間件
這里主要介紹互聯網行業內有關數據庫的相關中間件。數據庫相關平臺主要解決以下三個方面的問題:
應用層通過分表分庫中間件訪問數據庫,包括讀操作()和寫操作(, 和等,DDL, DCL)。寫操作會在數據庫上產生變更記錄,MySQL的變更記錄叫, 的稱之為, 增量數據訂閱與消費中間件解析這些變更,并以統一的格式保存起來,下層應用根據這些數據進行消費應用。當然,在數據庫與數據庫本身之間也會有數據庫遷移的操作,這種操作可以不需要增量數據訂閱與消費中間件的數據,而可以自行處理。
數據庫中間件有以下幾種:
整個產品族圖如下:
最上層的是分布式數據庫分表分庫中間件,負責和上層應用打交道,對應用可表現為一個獨立的數據庫,而屏蔽底層復雜的系統細節。分布式數據庫中間件除了基本的分表分庫功能,還可以豐富一下,比如講讀寫分離或者水平擴容功能集成在一起,或者比如讀寫分離本身也可以作為一個獨立的中間件。(Cobar, MyCAT, TDDL, DRDS, DDB)
增量數據訂閱和消費,用戶對數據庫操作,比如DML, DCL, DDL等,這些操作會產生增量數據,下層應用可以通過監測這些增量數據進行相應的處理。典型代表Canal,根據MySQL的實現。也有針對()的增量數據訂閱與消費的中間件。(Canal, Erosa)
數據庫同步中間件涉及數據庫之間的同步操作,可以實現跨(同)機房同步以及異地容災備份、分流等功能。可以涉及多種數據庫,處理之后的數據也可以以多種形式存儲。(Otter, , DRC)
數據庫與數據庫之間會有數據遷移(同步)的動作,同款數據同步原理比較簡單,比如MySQL主備同步,只要在數據庫層進行相應的配置既可,但是跨數據庫同步就比較復雜了,比如->MySQL. 數據遷移一般包括三個步驟:全量復制,將原數據庫的數據全量遷移到新數據庫,在這遷移的過程中也會有新的數據產生;增量同步,對新產生的數據進行同步,并持續一段時間以保證數據同步;原庫停寫,切換新庫。將“跨數據庫”這個含義擴大一下——“跨數據源”,比如HDFS, HBase, FTP等都可以相互同步。(, DataX)
分布式數據庫
隨著互聯網產品在體量和規模上日益膨脹,無論是還是MySQL,都會第一時間面臨來自磁盤,CPU和內存等單機瓶頸,為此,產品方除了需要不斷購買成本難以控制的高規格服務器,還要面臨不斷迭代的在線數據遷移。在這種情況下,無論是海量的結構化數據還是快速成長的業務規模,都迫切需要一種水平擴展的方法將存儲成本分攤到成本可控的商用服務器上。同時,也希望通過線性擴容降低全量數據遷移對線上服務帶來的影響,分庫分表方案便應運而生。
分表分庫類的中間件主要有兩種形式向應用提供服務:
Cobar
Cobar 是提供關系型數據庫(MySQL)分布式服務的中間件,它可以讓傳統的數據庫得到良好的線性擴展,并看上去還是一個數據庫,對應用保持透明。
Cobar以Proxy的形式位于前臺應用和實際數據庫之間,對前臺的開放的接口是MySQL通信協議。將前臺SQL語句變更并按照數據分布規則發到合適的后臺數據分庫,再合并返回結果,模擬單庫下的數據庫行為。
Cobar屬于阿里B2B事業群,始于2008年,在阿里服役3年多,接管3000+個MySQL數據庫的,集群日處理在線SQL請求50億次以上。由于Cobar發起人的離職,Cobar停止維護。后續的類似中間件,比如MyCAT建立于Cobar之上,包括現在阿里服役的RDRS其中也復用了Cobar-Proxy的相關代碼。
Cobar結構
與應用之間通過MySQL 進行交互,是一個proxy的結構,對外暴露jdbc:mysql://:port/。對應用透明。
無需引入新的jar包,從訪問遷移到數據庫訪問Cobar可以復用原有的基于JDBC的DAO。
Cobar前后端都實現了MySQL協議,當接受到SQL請求時,會一次進行解釋(SQL )和路由(SQL )工作,然后使用SQL 去后端模塊獲取數據集(后端模塊還負責心跳檢查功能);如果數據集來自多個數據源,Cobar則需要把數據集進行組合( Merge),最后返回響應。
數據庫連接復用。Cobar使用連接詞與后臺真是數據庫進行交互。(實際應用中,根據應用的不同,使用proxy結構后數據庫連接數能夠節約2-10倍不等。)
Cobar事務,Cobar在單庫的情況下保持事務的強一致性,分庫的情況下保持事務的弱一致性,分庫事務采用2PC協議,包括執行階段和提交階段。
Cobar的前端是NIO的,而后端跟MySQL交互是阻塞模式,其NIO代碼只給出了框架,還沒有來得及實現。 據稱未開源版的Cobar實現了后端的NIO。
Cobar會出現假死,假死以后Cobar會頻繁進行主從切換(如果配置了的話),自動切換本身也存在隱患。
可以計算:Cobar的TPS=5,000,000,000/(3000*24*60*60)=20。
與Cobar相關的還有一共Cobar-。
Cobar通過SQL語句轉發的方式實現數據訪問。用戶發來的SQL語句,Cobar解析其內容,判斷該語句所涉及的數據分布在哪個分庫上,再將語句轉發給此分庫執行。當SQL語句中涉及的拆分字段有多值,如 IN, 或where條件中沒有出現拆分字段時,該語句將會轉發至后臺所有分庫執行,再將執行結果以MySQL協議包的形式送回應用端。
通信模塊,負責從連續的網絡數據流中識別出一個個MySQL協議包,再解析協議包識別出SQL語句輸出給模塊,同時,把 Merge模塊輸入的執行結果,編碼成MySQL的協議包。它以NIO方式實現,有很高的執行效率。之后進行優化,引入了一個池,將NIO的統一管理起來,減少了NIO數據交互時的垃圾回收。
Cobar前端使用的是優化后的NIO通信模塊,為了讓該模塊在后端使用,Cobar去除了JDBC。與后端數據庫交互,Cobar直接面向協議,目前實現了基于MySQL協議的后端交互。
水平拆分后,后臺有多個數據源,對他們的管理分為兩個層次:和(HA Pool)。
管理拆分,一個存放一個分片的數據,彼此無數據交集。每個分片的數據存多份以保證高可用,每一份叫做一個,由HA層管理。每一個表示一個具體的數據源,它是一個連接池,池內管理每一個具體的JDBC連接。路由運算只關注到層,之下的層次對其不可見。
每一份之間的數據復制和同步由MySQL本身的協議完成,同一時刻只有一個提供服務(稱為,其余稱為Slave).Cobar會與之保持心跳,一旦發現它不可用,會切換至另一個,解決單點的第二個問題。
為了節省數據庫的機器數量,可以采用下圖中的方式部署:
HA
在用戶配置了MySQL心跳的情況下,Cobar可以自動向后端連接的MySQL發生心跳,判斷MySQL運行狀況,一旦運行出現異常,Cobar可以自動切換到備機工作,但需要強調的是:
Cobar解決的問題
分布式:Cobar的分布式主要是通過將表放入不同的庫來實現。
這里需要強調的是,Cobar不支持將一張表,例如test表拆分成, , ….放在同一個庫中,必須拆分后的表分別放入不同的庫來實現分布式。
Cobar的約束
MyCAT
從定義和分類看,它是一個開源的分布式數據庫系統,是一個實現了MySQL協議的,前端用戶可以把它看做是一個數據庫代理,用MySQL客戶端工具和命令行訪問,而其后端可以用MySQL 與多個MySQL服務器通信,也可以用JDBC協議與大多數主流數據庫服務器通信,其核心功能是分表分庫,即將一個大表水平分割為N個小表數據庫中間件原理,存儲在后端MySQL服務器里或者其他數據庫里。
MyCAT發展到目前的版本,已經不是一個單純的MySQL代理了,它的后端可以支持MySQL, SQL , , DB2, 等主流數據庫,也支持這種新型NoSQL方式的存儲,未來還會支持更多類型的存儲。
MyCAT是一個強大的數據庫中間件,不僅僅可以用作讀寫分離,以及分表分庫、容災管理,而且可以用于多租戶應用開發、云平臺基礎設施,讓你的架構具備很強的適應性和靈活性,借助于即將發布的MyCAT只能優化模塊,系統的數據訪問瓶頸和熱點一目了然,根據這些統計分析數據,你可以自動或手工調整后端存儲,將不同的表隱射到不同存儲引擎上,而整個應用的代碼一行也不用改變。
MyCAT是在Cobar基礎上發展的版本,兩個顯著提高:
MyCAT架構
事務是弱XA
MyCAT的原理中最重要的一個動詞是“攔截”,它攔截了用戶發來的SQL語句數據庫中間件原理,首先對SQL語句做了一些特定的分析:如分片分析,路由分析、讀寫分離分析、緩存分析等,然后將此SQL發往后端的真實數據庫,并將返回的結果做適當的處理,最終再返回給用戶。
MyCAT對自身不支持的SQL語句提供了一種解決方案——在要執行的SQL語句前添加額外的一段由注解SQL組織的代碼,這樣SQL就能正確執行,這段代碼稱之為“注解”。注解的使用相當于對MyCAT不支持的SQL語句做了一層透明代理轉發,直接交給目標的數據節點進行SQL語句執行。
MyCAT自身有類似其他數據庫的管理監控方式,可以通過MySQL命令行,登錄管理端口(9066)執行相應的SQL進行管理,也可以通過jdbc的方式進行遠程連接管理。
HA
MyCAT作為一個代理層中間件,MyCAT系統的高可用設計到MyCAT本身的高可用以及后端MySQL的高可用. 在多數情況下,建議采用MySQL主從復制高可用性配置并交付給MyCAT來完成后端MySQL節點的主從自動切換。
MySQL側的HA
MySQL節點開啟主從復制的配置方案,并將主節點配置為MyCAT的里的,從節點配置為,同時MyCAT內部定期對一個里的所有與節點發起心跳檢測。
正常情況下,MyCAT將第一個作為寫節點,所有的DML SQL會發送此節點。
若MyCAT開啟了讀寫分離,則查詢節點會根據讀寫分離的策略發往(+)執行。
如果第一個宕機,MyCAT會在默認的三次心跳檢測失敗后,自動切換到下一個可用的執行DML SQL語句
當原來配置的MySQL寫節點宕機恢復后,作為從節點,跟隨新的主節點,重新配置主從同步。
MyCAT自身的HA
官方建議是采用基于硬件的負載聚亨或者軟件方式的等。
如果還擔心的穩定性和但節點問題,則可以用的VIP的浮動功能,加以強化。
MyCAT功能和特性
支持SQL 92標準
支持Mysql集群,可以作為Proxy使用
支持JDBC連接多數據庫
支持NoSQL數據庫
支持 sfor mysql集群,-或者 ,提供高可用性分片集群
自動故障切換,高可用性
支持讀寫分離,支持MySQL雙主多從,以及一主多從的模式
支持全局表,數據自動分片到多個節點,用于高效表關聯查詢
支持一致性Hash分片,有效解決分片擴容難題
多平臺支持,部署和試試簡單
支持開發,類似數據庫存儲過程,用于跨分片復雜SQL的人工智能編碼實現
支持NIO與AIO兩種網絡通信機制,下建議AIO,Linux下目前建議NIO
支持MySQL存儲過程調用
以插件的方式支持SQL攔截和改寫
支持自增長逐漸、支持的機制
支持Mysql, ,, SQL , Hive, DB2, 等。
MyCAT目前的項目
MyCAT-:MyCAT核心服務
MyCAT-:MyCAT爬蟲技術
MyCAT-:MyCAT配置中心
MyCAT-:MyCAT大數據處理(暫未更細)
MyCAT-Web:MyCAT監控及web(新版開發中)
MyCAT-:MyCAT負載均衡(暫未更細)
DRDS/TDDL
. .
阿里分布式數據庫DRDS的前身是淘寶分布式數據庫層TDDL,大概在2012年的時候,阿里開始嘗試將TDDL這套體系輸出到阿里云上,也有了一個新的名字:DRDS.
TDDL
Tabao根據自己的業務特點開發了TDDL(Tabao Data Layer, 外號:頭都大了)。主要解決了分庫分表對應用的透明化以及異構數據庫之間的數據復制,它是一個基于集中式配置的jdbc 實現,具有主備,讀寫分離,動態數據庫配置等功能。
TDDL并非獨立的中間件,只能算作中間層,是以Jar包方式提供給應用調用。屬于JDBC Shard的思想。
TDDL處于業務層和JDBC層中間。
TDDL其實主要可以劃分為3層架構,分別是層,Group層和Atom層。層用于實現分庫分表邏輯,底層多個Group實例。而Group和Atom共同組成了動態數據源,Group層實現了數據庫的/Slave模式的寫分離邏輯,底層持有多個Atom實例。最后Atom層(持有數據源)實現數據庫ip, port, , 等信息的動態推送,以及持有院子的數據源分離的JBoss數據源。
TDDL社區處于停滯狀態,網上可查資源也較少。
RDRS
DRDS/TDDL是阿里巴巴自主研發的分布式數據庫服務。DRDS脫胎于阿里巴巴開源的Cobar分布式數據庫引擎,吸收了Cobar核心的Cobar-Proxy源碼,實現了一套獨立的類似MySQL-Proxy協議的解析端,能夠對傳入的SQL進行解析和處理,對應用程序屏蔽各種復雜的底層DB拓撲結構,獲得單機數據庫一樣的使用體驗,同時借鑒了淘寶TDDL豐富的分布式數據庫實踐經驗,實現了對分布式Join支持,SUM/MAX/COUNT/AVG等聚合函數支持以及排序等函數支持,通過異構索引、小表廣播等解決分布式數據庫使用場景下衍生出的一系列問題,最終形成了完整的分布式數據庫方案。
DRDS在整個阿里系統中所處的位置:
對于很多應用而言,單機數據庫最終都會碰到單機性能上的天花板,在TPS/QPS/內存容量/磁盤容量等等一系列系統資源上會碰到各類限制。DRDS的主要目標就是幫您解決這方面的各類問題,他主要提供了兩個功能,讀寫分離和數據庫切分:
讀寫分離,能夠運行實現一臺機器寫入,多臺機器讀取,這對于讀多寫少的應用,能夠以極低的成本解決系統的瓶頸。
數據庫切分是一個解決系統存儲瓶頸的最終極解決方案,數據庫切分的核心思想其實很簡單,就是分而治之。將數據分散到多臺機器,并保證請求能夠平均的分發到這些機器上,就可以以極低的成本來解決業務的各類性能瓶頸。當然切分也是有代價的,最明顯的代價就是,分布式數據庫會對一些原有單機數據的場景進行限制,因為這些操作,在分布式環境下的延遲或效率非常低效,就算是能夠實現出來,也會因為性能問題而無法使用。
其他功能特性
1、分布式MySQL執行引擎
主要目標是實現與單機數據庫SQL引擎的完全兼容,實現SQL的智能下推,能夠智能分析SQL,解析出那些SQL可以直接下發,那些SQL需要進行優化改造,優化成什么樣,以及路由到哪些實例節點上執行,充分發揮數據庫實例的全部能力,減少網絡之間的數據傳輸量,最終對不同實例處理后的少量結果進行聚合計算返回給應用調用方。這就是分布式SQL引擎的智能下推功能。
分布式引擎的職責包含SQL解析,優化,執行和合并四個流程。
支持市面上幾乎所有的語言(具有MySQL訪問能力的),兼容90%以上MySQL語法。
案例分析:
比如一個簡單的AVG操作,對于一些比較初級的分布式數據庫模型而言,常見做法是把AVG直接下發到所有存儲節點,這樣造成的結果就是語法兼容,語義不兼容,最終拿到的是錯誤結果。而DRDS的智能下推引擎,對SQL的語法做充分的語義兼容性適配,針對AVG操作,只能由引擎將邏輯AVG SQL解析優化為SUM和COUNT的SQL然后進行下推,由底層的數據庫實例節點完成SUM和COUNT計算,充分利用底層節點的計算能力,在引擎層將各個存儲節點的SUM和COUNT結果聚合計算,最終計算出AVG。
2.在線平滑擴容
在線數據擴容的重點在于“在線”兩字,也就是用戶不需要停止業務進行割接操作,直接就可以添加新的RDS節點到集群中,實現無縫的自由擴展。RDRS則將整個擴容過程分為幾個階段,包括全量遷移,增量同步,切換數據庫等幾個步驟。數據會提前進行搬遷,并進行增量并行同步一段時間,因此,我們可以在非常短的時間內(秒級別)完成數據庫的最終擴容切換工作,對業務沒有影響。
3.小表廣播
在一些大的業務表進行了切分后,總會存在一些表的數據量不大,更新量也不大的原始信息表。這些表往往會與我們的切分后大表進行join操作,這種操作物理上就會造成分布式join查詢,效率從整體上會比較地下。針對這種分布式join的場景,開發了OETL專用工具來進行小表廣播,將原信息表的所有數據(包括增量更新)全部自動的廣播到大表的機器上,這樣,就可以讓原來的分布式查詢變成單機本地查詢了。
4.全局唯一ID
DRDS 功能的目標只是為了保證數據的全局唯一,雖然基本上是按時間序列獲取的,但并不全局有序。
5.異構索引
解決分布式場景下數據拆分維度和數據查詢使用維度不一致導致的低效問題。
當數據表被拆分為多個分庫分表時,數據在分庫分表的分布規則就固定了。但是通常數據的業務使用場景非常復雜,如果數據的查詢維度和數據拆分分布的規則一直,單條SQL會在一個分庫分表上執行;如果數據的查詢使用維度和數據拆分分布的規格不一致,單條SQL可能在多個分庫分表上執行,出現跨庫查詢,跨庫查詢會增加IO成本,查詢效率必然下降。
解決這個問題的思路還是分布式數據庫的一貫原則,讓SQL執行在單庫上完成,實際采用的方式就是用“空間換效率”的方案,也就是將同一份數據表,冗余存儲多份,按照不同的業務使用場景進行拆分,保持拆分維度和使用維度統一,而多份數據之間會實時數據復制以解決數據一致性問題,這就是“異構索引”方案。當然異構索引表不能無限制濫用,過多的異構索引表會影響同步效率,對源數據表造成同步壓力。
其他同款中間件
Altas, , , CDS, DDB, 等等。
Atlas
Qihoo 360
Web平臺部基礎架構團隊開發維護的一個基于MySQL協議的數據中間層項目,它是在mysql-proxy 0.8.2版本上對其進行優化,增加了一些新的功能特性。
Atlas是一個位于應用程序與MySQL之間,它實現了MySQL的客戶端和服務端協議,作為服務端與應用程序通訊,同時作為客戶端與MySQL通訊。它對應用程序屏蔽了DB的細節。
Altas不能實現分布式分表,所有的字表必須在同一臺DB的同一個里且所有的字表必須實現建好,Altas沒有自動建表的功能。
Baidu
其優點:分庫分表與應用脫離,分庫表如同使用單庫表一樣,減少db連接數壓力,熱重啟配置,可水平擴容,遵守MySQL原生協議,讀寫分離,無語言限制,, c, Java都可以使用服務器通過管理命令可以查看,如連接數,線程池,結點等,并可以調整采用的分庫分表腳本進行自定義分庫表,相當的靈活。
(開源版已停止維護)
CDS
JD. .
CDS是一款基于客戶端開發的分庫分表中間件產品,實現了JDBC標準API,支持分庫分表,讀寫分離和數據運維等諸多共,提供高性能,高并發和高可靠的海量數據路由存取服務,業務系統可近乎零成本進行介入,目前支持MySQL, 和SQL .
(架構上和Cobar,MyCAT相似,直接采用jdbc對接,沒有實現類似MySQL協議,沒有NIO,AIO,SQL 模塊采用, Sql解析器有:druid>>.)
DDB
豬場. .
DDB經歷了三次服務模式的重大更迭:模式->Proxy模式->云模式。
模式:基于JDBC驅動訪問,提供一個db.jar, 和TDDL類似, 位于應用層和JDBC之間.
Proxy模式:在DDB中搭建了一組代理服務器來提供標準的MySQL服務,在代理服務器內部實現分庫分表的邏輯。應用通過標準數據庫驅動訪問DDB Proxy, Proxy內部通過MySQL解碼器將請求還原為SQL, 并由DDB 執行得到結果。
私有云模式:基于網易私有云開發的一套平臺化管理工具, 將DDB原先的功能打散,一部分分庫相關功能集成到proxy中,如分庫管理、表管理、用戶管理等,一部分中心化功能集成到中,如報警監控,此外,中提供了一鍵部署、自動和手動備份,版本管理等平臺化功能。