本文基于 Redis6.2.7 和 CentOS 7
首先要告诉大家,redis的事务和mysql的事务是不一样。
multi #开启事务
exec #提交事务
discard #回滚事务
一个事务从开始到执行会经历以下三个阶段:
1.执行multi
开始事务
2.将命令依次放入队列(此时还未真实执行)
3.exec
执行事务(执行队列中的命令)
① 演示正常情况下事务提交
127.0.0.1:6379> MULTI
OK
127.0.0.1:6379(TX)> set k1 v1
QUEUED
127.0.0.1:6379(TX)> set k2 v2
QUEUED
127.0.0.1:6379(TX)> EXEC
1) OK
2) OK
② 演示正常情况下事务回滚
127.0.0.1:6379> MULTI
OK
127.0.0.1:6379(TX)> set k3 v3
QUEUED
127.0.0.1:6379(TX)> set k4 v4
QUEUED
127.0.0.1:6379(TX)> DISCARD
OK
③ 演示异常情况(命令放入队列时就发生异常,执行事务,则全部回滚)
127.0.0.1:6379> MULTI
OK
127.0.0.1:6379(TX)> set k3 v4
QUEUED
127.0.0.1:6379(TX)> set k4 v4
QUEUED
127.0.0.1:6379(TX)> set k5 #命令不全,发生语法错误
(error) ERR wrong number of arguments for 'set' command
127.0.0.1:6379(TX)> EXEC #执行事务提交失败,整个事务中的3条命令都未执行成功
(error) EXECABORT Transaction discarded because of previous errors.
④ 演示异常情况(命令放入队列时无异常,执行时异常,则仅会失败有语法错误的指令,其他指令依然会执行成功)
127.0.0.1:6379> MULTI
OK
127.0.0.1:6379(TX)> set k6 v6
QUEUED
127.0.0.1:6379(TX)> set k7 v7
QUEUED
127.0.0.1:6379(TX)> incr k7 #仅会失败这一条
QUEUED
127.0.0.1:6379(TX)> set k8 v8
QUEUED
127.0.0.1:6379(TX)> exec
1) OK
2) OK
3) (error) ERR value is not an integer or out of range
4) OK
Redis的Watch 命令用于监视一个(或多个) key ,如果在事务执行之前这个(或这些) key 被其他命令所改动,那么事务将被打断。他的实现方式是乐观锁。
语法:
WATCH key [key ...]
watch案例:
原因分析:在客户端1提交事务后,num被改变的同时版本号也跟着变化了,客户端2在执行时对比版本不一致,则执行失败。
Redis还提供了 unwatch
命令用于取消 WATCH
命令对所有 key 的监视。
Redis 发布订阅 (pub/sub) 是一种消息通信模式:发送者 (pub) 发送消息,订阅者 (sub) 接收消息。
Redis 客户端可以订阅任意数量的频道。
下图展示了频道 channel1 , 以及订阅这个频道的三个客户端 —— client2 、 client5 和 client1 之间的关系:
当有新消息通过 PUBLISH 命令发送给频道 channel1 时, 这个消息就会被发送给订阅它的三个客户端:
代码演示:
客户端1:订阅频道
127.0.0.1:6379> SUBSCRIBE channel1 #订阅了频道channel1
Reading messages... (press Ctrl-C to quit)
1) "subscribe"
2) "channel1"
客户端2:向频道中发送消息
127.0.0.1:6379> PUBLISH channel1 helloRedis #向频道channel1中发送了信息helloR