cache_lock_thorws_excption = $cache_lock_thorws_excption; return $this; } public function getCacheLockThorwsExcption(){ return $this->cache_lock_thorws_excption; } public function hasRedis($is_interrupt = false) { $error_msg = ''; try { $redis = $this->getRedis(); // 检测连接是否正常 $redis->ping(); } catch (\BadFunctionCallException $e) { // 缺少扩展 $error_msg = $e->getMessage() ? $e->getMessage() : "缺少 redis 扩展"; } catch (\RedisException $e) { // 连接拒绝 \think\Log::write('redis connection redisException fail: ' . $e->getMessage()); $error_msg = $e->getMessage() ? $e->getMessage() : "redis 连接失败"; } catch (\Exception $e) { // 异常 \think\Log::write('redis connection fail: ' . $e->getMessage()); $error_msg = $e->getMessage() ? $e->getMessage() : "redis 连接异常"; } if ($error_msg) { if ($is_interrupt || $this->cache_lock_thorws_excption) { throw new \Exception($error_msg); } else { $this->setCacheLockErrorMsg($error_msg); return false; } } return true; } public function getRedis() { if (!isset($GLOBALS['SPREDIS'])) { $GLOBALS['SPREDIS'] = (new Redis())->getRedis(); } return $GLOBALS['SPREDIS']; } public function getLock($key,$suffix = "-lock-suffix", $timeout = 120){ $this->hasRedis(true); $redis = $this->getRedis(); $hashKey = $key.$suffix; // $redis->del($hashKey); // var_dump($hashKey);die; //判断锁是否存在,如果存在,返回错误 // if ($redis->exists($hashKey)){ //// var_dump(111111222);die; // if($this->cache_lock_thorws_excption){ // throw new \Exception($this->cache_lock_error_msg); // }else{ // return false; // } // // } //如果不存在创建锁并返回 // $redis->set($hashKey, 1,$timeout);//注释掉 //替换成原子操作的命令 $nxLock = $redis->set($hashKey, 1,['nx', 'ex' => $timeout]); if ($nxLock == 1) { return true; } else { if($this->cache_lock_thorws_excption){ throw new \Exception($this->cache_lock_error_msg); }else{ return false; } } } public function setCacheLockErrorMsg($cache_lock_error_msg){ $this->cache_lock_error_msg = $cache_lock_error_msg; return $this; } public function getCacheLockErrorMsg(){ return $this->cache_lock_error_msg; } public function freeLock($key,$suffix = "-lock-suffix"){ $this->hasRedis(true); $redis = $this->getRedis(); if(!$key || !$suffix) return true; $hashKey = $key.$suffix; //执行lua脚本,确保删除锁是原子操作 $lua = 'if redis.call("get",KEYS[1]) == ARGV[1] then return redis.call("del",KEYS[1]) else return 0 end'; $result = $redis->eval($lua, [$hashKey, 1], 1); if ('1' == $result) { return true; } return false; // if (!$redis->EXISTS($hashKey)) return true; // $redis->del($hashKey); // return true; } }