-
事务本质:一组命令的集合!
-
一个事务的所有命令都会被序列化,在事务执行的过程中,会按照顺序执行。
-
一次性
-
顺序性
-
排他性
-
执行一系列的命令!
-
Redis事务没有隔离级别的概念!
-
所有的命令在事务中,并没有直接执行!只有发起执行命令才会执行!Exec
-
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)> exec
1) OK
2) OK
3) "v1"
-
取消事务!
127.0.0.1:6379> multi
OK
127.0.0.1:6379(TX)> set k3 v3
QUEUED
127.0.0.1:6379(TX)> discard
OK
127.0.0.1:6379> get k3
(nil)
-
编译型异常(代码有问题!命令有错,事务所有的命令都不执行!)
127.0.0.1:6379> flushdb
OK
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)> getset k3
(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> get k1
(nil)
-
运行时一场(1/0),如果事务队列存在语法型,那么执行命令的时候,其他的命令是可以正常执行的,错误命令抛出异常!!!
127.0.0.1:6379> set k1 "k1"
OK
127.0.0.1:6379> multi
OK
127.0.0.1:6379(TX)> incr k1
QUEUED
127.0.0.1:6379(TX)> set k2 v2
QUEUED
127.0.0.1:6379(TX)> get k2
QUEUED
127.0.0.1:6379(TX)> exec
1) (error) ERR value is not an integer or out of range
2) OK
3) "v2"
127.0.0.1:6379> get k2
"v2"
-
悲观锁!
-
很悲观,认为什么时候都会出现问题,无论做什么都会加锁
-
乐观锁!
-
很乐观,认为什么时候都不会出现问题,所以不会上锁,更新数据的时候去判断下,在此期间,是否有人修改过这个数据!!!
-
获取version
-
更新时候比较version
-
Redis监视测试!!
-
正常执行成功!
-
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
127.0.0.1:6379> multi
OK
127.0.0.1:6379(TX)> decrby money 10
QUEUED
127.0.0.1:6379(TX)> incrby out 10
QUEUED
127.0.0.1:6379(TX)> exec
1) (integer) 90
2) (integer) 10
-
测试多线程修改值,监视失败,相当于乐观锁,使用watch可以当做redis乐观锁操作
-
127.0.0.1:6379> watch money
OK
127.0.0.1:6379> multi
OK
127.0.0.1:6379(TX)> decrby money 10
QUEUED
127.0.0.1:6379(TX)> incrby out 10
QUEUED
127.0.0.1:6379(TX)> exec
(nil)
-
如果监视失败,则进行解锁
-
127.0.0.1:6379> unwatch
OK
127.0.0.1:6379> watch money
OK
127.0.0.1:6379> multi
OK
127.0.0.1:6379(TX)> decrby money 10
QUEUED
127.0.0.1:6379(TX)> incrby out 10
QUEUED
127.0.0.1:6379(TX)> exec
1) (integer) 60
2) (integer) 40