3.redis事務概念
redis事務與監控
在redis中它的事務與批處理非常相似
Redis中的事務(transaction)是一組命令的集合。事務同命令一樣都是Redis的最小執行單位,一個事務中的命令要麼都執行,要麼都不執行。事務的應用非常普遍,如銀行轉賬過程中A給B匯款,首先系統從A的賬戶中將錢划走,然後向B的賬戶增加相應的金額。這兩個步驟必須屬於同一個事務,要麼全執行,要麼全不執行。否則只執行第一步,錢就憑空消失了,這顯然讓人無法接受。
Redis 事務可以一次執行多個命令, 並且帶有以下兩個重要的保證:
- 事務是一個單獨的隔離操作,事務中的所有命令都會序列化、按順序地執行。事務在執行的過程中,不會被其他客戶端傳送來的命令請求所打斷。
- 事務是一個原子操作:事務中的命令要麼全部被執行,要麼全部都不執行
事務的三個步驟
- 開啟事務:以MULTI開啟一個事務。
- 命令入隊:將多個命令新增到命令佇列中,接到這些命令不會立即執行,而是放到等待執行的事務佇列中。
- 執行事務:有EXEC執行事務。(或者DISCARD取消執行)
MULTI | 標記一個事務塊的開始。 |
---|---|
EXEC | 執行所有事務塊內的命令。 |
DISCARD | 取消事務,放棄執行事務塊內的所有命令。 |
UNWATCH | 取消 WATCH 命令對所有 key 的監視。 |
WATCH key [key ...] | 監視一個(或多個) key ,如果在事務執行之前這個(或這些) key 被其他命令所改動,那麼事務將被打斷 |
常見案例:
正常執行:指的是佇列的中所有操作全部都會執行
全部取消:指的是佇列中的所有操作全部都會被取消
執行:DISCARD
全體連坐:如果指令集中有一條在加入佇列時報錯,則佇列中的所有指令全部取消。指的是有語法錯誤
冤有頭債有主:如果指令已經加入到佇列中,但執行失敗,只有當前指令失敗,其它繼續執行。指的是已經新增到佇列但是執行失敗
watch監控
watch監控表示對需要操作的key新增一個樂觀鎖,防止另一個使用者進行修改,導致結果錯誤。
悲觀鎖:
顧名思義,就是很悲觀,每次去拿資料的時候都認為別人會修改,所以每次在拿資料的時候都會上鎖,這樣別人想拿這個資料就會被block直到它拿到鎖。傳統的關係型資料庫裡面就用到了很多這種鎖,比如行鎖,表鎖,讀鎖,寫鎖等,都是在操作之前先上鎖。
樂觀鎖:
顧名思義,就是很樂觀,每次去拿資料的時候都認為別人不會修改,所以不會上鎖,但是在更新的時候會判斷一下在此期間別人有沒有去更新這個資料,可以使用版本號等機制。提交的版本號必須大於當前版本號才可以提交。
案例:
圖一
圖二
圖解:當圖一開啟監控key “money”,開啟事務的時候加入拿著的是版本1,在事務執行過程中圖二第二個客戶端修改了版本一的指,現在庫中存在的是版本二,而incrby money 200 在執行exec的時候我們的是版本二,樂觀鎖在這個時候並不允許我們提交,因為當前庫中版本是2而我們提交的版本也是2。提交的版本號必須大於當前版本號才可以提交。!!!!!!!!!!
通過watch命令在事務執行之前監控了多個keys,倘若在watch之後有任何的key的值發生了變化,exec命令執行的事務會被取消。
事務的三個特性
單獨的隔離性:事務中的所有的命令都會序列化,按順序執行,事務在執行過程中,不會被其它客戶端傳送過來的命令請求所打斷。
沒有隔離級別的概念:佇列中的命令沒有提交之前都不會實際的被執行,因為事務提交前任何指令都不會被實際執行,也就不存在”事務內的查詢要看到事務裡的更新。
不保證原子性:redis同一個事務中如果有一條命令執行失敗,其後的命令仍然會被執行,沒有回滾