4.1实现锁

利用watch+multi来实现乐观锁

乐观锁,顾名思义,乐观的认为数据不会被修改,只有当更新时才去判断数据是否被修改过,通常用版本号或时间戳来实现。 redis中通过watch和multi来实现,watch会监视给定的key是否发生更改,当exec的时候如果监视的key发生过改变,则整个事务会失败。 当然我们可以调用多次watch监视多个key。

<?php

$redis = new Redis();
$redis->connect('127.0.0.1', 6379, 60);

//设置商品的库存数为100
$redis->set('goods_stock_nums', 100);
//监视该key
$redis->watch('goods_stock_nums');

//开启事务
$redis->multi();

//修改库存数,incr原子性递增,decr原子性递减
$redis->decr('goods_stock_nums');

//提交事务,如果在此期间有其他请求修改了该key,那么事务会失败
if ($redis->exec()) {
    echo '抢购成功';
} else {
    echo '数据错误,请重新再试';
}

使用setnx来实现悲观锁

分布式锁

问题主要集中在如何获取分布式锁 setnx创建锁成功 或者 锁过期且getset时间为过期时间

redis锁(setnx)有一定的安全风险,redis挂掉。第一个客户端没释放锁,第二个客户端就获取到锁 持久化 rdb 镜像复制 aof 增量复制 1、每操作 2、每时间段 3、每cpubuffer 都有空窗期 redis集群默认是弱一致性,开启强一致性 1、每操作 降低性能 zookeeper是解决分布式锁的较好方案(zookeeper 安全性能非最优) 大数据etcd 安全性能优

基于golang实现

最后更新于