PHP如何使用分布式锁、分布式红锁,一篇文章带你轻松搞懂

GitHub地址:https://github.com/ihongwu/redis-redlock

最新使用教程请关注GitHub最新的更新即可!

PHP版本的Redis红锁,已支持以下特性:

  • 单机Redis
  • 多机版Redis
  • 传入Redis配置
  • 传入Redis对象,方便在常驻内存的框架中使用,如webman
  • 可重入
  • 锁等待

注意事项

  • 锁超时时间默认为30秒
  • 连接Redis超时时间默认50毫秒
  • 重试获取锁次数默认200次,100毫秒重试一次

使用方法

安装
composer require ihongwu/redis-redlock

or

git@github.com:ihongwu/redis-redlock.git
常规使用:传入Redis配置信息

use RedisLock\RedisRedLock;

// 有自动加载则不需要
require_once 'src/RedisRedLock.php';


$servers = [
    ['host' => '127.0.0.1', 'port' => 6391, 'password' => '88888888'],
    ['host' => '127.0.0.1', 'port' => 6392, 'password' => '88888888'],
    ['host' => '127.0.0.1', 'port' => 6393, 'password' => '88888888'],
];

$resourceKey = 'my_distributed_lock';

try {
    $redlock = new RedisRedLock($servers, $resourceKey);
    if ($redlock->lock()) {
        echo "成功获取锁,执行任务...\n";
        if ($redlock->lock()) {
            echo "再次获取锁,继续执行任务...\n";
        }

        if ($redlock->unlock()) {
            echo "锁已释放一次。\n";
        }

        if ($redlock->unlock()) {
            echo "锁已全部释放。\n";
        }
    } else {
        echo "获取锁失败。\n";
    }
} catch (\Exception $e) {
    var_dump($e->getMessage());
}
常驻内存框架:传入Redis连接池,以webman为例
// 配置信息
return [
    '6391' => [
        'host' => '127.0.0.1',
        'password' => '88888888',
        'port' => 6391,
        'database' => 0,
        'pool' => [
            'min' => 5,
            'max' => 50,
            'timeout' => 5
        ]
    ],
    '6392' => [
        'host' => '127.0.0.1',
        'password' => '88888888',
        'port' => 6392,
        'database' => 0,
        'pool' => [
            'min' => 5,
            'max' => 50,
            'timeout' => 5
        ]
    ],
    '6393' => [
        'host' => '127.0.0.1',
        'password' => '88888888',
        'port' => 6393,
        'database' => 0,
        'pool' => [
            'min' => 5,
            'max' => 50,
            'timeout' => 5
        ]
    ],
];

use RedisLock\RedisRedLock;

// 不想传入连接池的,也可以直接传入Redis配置信息
// 连接成功的redis实例,才给锁对象使用
$servers = [];
try {
    $servers[] = Redis::connection('6391')->client();
} catch (\Exception $e) {}
try {
    $servers[] = Redis::connection('6392')->client();
} catch(\Exception $e) {}
try {
    $servers[] = Redis::connection('6393')->client();
} catch(\Exception $e) {}

$resourceKey = 'my_distributed_lock';

try {
    $redlock = new RedisRedLock($servers, $resourceKey);
    if ($redlock->lock()) {
        echo "成功获取锁,执行任务...\n";
        if ($redlock->lock()) {
            echo "再次获取锁,继续执行任务...\n";
        }

        if ($redlock->unlock()) {
            echo "锁已释放一次。\n";
        }

        if ($redlock->unlock()) {
            echo "锁已全部释放。\n";
        }
    } else {
        echo "获取锁失败。\n";
    }
} catch (\Exception $e) {
    var_dump($e->getMessage());
}

声明

1、该库已通过库存200,并发1000的多轮测试并正常工作,但并不意味这它100%没问题
2、传入的redis配置/实例数理论上为奇数,但考虑到常驻内存框架自行判断连接后,最后可能达不到奇数的要求,所以只要可用连接数能达到N / 2 + 1即可
3、如发现问题,请随时提issues或提交更正代码,在生产环境中使用它之前,请务必了解它的工作原理

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值