1. 程式人生 > >淺析postgresql數據庫事務及行鎖特征

淺析postgresql數據庫事務及行鎖特征

影像 關系 重新 TP 工作 之一 date comm oracl

開源數據庫領域,postgresql以其優越的性能、功能及良好的穩定性排名首位可謂當之無愧,尤其是對高並發的支持可謂匠心獨具。而優越的性能和穩定性,究其根本無非是良好的基礎架構,本文將對其性能和穩定性有著良好支撐的事務及鎖機制進行探討,並結合實際測試,以真切說明和證明其特點。

1、可在事務中的DDL

postgresql中,DDL語句可以在事務中,既可以提交,也可以回滾,這在實際工作中,不然具備很大的實際意義,也會給工作帶來方便和安全,如下圖所示:

技術分享圖片

技術分享圖片

2、mvcc

postgresql中,很好的實現了mvcc功能,postgresql中mvcc實現了讀寫不阻塞,同時也說明了相同數據行上的寫寫阻塞,如下圖所示:

session1:開始一個事務,事務中insert into t1中一條數據,但不提交,也不會滾,如圖:

技術分享圖片

session2:此時另開一個會話,連接到相同的用戶和數據庫,也insert into t1中同樣的數據行,此時,該事務被阻塞,表現為在該會話中掛住,如圖:

技術分享圖片

session1:在回到session1中,此時發出commit命令,如圖:

技術分享圖片

session2:在回到session2中,此時,因為session1中的相同數據被成功insert並提交,因為t1表c2字段上有主鍵,因此,session2中的insert into t1事務失敗,並報錯,如圖:

技術分享圖片

3、mvcc實現機制

雖然目前的關系庫都實現了mvcc功能,但因為底層架構和設計的因素,有些導致系統穩定性和性能方面的不足。而postgresql中,該功能的實現可謂非常巧妙,這也是postgresql號稱免費版的Oracle的重要因素之一。因為mvcc功能,postgresql中相同數據行的讀寫不阻塞,而寫寫會阻塞和等待。那麽,postgresql中是如何實現了mvcc功能的呢?postgresql中,主要通過數據行上的幾個隱含字段實現了mvcc功能,他們分別是:xmin,amax,cmin,cmax,如下圖所示:

session1:在此會話中,開始一個事務,並在事務中分別update字段c1=1和delete字段c1=2的兩個數據行,期間分別查詢t1中每個數據行的數據和隱含字段:

技術分享圖片

session2:打開另一個會話session2,並連接到相同的數據庫和用戶,在session1中delete、update、commit操作後,分別查詢表t1中數據行和幾個隱藏列的值,可以發現:session1中,update數據行前insert的數據行,只填寫了xmin隱藏列的值,並且是當時的xid;update操作時,將舊數據行的xmax填寫為update事務的xid,並重新insert一行新數據,且將新數據行的xmin填寫為當前事務xid,session1中update後查到的數據是新數據行(xmin為當前事務xid),而因為session1中update未提交,session2中查到的數據行為舊數據行(xmin為之前第一次insert時的xid,xmax為當前事務的xid);delete操作時,會將舊數據行的xmax填寫為當前事務的xid,在session1中查詢時,因為已經刪除,已經查不到該數據行,而在session2中,因為session1中的delete操作並未提交,所以看到的是刪除前的數據行,但此時看到舊數據行的xmax已被填寫為session1中事務的xid。session1中提交後,session2中再也看不到舊數據行,只看到了update和delete後的結果,如圖所示:

技術分享圖片

這樣postgresql通過數據行的幾個隱藏列巧妙的實現了mvcc功能;而同樣的mvcc功能,oracle雖然實現的很優雅,但需要到undo段中獲取改變向量以重構數據塊的前影像,這也許會消耗掉一部分系統資源;mysql的innodb中,雖然不需要重構數據塊前影像,但也需要到undo空間獲取舊的數據行;db2和sql server庫中,雖然也實現了類似mvcc功能,但db2中,通過redo信息重構數據前影像,這可能會使得redo變得過熱和擁塞,sql server則是將前影像信息放到了temp數據庫中。postgresql中mvcc的功能雖然實現的巧妙,且在獲取舊數據行的過程中不會消耗太多系統資源,但也存在不同版本數據行都存在數據段內的情況,當這種舊數據太多時,可能會帶來性能上的問題,清理這些舊數據時,也可能會導致系統負載和性能的抖動或顛簸。

4、免費版的Oracle當之無愧

postgresql除了行鎖實現機制外,事務級別和oracle也非常相似,雖然支持四個標準事務級別的設置,但postgresql實際上只支持兩個事務級別:read committed和serializable。此外,postgresql還支持完備的約束,索引,多種語言的函數和過程編碼實現,且為進程模型,幾乎可以在每個流行的平臺上安裝使用等,這些特點和功能,足可以說其為免費版的oracle當之無愧。

淺析postgresql數據庫事務及行鎖特征