事務的定義:數據庫
事務(Transaction)是由一系列對系統中數據進行訪問與更新的操做所組成的一個程序執行邏輯單元(Unit),狹義上的事務特指數據庫事務。服務器
事務的做用:網絡
當多個應用程序併發訪問數據庫時,事務能夠在這些應用程序之間提供一個隔離方法,以防止彼此的操做相互干擾。架構
事務爲數據庫操做序列提供了一個從失敗中恢復到正常狀態的方法,同時提供了數據庫即便在異常狀態下仍能保持數據一致性的方法。併發
事務具備四個特性,分別是原子性(Atomicity)、一致性(Consistency)、隔離性(Isolation)和持久性(Durability),簡稱爲事務的ACID特性。異步
事務的原子性是指事務必須是一個原子的操做序列單元。事務中包含的各項操做在一次執行過程當中,要麼所有執行,要麼所有不執行。分佈式
任何一項操做失敗都將致使整個事務失敗,同時其餘已經被執行的操做都將被撤銷並回滾。只有全部的操做所有成功,整個事務纔算是成功完成。性能
事務的一致性是指事務的執行不能破壞數據庫數據的完整性和一致性,一個事務在執行先後,數據庫都必須處於一致性狀態。換句話說,事務的執行結果必須是使數據庫從一個一致性狀態轉變到另外一個一致性狀態。網站
舉個例子搜索引擎
銀行的轉帳操做就是一個事務。假設A和B原來帳戶都有100元。此時A轉帳給B50元,轉帳結束後,應該是A帳戶減去50元變成50元,B帳戶增長50元變成150元。A、B的帳戶總和仍是200元。轉帳先後,數據庫就是從一個一致性狀態(A100元,B100元,A、B共200元)轉變到另外一個一致性狀態(A50元,B150元,A、B共200元)。假設轉帳結束後只扣了A帳戶,沒有增長B帳戶,這時數據庫就處於不一致的狀態。
事務的隔離性是指在併發環境中,併發的事務是相互隔離的,事務之間互不干擾。
在標準的SQL規範中,定義的4個事務隔離級別,不一樣隔離級別對事務的處理不一樣。4個隔離級別分別是:未受權讀取、受權讀取、可重複讀取和串行化。
下表展現了不一樣隔離級別下事務訪問數據的差別
隔離級別 | 髒讀 | 可重複讀 | 幻讀 |
---|---|---|---|
未受權讀取 | 存在 | 不能夠 | 存在 |
受權讀取 | 不存在 | 不能夠 | 存在 |
可重複讀取 | 不存在 | 能夠 | 存在 |
串行化 | 不存在 | 能夠 | 不存在 |
以上4個級別的隔離性依次加強,分別解決不一樣的問題。事務隔離級別越高,就越能保證數據的完整性和一致性,但同時對併發性能的影響也越大。
一般,對於絕大多數的應用來講,能夠優先考慮將數據庫系統的隔離級別設置爲受權讀取,這可以在避免髒讀的同時保證較好的併發性能。儘管這種事務隔離級別會致使不可重複讀、幻讀和第二類丟失更新等併發問題,但較爲科學的作法是在可能出現這類問題的個別場合中,由應用程序主動採用悲觀鎖或樂觀鎖來進行事務控制。
事務的持久性又稱爲永久性,是指一個事務一旦提交,對數據庫中對應數據的狀態變動就應該是永久性的。即便發生系統崩潰或機器宕機等故障,只要數據庫可以從新啓動,那麼必定可以將其恢復到事務成功結束時的狀態。
事務在分佈式計算領域也獲得了普遍的應用。在單機數據庫中,咱們很容易可以實現一套知足ACID特性的事務處理系統,可是在分佈式數據庫中,數據分散在各臺不一樣的機器上,如何對這些數據進行分佈式事務處理具備很是大的挑戰。
分佈式事務是指事務的參與者、支持事務的服務器、資源服務器以及事務管理器分別位於分佈式系統的不一樣節點之上。一般一個分佈式事務會涉及對多個數據源或業務系統的操做。
舉個例子來講明分佈式事務。一個最典型的分佈式事務場景是跨行的轉帳操做。該操做涉及調用兩個異地的銀行服務。其中一個是本地銀行提供的取款服務,另外一個是目標銀行提供的存款服務,這兩個服務自己是無狀態且相互獨立的,共同構成了一個完整的分佈式事務。取款和存款兩個步驟要麼都執行,要麼都不執行。不然,若是從本地銀行取款成功,可是由於某種緣由存款服務失敗了,那麼必須回滾到取款以前的狀態,不然就會致使數據不一致。
從上面的例子能夠看出,一個分佈式事務能夠看做是由多個分佈式操做序列組成的,例如上面例子中的取款服務和存款服務,一般能夠把這一系列分佈式的操做序列稱爲子事務。因爲分佈式事務中,各個子事務的執行是分佈式的,所以要實現一種可以保證ACID特性的分佈式事務處理系統就顯得格外複雜。
CAP定理:
一個分佈式系統不可能同時知足一致性(C:Consistency)、可用性(A:Availability)和分區容錯性(P:Partition tolerance)這三個基本要求,最多隻能知足其中的兩項。
在分佈式環境中,一致性是指數據在多個副本之間是否可以保持一致的特性(這點跟ACID中的一致性含義不一樣)。
對於一個將數據副本分佈在不一樣節點上的分佈式系統來講,若是對第一個節點的數據進行了更新操做而且更新成功後,卻沒有使得第二個節點上的數據獲得相應的更新,因而在對第二個節點的數據進行讀取操做時,獲取的依然是更新前的數據(稱爲髒數據),這就是典型的分佈式數據不一致狀況。在分佈式系統中,若是可以作到針對一個數據項的更新操做執行成功後,全部的用戶都能讀取到最新的值,那麼這樣的系統就被認爲具備強一致性(或嚴格的一致性)。
可用性是指系統提供的服務必須一直處於可用的狀態,對於用戶的每個操做請求老是可以在有限的時間內返回結果,若是超過了這個時間範圍,那麼系統就被認爲是不可用的。
『有限的時間內』是一個在系統設計之初就設定好的運行指標,不一樣的系統會有很大的差異。好比對於一個在線搜索引擎來講,一般在0.5秒內須要給出用戶搜索關鍵詞對應的檢索結果。而對應Hive來講,一次正常的查詢時間可能在20秒到30秒之間。
『返回結果』是可用性的另外一個很是重要的指標,它要求系統在完成對用戶請求的處理後,返回一個正常的響應結果。正常的響應結果一般可以明確地反映出對請求的處理結果,及成功或失敗,而不是一個讓用戶感到困惑的返回結果。
讓咱們再來看看上面提到的在線搜索引擎的例子,若是用戶輸入指定的搜索關鍵詞後,返回的結果是一個系統錯誤,好比"OutOfMemoryErroe"或"System Has Crashed"等提示語,那麼咱們認爲此時系統是不可用的。
分區容錯性要求一個分佈式系統須要具有以下特性:分佈式系統在遇到任何網絡分區故障的時候,仍然可以保證對外提供知足一致性和可用性的服務,除非是整個網絡環境都發生了故障。
網絡分區是指在分佈式系統中,不一樣的節點分佈在不一樣的子網絡(機房或異地網絡等)中,因爲一些特殊的緣由致使這些子網絡之間出現網絡不連通的情況,但各個子網絡的內部網絡是正常的,從而致使整個系統的網絡環境被切分紅了若干個孤立的區域。
以上就是對CAP定理中一致性、可用性和分區容錯性的講解。
既然一個分佈式系統沒法同時知足上述三個要求,而只能知足其中的兩項,所以在對CAP定理應用時,咱們就須要拋棄其中的一項,下表是拋棄CAP中任意一項特性的場景說明。
CAP | 說明 |
---|---|
放棄P | 若是但願可以避免系統出現分區容錯性問題,一種較爲簡單的作法是將全部的數據(或者僅僅是哪些與事務相關的數據)都放在一個分佈式節點上。這樣作雖然沒法100%保證系統不會出錯,但至少不會碰到因爲網絡分區帶來的負面影響。但同時須要注意的是,放棄P的同時也就意味着放棄了系統的可擴展性 |
放棄A | 一旦系統遇到網絡分區或其餘故障或爲了保證一致性時,放棄可用性,那麼受到影響的服務須要等待必定的時間,所以在等待期間系統沒法對外提供正常的服務,即不可用 |
放棄C | 這裏所說的放棄一致性,實際上指的是放棄數據的強一致性,而保留數據的最終一致性。這樣的系統沒法保證數據保持實時的一致性,可是可以承諾的是,數據最終會達到一個一致的狀態。 |
須要明確的一點是:對於一個分佈式系統而言,分區容錯性能夠說是一個最基本的要求。由於既然是一個分佈式系統,那麼分佈式系統中的組件必然須要被部署到不一樣的節點,不然也就無所謂的分佈式系統了,所以必然出現子網絡。而對於分佈式系統而言,網絡問題又是一個一定會出現的異常狀況,所以分區容錯性也就成爲了一個分佈式系統必然須要面對和解決的問題。所以系統架構師每每須要把精力花在如何根據業務特色在C(一致性)和A(可用性)之間尋求平衡。
BASE是Basically Available(基本可用)、Soft state(軟狀態)和Eventually consistent(最終一致性)三個短語的簡寫。BASE是對CAP中一致性和可用性權衡的結果,其來源於對大規模互聯網系統分佈式實踐的總結,是基於CAP定理逐步演化而來的,其核心思想是即便沒法作到強一致性,但每一個應用均可以根據自身的業務特色,採用適當的方法來使系統達到最終一致性。接下來,咱們着重對BASE中的三要素進行講解。
基本可用是指分佈式系統在出現不可預知故障的時候,容許損失部分可用性——但請注意,這毫不等價於系統不可用。一下就是兩個"基本可用"的例子。
響應時間上的損失:正常狀況下,一個在線搜索引擎須要在0.5秒以內返回給用戶相應的查詢結果,但因爲出現故障(好比系統部分機房發生斷電或斷網故障),查詢結果的響應時間增長到了1~2秒。
功能上的損失:正常狀況下,在一個電子商務網站(好比淘寶)上購物,消費者幾乎可以順利地完成每一筆訂單。但在一些節日大促購物高峯的時候(好比雙11、雙十二),因爲消費者的購物行爲激增,爲了保護系統的穩定性(或者保證一致性),部分消費者可能會被引導到一個降級頁面,以下:
軟狀態是指容許系統中的數據存在中間狀態,並認爲該中間狀態的存在不會影響系統的總體可用性,即容許系統在不一樣的數據副本之間進行數據同步的過程存在延時。
最終一致性強調的是系統中全部的數據副本,在通過一段時間的同步後,最終可以達到一個一致的狀態。所以,最終一致性的本質是須要系統保證最終數據可以達到一致,而不須要實時保證系統數據的強一致性。
最終一致性是一種特殊的弱一致性:系統可以保證在沒有其餘新的更新操做的狀況下,數據最終必定可以達到一致的狀態,所以全部客戶端對系統的數據訪問都可以獲取到最新的值。同時,在沒有發生故障的前提下,數據到達一致狀態的時間延遲,取決於網絡延遲、系統負載和數據複製方案設計等因素。
在實際工程實踐中,最終一致性存在一下五類主要變種。
以上就是最終一致性的五種常見的變種,在實際系統實踐中,能夠將其中的若干個變種互相結合起來,以構建一個具備最終一致性特性的分佈式系統。事實上,最終一致性並非只有那些大型分佈式系統才涉及的特性,許多現代的關係型數據庫都採用了最終一致性模型。在現代關係型數據庫中(好比MySQL和PostgreSQL),大多都會採用同步或異步方式來實現主備數據複製技術。在同步方式中,數據的複製過程一般是更新事務的一部分,所以在事務完成後,主備數據庫的數據就會達到一致。而在異步方式中,備庫的更新每每會存在延時,這取決於事務日誌在主備數據庫之間傳輸的時間長短。若是傳輸時間過長或者甚至在日誌傳輸過程當中出現異常致使沒法及時將事務應用到備庫上,那麼很顯然,從備庫中讀取的數據將是舊的,所以就出現了數據不一致的狀況。固然,不管是採用屢次重試仍是人爲數據訂正,關係型數據庫仍是可以保證最終數據達到一致,這就是系統提供最終一致性保證的經典案例。
歡迎關注公衆號: FullStackPlan 獲取更多幹貨哦~