Redis 事务:一次执行多个命令
Redis事务工作特点:
三个阶段:
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)> get k1 QUEUED 127.0.0.1:6379(TX)> set k3 v3 QUEUED ########### 命令入队 结束 ################# 127.0.0.1:6379(TX)> exec # 执行事务 1) OK 2) OK 3) "v1" 4) OK
127.0.0.1:6379> multi OK 127.0.0.1:6379(TX)> set k4 v4 QUEUED 127.0.0.1:6379(TX)> set k5 v5 QUEUED 127.0.0.1:6379(TX)> discard #取消事务 OK 127.0.0.1:6379> get k4 ####取消执行事务中所有命令,k4就会没值 (nil)
127.0.0.1:6379> multi OK 127.0.0.1:6379(TX)> set k1 v1 QUEUED 127.0.0.1:6379(TX)> getset k2 #命令错误 (error) ERR wrong number of arguments for ‘getset‘ command 127.0.0.1:6379(TX)> set k3 v3 QUEUED 127.0.0.1:6379(TX)> exec (error) EXECABORT Transaction discarded because of previous errors.
127.0.0.1:6379> set k1 v1 OK 127.0.0.1:6379> multi OK 127.0.0.1:6379(TX)> INCR k1 #k1自加一,必须时数值,有错误,不影响其他命令执行 QUEUED 127.0.0.1:6379(TX)> set k2 v2 QUEUED 127.0.0.1:6379(TX)> exec 1) (error) ERR value is not an integer or out of range 2) OK 127.0.0.1:6379> get k2 "v2"
通过监视key的值是否改变来决定事务能否正常提交
正常执行
127.0.0.1:6379> set money 100 OK 127.0.0.1:6379> set out 0 OK 127.0.0.1:6379> watch money #监视money OK 127.0.0.1:6379> multi OK 127.0.0.1:6379(TX)> decrby money 20 QUEUED 127.0.0.1:6379(TX)> incrby out 20 QUEUED 127.0.0.1:6379(TX)> exec #正常执行 1) (integer) 80 2) (integer) 20
事务正常执行完成后,watch监视结束
多线程操作
127.0.0.1:6379> watch money OK 127.0.0.1:6379> multi OK 127.0.0.1:6379(TX)> DECRBY money 50 QUEUED 127.0.0.1:6379(TX)> INCRBY out 50 QUEUED 127.0.0.1:6379(TX)>
事务没有执行,另一个线程修改了监视的key
执行事务
127.0.0.1:6379(TX)> exec #执行失败 (nil)
重新执行事务,使用UNWATCH命令(用于取消 WATCH 命令对所有 key 的监视)来保证下一个事务的执行不会受到影响
127.0.0.1:6379> watch money #开启监视 OK 127.0.0.1:6379> multi OK 127.0.0.1:6379(TX)> DECRBY money 50 QUEUED 127.0.0.1:6379(TX)> INCRBY out 50 QUEUED 127.0.0.1:6379(TX)> exec # 执行之前,另一个线程执行了 set money 200 (nil) 127.0.0.1:6379> UNWATCH #取消 WATCH 命令对所有 key 的监视 OK 127.0.0.1:6379> WATCH money #开启监视 OK 127.0.0.1:6379> multi OK 127.0.0.1:6379(TX)> DECRBY money 50 QUEUED 127.0.0.1:6379(TX)> INCRBY out 50 QUEUED 127.0.0.1:6379(TX)> exec 1) (integer) 150 2) (integer) 50
原文:https://www.cnblogs.com/WarBlog/p/15245561.html