阿裏雲自研新一代企業雲數據庫POLARDB背後的技術
從2008年到2018年,阿裏巴巴的數據庫技術已經發展了10年的時間,10年的時間從AliSQL到RDS,再到自研POLARDB,阿裏巴巴數據庫技術得到了極大的提升。那麽在阿裏雲自研新一代企業雲數據庫POLARDB背後有哪些技術呢?本文中,阿裏雲數據庫事業部總經理鳴嵩就為大家進行分享。
阿裏巴巴數據庫發展的十年歷程
首先介紹一下阿裏巴巴數據庫發展的十年歷程。阿裏巴巴數據庫技術發展源於2008年所做的去“IOE“這件事情。之前阿裏巴巴所使用的是商用數據庫比如Oracle,阿裏巴巴之所以要做“去O”是因為馬老師看了財務報表之後發現如果繼續使用Oracle等商用數據庫,阿裏巴巴的盈利就會補不上數據庫的費用。於是,從2008年開始進行“去O”,當時使用的是MySQL開源分支上自建的一個分支——AliSQL,在其上放了電商場景中的像秒殺之類的各種補丁。基於AliSQL數據庫內核,阿裏巴巴在2011年開始研發雲RDS產品,最開始只有MySQL服務,後來增加了SQL Server等數據庫服務。在2018年,阿裏雲數據庫團隊推出了自研的POLARDB數據庫產品,POLARDB在2014年開始研發,2017年在北京宣布開始公測,在2018年4月份正式商業化。與此同時RDS數據庫實例數正式突破20萬,占國內雲數據庫市場份額的50%。
因為阿裏雲RDS具有20萬數據庫實例,在服務這個20萬實例以及背後的8萬客戶的過程中,阿裏雲也發現了用戶使用數據庫過程中的痛點和需求。因此,阿裏雲設計了POLARDB下一代數據庫產品來解決用戶的這些痛點和需求。用戶的痛點一部分和數據庫的能力和容量有關,比如數據庫在單機上最大規模是3T,這還是因為一臺機器所能插下的SSD盤有限,當用戶的數據存儲量超過3T,那麽用戶就需要自己做分布式以及分庫分表這些事情,這使得用戶開發的要求大大提高。過去的MySQL寫性能大概是2萬TPS,而這樣的性能對於很多用戶而言是不夠的,那麽如何使一臺數據庫擁有更多的寫入吞吐和讀吞吐成為了需要解決的問題。此外還有並發的問題,因為用戶在雲上可能有幾百個ECS客戶端共同訪問一個數據庫,那麽如何解決這種幾百個並發之下的數據庫性能也是一個問題。此外,主從復制也是一個問題,在雲上需要兩個實例做主從復制,但是基於Binlog的主從復制卻帶來了很多問題,比如DDL同步時間過長,主從復制中斷會造成數據不一致。第三大類問題與備份相關,當數據庫的容量達到一定程度,備份就成為一個難題,因為對於塊進行備份需要進行上鎖然後拷貝出來,這樣的過程非常慢。復雜SQL,用戶數據量增大之後,一些報表的需求就會需要執行很長時間,而希望這樣的復雜SQL變成分鐘級的操作。
而今天,阿裏雲是帶著用戶對於數據庫的需求來設計下一代數據庫POLARDB的。POLARDB是阿裏雲新一代企業級雲原生關系型數據庫,100%兼容MySQL協議,最大容量可以達到100T。其彈性擴展能力非常強,可以從10G擴展到100T,可以從4核擴展到60核,可以從1個節點擴展到16個節點,是一個擴展性非常強的數據庫集群。
POLARDB的架構設計
POLARDB整體架構可以分為四層,第一層是POLAR Proxy層,這一層解決的問題就是POLARDB是一寫多讀的數據庫,最多可以達到16個節點,但是讓用戶去管理16個節點就變得非常復雜了。POLAR Proxy層就是讓用戶只看到一個endpoint,只看到一個VIP去訪問數據庫。讀寫分離等都可以在這一層實現。第二層就是關系數據庫引擎層,第三層和第四層就是存儲層,第三層是文件系統,第四層是存儲擴展能力。
接下來將會自底向上介紹POLARDB的設計,最底下是分布式存儲和文件系統層,這一層是為了解決容量問題。因為單機容量有限,但是如果想要實現100T的數據庫就必須將數據存儲到多臺機器上面,這就是為什麽需要分布式存儲層的原因。數據庫不僅僅使用存儲,還需要使用文件,因此在存儲層之上還需要構建一層文件系統。在存儲層裏面,數據使用了三副本,提升了數據的可靠性和可用性。在存儲層還是用了新的硬件,這使得優勢更加明顯,使得數據庫性能能夠實現數量級上的提升。軟件方面也做了操作系統、用戶態文件系統以及用戶態網絡協議棧等優化。分布式存儲層使得容量最高可以擴展到100TB,可以使數據庫文件分布在幾十臺機器裏面,可以用這些機器的SSD來存儲數據和提高I/O吞吐。其次,共享存儲實現了Serverless計費。之前購買數據庫時就需要預定存儲容量,但是在POLARDB上,因為存儲時分布式的,因此可以做到存儲按照使用付費,幫助用戶節省了存儲開銷。實現了無鎖備份,之前的數據庫備份是邏輯備份,有可能鎖表也有可能鎖頁,所以性能很慢。而POLARDB是在存儲層實現快照備份,在決定備份的時候直接生成一個只讀快照,一分鐘之內就實現了百T數據庫的備份。
數據庫引擎層所實現的核心功能是基於一份存儲實現多節點掛載的,一寫多讀能力。這裏介紹一下“一寫多讀”,大家都知道讀寫分離技術,其是說數據庫主實例負責寫,為了線性擴展讀能力只能在主實例上掛載多個只讀實例,通過將讀邏輯復制到只讀實例中,在只讀實例中提升寫性能,只讀實例越多,整個集群的讀能力就越強,其缺點是每個只讀實例都需要一個存儲副本,實例之間通過Binlog復制實現數據拷貝。而在POLARDB中實現了突破,在主實例和多個讀實例之間共享一份存儲,這就意味著存儲成本大大降低,並且只讀實例越多,節省的成本就越多。此外,還使得只讀實例的節點擴充變得更快,因為在生成只讀實例的時候不需要進行數據拷貝,也就是通過技術帶來了極速的彈性擴展能力。
接下來介紹如何實現多個節點共享一份數據庫存儲,其實類似的技術在全球也沒有幾家公司擁有。首先回顧一下數據庫原理,假設原本有5個事務在執行,他們是T1~T5,他們在提交的時候會同步地寫,代表事務的提交。但是之後更新到內存中後並不會立刻刷新到磁盤文件中,也就是說數據文件的更新是異步的。在POLARDB中,由於刷新數據文件是異步的,因此在共享存儲中僅刷新了T1的狀態,其他的事務仍然存在於主實例的Buffer Pool裏面。只讀實例會不斷地從磁盤中拉取RedoLog,將狀態不停地拉到內存當中去,將事務保存到內存的Hash表中去,這時候如果有請求下來,如果命中Buffer Pool就讀取,否則會到磁盤中讀取較老的數據文件中的版本號,然後與內存表中的狀態合並之後放到Buffer Pool並返回給用戶。簡單而言,只讀實例通過讀取共享存儲中的Redo文件在內存中維護一個數據庫,這個內存數據庫只維護近期的更新,而又會從存儲中讀取老數據,在內存中完成實時合並,並最終返回給用戶。
前面的過程較為通用,有些邊緣情況是數據庫系統所必須考慮的。所謂邊緣情況就是過去5分鐘內緩存了RedoLog,這些會占據內存空間,所以需要定期刪除數據。那麽這就出現了一個問題,如果只讀節點刪除數據的頻率過高,就有可能導致部分RedoLog的丟失。為了避免以上情況的發生,就需要主實例定期將自己Checkpoint的LSN發送給所有的只讀實例,只讀實例就會註意不能夠刪除Checkpoint後的任何RedoLog,避免產生數據空隙。第二個問題就是主庫寫數據文件也不能過於頻繁,因為主庫寫數據過於頻繁,也會導致只讀庫快照隔離出現問題。為此,從庫需要定期將自己Snapshot的狀態發送給主庫,主庫將所有只讀節點的Snapshot版本取最小作為自己刷臟的閾值,如果某一個只讀實例的Snapshot版本太老了就可以將其踢掉。
基於共享存儲實現“一寫多讀”不僅帶來了只讀實例的橫向擴展能力,此外還大大地減少了在主實例上執行DDL,只讀實例上執行DDL的時間間隔。今天,POLARDB可以做到僅需要極短的時間就可以將DDL同步到所有只讀實例上,主庫在執行DDL的同時,共享存儲中的數據文件也在不斷地進行修改,當主庫執行完DDL之後,只需要將自己庫的元信息進行修改,從庫就立即可見,能達到低於10毫秒的延遲。
在“一寫多讀”之上就是智能的接入層,也就是Proxy層。因為POLARDB可以有多個節點,但是只希望用戶看到一個端口進行訪問,這時候就需要Proxy層發揮作用了。Proxy層將負責負載均衡、連接管理以及安全管理。通過Proxy層實現了統一的集群入口,一個endpoint訪問所有的數據節點,並且可以在其上實現白名單的安全機制。
POLARDB產品進展
最後為大家釋放三個重磅信息。
首先,從POLARDB 2017年在北京發布到2018年宣布正式商業化,經過一年的發展時間,POLARDB的寫入時間已經比AWS速度快2倍,在各個數量內核的情況下寫入的TPS都是AWS的2倍。
其次,在Proxy層實現了會話單調一致性讀寫分離,這個功能使得用戶感受不到讀寫分離所帶來的主庫和從庫之間的延遲,使得用戶就像使用一個數據庫一樣地使用POLARDB。
第三個亮點就是SQL加速,這是POLARDB團隊在過去一年的時間內服務了200多家企業用戶後得到的需求。因為用戶的數據庫容量變大了,數據表和數據量都變大了,也需要查詢變得更快。在這樣的需求的啟發下,POLARDB就實現了SQL加速。其原理就是在多個POLARDB只讀實例中並發地加載同一個Snapshot數據,在中間層完成MPP運算。目前的效果是對於TPC-H和TPC-DS可以完美地支持,對於SQL查詢速度提升了8到14倍,而未來將會進一步加快SQL查詢速度。
阿裏雲自研新一代企業雲數據庫POLARDB背後的技術