この記事では主にphp redisのロックとロック解除について紹介しますが、参考値があるのでみんなに共有します。困っている友達は参考にしてください
ビジネスの背景: ルーム チェスやカード ゲームでは、同時操作による Redis データの不正な読み取りを防ぐために、ロックが必要です (たとえば、ユーザーがルームに入るアクションを追加するなど)。
同時実行の場合、get RoomUsers はダーティ読み取りを行うことになります;ソリューションのアイデア : ルームをロックして、それを実現するだけです一度に 1 つのルームを読み取ることができます 他の同時クライアントが待機している間、1 つのクライアントが動作できるようにします; つまり、----- ブロック ロック;
Lock: いくつかありますRedis ロック メソッド: incr 、 set、setnx、hSetnx。この記事を参照してください: Redis ロックのいくつかの実装
ここでは set メソッドを使用します$roomId = $_GET['roomId']; $user = $_GET['user']; // '张三' $key = "LockRoom:{$roomId}"; $value = $roomId.uniqid(); $ex = 3; // 如果 $key 不存在的话,就设置 $key 的值为 $value,且有效期为 3s; // return TRUE / FALSE while(true){ $res = $this->redis->set($key, $value, ['nx', 'ex' => $ex]); if($res) { break; } usleep(5000); } // 将用户添加进房间 $roomUsers = $this->redis->get("Room:{$roomId}:Users"); // ['李四', '王五'] $roomUsers[] = $user; $this->redis->set("Room:{$roomId}:Users", $roomUsers); // ['李四', '王五', '张三']
Unlocking : もちろん、操作後にロックを解除する必要があります。ロックを解除しない場合は、少なくとも 3 秒待つ必要があります。 ロックを解除するキーを削除するには、delete を使用します。しかし、ここに落とし穴があります。 client01 がロックを取得していると想定されているため、削除を直接使用することはできません。ユーザーを追加してルームに入室すると、処理時間が 3 秒を超えます。このとき、client02 もロックを取得して 3S を設定します。 client01 が操作を完了してキーを削除すると、client02 によって設定されたロックが削除されます;
Lua の実行はアトミックであるため、削除を実行するには lua コードを使用することをお勧めします。
// 将用户添加进房间 $roomUsers = $this->redis->get("Room:{$roomId}:Users"); // ['李四', '王五'] $roomUsers[] = $user; $this->redis->set("Room:{$roomId}:Users", $roomUsers); // ['李四', '王五', '张三'] // lua 脚本解锁 // 先判断 key的值是否为 value, TRUE 才会删除, 所以 $value 的设计要有随机唯一性 $script = 'if redis.call("get",KEYS[1]) == ARGV[1] then return redis.call("del",KEYS[1]) else return 0 end '; $this->redis->eval($script, array($key , $value), 1);詳細については、次の記事もお読みください: Redis ロックを解除するための正しい姿勢PHP の Redis 操作に関するドキュメントもあります: PhpRedis には set() と eval の説明が含まれています() 関数注: ここで lua スクリプトを使用する場合、php.ini はshell_exec() などのシステム関数を開く必要があります。
上記のコードは参照のみです。 !
PHP 操作 Beanstalkd のメソッドとパラメーターのコメント
PHP リファクタリングによって実装されたイントラネット侵入アプリケーション Spike が完了しました
以上がPHP Redisのロックとロック解除の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。