溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊(cè)×
其他方式登錄
點(diǎn)擊 登錄注冊(cè) 即表示同意《億速云用戶服務(wù)條款》

redis中事務(wù)命令的介紹和使用

發(fā)布時(shí)間:2020-06-23 14:09:43 來(lái)源:億速云 閱讀:110 作者:元一 欄目:關(guān)系型數(shù)據(jù)庫(kù)

這篇文章將為大家詳細(xì)講解有關(guān)redis中事務(wù)命令的介紹和使用,文章內(nèi)容質(zhì)量較高,因此分享給大家做個(gè)參考,希望大家閱讀完這篇文章后可以有所收獲。

一、概述:

Redis 事務(wù)的本質(zhì)是一組命令的集合。事務(wù)支持一次執(zhí)行多個(gè)命令,一個(gè)事務(wù)中所有命令都會(huì)被序列化。在事務(wù)執(zhí)行過(guò)程,會(huì)按照順序串行化執(zhí)行隊(duì)列中的命令,其他客戶端提交的命令請(qǐng)求不會(huì)插入到事務(wù)執(zhí)行命令序列中。

總結(jié)說(shuō):redis事務(wù)就是一次性、順序性、排他性的執(zhí)行一個(gè)隊(duì)列中的一系列命令。

二、相關(guān)命令列表:

命令原型時(shí)間復(fù)雜度命令描述返回值

M

U

L

T

I


用于標(biāo)記事務(wù)的開(kāi)始,其后執(zhí)行的命令都將被存入命令隊(duì)列,直到執(zhí)行EXEC時(shí),這些命令才會(huì)被原子的執(zhí)行。始終返回OK

E

X

E

C


執(zhí)行在一個(gè)事務(wù)內(nèi)命令隊(duì)列中的所有命令,同時(shí)將當(dāng)前連接的狀態(tài)恢復(fù)為正常狀態(tài),即非事務(wù)狀態(tài)。如果在事務(wù)中執(zhí)行了WATCH命令,那么只有當(dāng)WATCH所監(jiān)控的Keys沒(méi)有被修改的前提下,EXEC命令才能執(zhí)行事務(wù)隊(duì)列中的所有命令,否則EXEC將放棄當(dāng)前事務(wù)中的所有命令。原子性的返回事務(wù)中各條命令的返回結(jié)果。如果在事務(wù)中使用了WATCH,一旦事務(wù)被放棄,EXEC將返回NULL-multi-bulk回復(fù)。

D

I

S

C

A

R

D


回滾事務(wù)隊(duì)列中的所有命令,同時(shí)再將當(dāng)前連接的狀態(tài)恢復(fù)為正常狀態(tài),即非事務(wù)狀態(tài)。如果WATCH命令被使用,該命令將UNWATCH所有的Keys。始終返回OK。

W

A

T

C

H

k

e

y

[key ...]

O(1)在MULTI命令執(zhí)行之前,可以指定待監(jiān)控的Keys,然而在執(zhí)行EXEC之前,如果被監(jiān)控的Keys發(fā)生修改,EXEC將放棄執(zhí)行該事務(wù)隊(duì)列中的所有命令。始終返回OK。

U

N

W

A

T

C

H

O(1)取消當(dāng)前事務(wù)中指定監(jiān)控的Keys,如果執(zhí)行了EXEC或DISCARD命令,則無(wú)需再手工執(zhí)行該命令了,因?yàn)樵诖酥?,事?wù)中所有被監(jiān)控的Keys都將自動(dòng)取消。始終返回OK。

三、命令示例:

1、事務(wù)被正常執(zhí)行:
#在Shell命令行下執(zhí)行Redis的客戶端工具。

 /> redis-cli

#在當(dāng)前連接上啟動(dòng)一個(gè)新的事務(wù)。

redis 127.0.0.1:6379> multi
OK

#執(zhí)行事務(wù)中的第一條命令,從該命令的返回結(jié)果可以看出,該命令并沒(méi)有立即執(zhí)行,而是存于事務(wù)的命令隊(duì)列。

redis 127.0.0.1:6379> incr t1
QUEUED

#又執(zhí)行一個(gè)新的命令,從結(jié)果可以看出,該命令也被存于事務(wù)的命令隊(duì)列。

redis 127.0.0.1:6379> incr t2
QUEUED

#執(zhí)行事務(wù)命令隊(duì)列中的所有命令,從結(jié)果可以看出,隊(duì)列中命令的結(jié)果得到返回。

redis 127.0.0.1:6379> exec
1) (integer) 1
2) (integer) 1

2、 事務(wù)中存在失敗的命令:
#開(kāi)啟一個(gè)新的事務(wù)。

redis 127.0.0.1:6379> multi
OK

#設(shè)置鍵a的值為string類(lèi)型的3。

redis 127.0.0.1:6379> set a 3
QUEUED

#從鍵a所關(guān)聯(lián)的值的頭部彈出元素,由于該值是字符串類(lèi)型,而lpop命令僅能用于List類(lèi)型,因此在執(zhí)行exec命令時(shí),該命令將會(huì)失敗。

redis 127.0.0.1:6379> lpop a
QUEUED

#再次設(shè)置鍵a的值為字符串4。

redis 127.0.0.1:6379> set a 4
QUEUED

#獲取鍵a的值,以便確認(rèn)該值是否被事務(wù)中的第二個(gè)set命令設(shè)置成功。

redis 127.0.0.1:6379> get a
QUEUED

#從結(jié)果中可以看出,事務(wù)中的第二條命令lpop執(zhí)行失敗,而其后的set和get命令均執(zhí)行成功,這一點(diǎn)是Redis的事務(wù)與關(guān)系型數(shù)據(jù)庫(kù)中的事務(wù)之間最為重要的差別。
redis 127.0.0.1:6379> exec
1) OK
2) (error) ERR Operation against a key holding the wrong kind of value
3) OK
4) "4"
3、回滾事務(wù):
#為鍵t2設(shè)置一個(gè)事務(wù)執(zhí)行前的值。

redis 127.0.0.1:6379> set t2 tt
OK

#開(kāi)啟一個(gè)事務(wù)。

redis 127.0.0.1:6379> multi
OK

#在事務(wù)內(nèi)為該鍵設(shè)置一個(gè)新值。

redis 127.0.0.1:6379> set t2 ttnew
QUEUED

#放棄事務(wù)。

redis 127.0.0.1:6379> discard
OK

#查看鍵t2的值,從結(jié)果中可以看出該鍵的值仍為事務(wù)開(kāi)始之前的值。

redis 127.0.0.1:6379> get t2
"tt"

四、WATCH命令和基于CAS的樂(lè)觀鎖:

在Redis的事務(wù)中,WATCH命令可用于提供CAS(check-and-set)功能。假設(shè)我們通過(guò)WATCH命令在事務(wù)執(zhí)行之前監(jiān)控了多個(gè)Keys,倘若在WATCH之后有任何Key的值發(fā)生了變化,EXEC命令執(zhí)行的事務(wù)都將被放棄,同時(shí)返回Null multi-bulk應(yīng)答以通知調(diào)用者事務(wù)執(zhí)行失敗。

例如,我們?cè)俅渭僭O(shè)Redis中并未提供incr命令來(lái)完成鍵值的原子性遞增,如果要實(shí)現(xiàn)該功能,我們只能自行編寫(xiě)相應(yīng)的代碼。其偽碼如下:

      val = GET mykey
      val = val + 1
      SET mykey $val

以上代碼只有在單連接的情況下才可以保證執(zhí)行結(jié)果是正確的,因?yàn)槿绻谕粫r(shí)刻有多個(gè)客戶端在同時(shí)執(zhí)行該段代碼,那么就會(huì)出現(xiàn)多線程程序中經(jīng)常出現(xiàn)的一種錯(cuò)誤場(chǎng)景--競(jìng)態(tài)爭(zhēng)用(race condition)。

比如,客戶端A和B都在同一時(shí)刻讀取了mykey的原有值,假設(shè)該值為10,此后兩個(gè)客戶端又均將該值加一后set回Redis服務(wù)器,這樣就會(huì)導(dǎo)致mykey的結(jié)果為11,而不是我們認(rèn)為的12。為了解決類(lèi)似的問(wèn)題,我們需要借助WATCH命令的幫助,見(jiàn)如下代碼:

      WATCH mykey
      val = GET mykey
      val = val + 1
      MULTI
      SET mykey $val
      EXEC

和此前代碼不同的是,新代碼在獲取mykey的值之前先通過(guò)WATCH命令監(jiān)控了該鍵,此后又將set命令包圍在事務(wù)中,這樣就可以有效的保證每個(gè)連接在執(zhí)行EXEC之前,如果當(dāng)前連接獲取的mykey的值被其它連接的客戶端修改,那么當(dāng)前連接的EXEC命令將執(zhí)行失敗。這樣調(diào)用者在判斷返回值后就可以獲悉val是否被重新設(shè)置成功。

以上就是redis中事務(wù)命令的介紹和使用,看完之后是否有所收獲呢?如果想了解更多相關(guān)內(nèi)容,歡迎關(guān)注億速云行業(yè)資訊,感謝各位的閱讀。

向AI問(wèn)一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI