>  기사  >  데이터 베이스  >  Redis를 잠그는 방법은 무엇입니까?

Redis를 잠그는 방법은 무엇입니까?

WBOY
WBOY앞으로
2023-05-27 12:43:061374검색

redis의 일반적인 잠금 명령은 INCR, SETNX, SET

1, INCR

입니다. 이러한 종류의 잠금에 대한 잠금 아이디어는 다음과 같습니다.

key가 존재하지 않으면 키 값은 다음과 같습니다. 먼저 0으로 초기화한 다음 INCR 작업을 수행하여 1을 추가합니다.

그런 다음 다른 사용자가 키를 추가하기 위해 INCR 작업을 수행할 때 반환된 값이 1보다 크면 키가 사용 가능하도록 잠겨 있다는 의미입니다.

1. 클라이언트 A는 서버에 값 1의 키를 가져오도록 요청합니다. 이는 잠금이 획득되었음을 나타냅니다.

2. 클라이언트 B도 서버에 값 2의 키를 가져오도록 요청합니다.

3. 클라이언트 A가 코드 실행을 완료하고 잠금을 삭제합니다.

4. 일정 시간 동안 기다린 후 클라이언트 B는 요청 시 키 값 1을 얻습니다. 이는 잠금이 성공적으로 획득되었음을 나타냅니다. 5. 클라이언트 B는 코드 실행을 완료하고 잠금을 삭제합니다.

$redis->incr($key);
$redis->expire($key, $ttl); //设置生成时间为1秒

특정 명령:

127.0.0.1:6379>INCR keyName

2.SETNX

이런 종류의 잠금 아이디어는 키가 존재하지 않으면 키를 값으로 설정한다는 것입니다. 키가 있으면 SETNX는 어떤 조치도 취하지 않습니다.

SETNX는 SET if Not eXists의 약어입니다.

1. 클라이언트 A가 서버에 키 값 설정을 요청하면 잠금이 성공한 것입니다.

2. 클라이언트 B도 반환에 실패하면 서버에 키 값 설정을 요청합니다. 잠금이 실패했다는 뜻입니다.

3. 클라이언트 A가 코드 실행을 완료하고 잠금을 삭제합니다

4. 클라이언트 B가 일정 시간 기다린 후 키 값 설정을 요청하여 설정이 성공합니다

5 . 클라이언트 B는 코드 실행을 완료하고 잠금을 삭제합니다.

$redis->setNX($key, $value);
$redis->expire($key, $ttl);

사용할 특정 명령:

redis> SETNX keyName value
(integer) 1

설정이 성공하면 1이 반환되고, 설정이 실패하면 0이 반환됩니다. SET

위의 두 가지 방법에는 문제가 있어 키 만료 시간을 설정해야 한다는 것을 알게 됩니다.

그렇다면 왜 키 만료를 설정해야 할까요?

어떤 이유로 요청 실행이 예기치 않게 종료되어 잠금이 생성되었지만 삭제되지 않은 경우 잠금은 항상 존재하므로 향후 캐시가 업데이트되지 않습니다. 따라서 예상치 못한 이벤트를 방지하려면 잠금에 만료 시간을 추가해야 합니다.

하지만 Expire로 설정하는 것은 원자적 연산이 아닙니다.

그래서 트랜잭션을 통해서도 원자성을 보장할 수 있지만 여전히 문제가 있어서 관계자는 2.6.12 버전부터 SET 명령 자체를 사용하면 만료 시간을 설정하는 기능이 포함되었다고 밝혔습니다.

1. 클라이언트 A가 서버에 키 값 설정을 요청하면 잠금이 성공한 것입니다.

2. 클라이언트 B도 서버에 키 값 설정을 요청합니다.

3. 클라이언트 A가 코드 실행을 완료하고 잠금을 삭제합니다

4. 클라이언트 B가 일정 시간 기다린 후 키 값 설정을 요청하고 설정이 성공합니다

5. 클라이언트 B는 코드 실행을 완료하고 잠금

$redis->set($key, $value, array('nx', 'ex' => $ttl));  //ex表示秒

을 삭제합니다. 특정 사용법:

redis>set key value NX EX max-lock-time 实现加锁

명령 설명:

key: key는 잠금 식별로 redis의 키 값입니다. , 값은 여기서 키-값이 일치하는 경우에만 삭제할 수 있습니다. [보안 보장]

  • max-lock-time: 교착 상태가 발생하지 않도록 max-lock-time을 통해 만료 시간을 설정합니다. [교착 상태 방지] key:key就是redis的key值作为锁的标识,value在这里作为客户端的标识,只有key-value都比配才有删除锁的权利【保证安全性】

  • max-lock-time:通过max-lock-time设置过期时间保证不会出现死锁【避免死锁】

  • NX:只有这个key不存才的时候才会进行操作,if not exists;

  • EX

NX: 키가 존재하지 않는 경우에만 작업이 수행됩니다. ;

EX: 키의 만료 시간을 초로 설정합니다. 구체적인 시간은 5개의 매개변수에 따라 결정됩니다.

잠금 코드:

 Jedis jedis = new Jedis("127.0.0.1", 6379);
 private static final String SUCCESS = "OK";
 /**
  * 加锁操作
  * @param key 锁标识
  * @param value 客户端标识
  * @param timeOut 过期时间
  */
  
 public Boolean lock(String key,String value,Long timeOut){
     String var1 = jedis.set(key,value,"NX","EX",timeOut);
     if(LOCK_SUCCESS.equals(var1)){
         return true;
     }
     return false;
 }

잠금 해제 코드:

🎜
 Jedis jedis = new Jedis("127.0.0.1", 6379); 
 private static final Long UNLOCK_SUCCESS = 1L;
 /**
  * 解锁操作
  * @param key 锁标识
  * @param value 客户端标识
  * @return
  */
  
 public static Boolean unLock(String key,String value){
     String luaScript = "if redis.call(\"get\",KEYS[1]) == ARGV[1] then return 
     redis.call(\"del\",KEYS[1]) else  return 0 end";
     Object var2 = jedis.eval(luaScript,Collections.singletonList(key), Collections.singletonList(value));
     if (UNLOCK_SUCCESS == var2) {
         return true;
     }
     return false;
}
🎜luaScript 이 문자열은 Lua 스크립트입니다. 즉, 키를 기반으로 얻은 값이 들어오는 값과 동일한 경우 del을 실행하면 됩니다. 그렇지 않으면 0이 반환됩니다. [보안 보장] 🎜🎜jedis.eval(String, list , list); 이 명령은 lua 스크립트를 실행하는 명령입니다. KEYS 집합은 두 번째 매개 변수이고 ARGV 집합은 세 번째 매개 변수입니다. [잠금 해제의 원자적 작동 보장]🎜🎜위에서는 Redis를 올바르게 사용하는 방법을 보여줍니다. 그러나 잠금 만료 시간을 적절한 값으로 설정해야 한다는 작은 결함이 있으며 이는 실제로 비즈니스 시나리오에 따라 고려되어야 합니다. 🎜

위 내용은 Redis를 잠그는 방법은 무엇입니까?의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

성명:
이 기사는 yisu.com에서 복제됩니다. 침해가 있는 경우 admin@php.cn으로 문의하시기 바랍니다. 삭제