redis 分布式事物

實(shí)現(xiàn)代碼

Jedis jedis = pool.getResource();
try {
    Transaction tx = jedis.multi();
    try {
        tx.get("XXX");
        tx.set("YYY","ZZZ")
        resp = tx.exec();
    } finally { tx.close(); }
} catch (Exception e) {
    // TODO
}finally { jedis.close(); }
  • 問題:
    1、客戶端分片和中間件(我們目前使用的codis)分片均不支持transaction。因?yàn)閠ransaction提供了原子級(jí)的執(zhí)行保證,在instance之外是無法提供的,也就是說必須同一個(gè)reids實(shí)例上
    2、Redis Cluster集群 支持transaction,但是前提是transaction涉及的所有key都屬于同一hash slot,2^14-1 16383個(gè)槽位(總)
  • 解決辦法:
/**
     * 嘗試獲取分布式鎖
     *
     * @param jedis     Redis客戶端
     * @param lockKey   鎖
     * @param requestId 請求標(biāo)識(shí)
     * @return 是否獲取成功
     */
    public static boolean tryGetDistributedLock(Jedis jedis, String lockKey, String requestId) {
        String result = jedis.set(lockKey, requestId, SET_IF_NOT_EXIST(NX), SET_WITH_EXPIRE_TIME(PX), expireTime(過期時(shí)間));
        if (LOCK_SUCCESS.equals(result)) {
            return true;
        }
        return false;
    }
 /**
     * 釋放分布式鎖
     *
     * @param jedis     Redis客戶端
     * @param lockKey   鎖
     * @param requestId 請求標(biāo)識(shí)
     * @return 是否釋放成功
     */
    public static boolean releaseDistributedLock(Jedis jedis, String lockKey, String requestId) {
        String script = "if redis.call('get', KEYS[1]) == ARGV[1] then return redis.call('del', KEYS[1]) else return 0 end";
        Object result = jedis.eval(script, Collections.singletonList(lockKey), Collections.singletonList(requestId));
        if (RELEASE_SUCCESS.equals(result)) {
            return true;
        }
        return false;
    }

解釋
使用 SETNX(set if not exist)指令插入一個(gè)鍵值對(duì),如果 Key 已經(jīng)存在,那么會(huì)返回 False,否則插入成功并返回 True。
SETNX 指令和數(shù)據(jù)庫的唯一索引類似,可以保證只存在一個(gè) Key 的鍵值對(duì),可以用一個(gè) Key 的鍵值對(duì)是否存在來判斷是否存于鎖定狀態(tài)。
EXPIRE 指令可以為一個(gè)鍵值對(duì)設(shè)置一個(gè)過期時(shí)間,從而避免了死鎖的發(fā)生。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • NOSQL類型簡介鍵值對(duì):會(huì)使用到一個(gè)哈希表,表中有一個(gè)特定的鍵和一個(gè)指針指向特定的數(shù)據(jù),如redis,volde...
    MicoCube閱讀 4,150評(píng)論 2 27
  • Codis 3.2 部署配置匯總 概念總結(jié) 集群配置前需要了解架構(gòu),集群分片主要分三種: 客戶端分片:這個(gè)需要自己...
    三杯水Plus閱讀 6,316評(píng)論 0 11
  • 之前寫過一篇介紹redis集群的文章,那篇可以方便大家入門,這篇是對(duì)這幾個(gè)方案的原理介紹,方便對(duì)大家對(duì)這幾個(gè)集群方...
    monkey01閱讀 2,771評(píng)論 1 7
  • 一、Redis集群概述 Redis官方近期推出的Redis Cluster,Redis集群有三種實(shí)現(xiàn)機(jī)制,分別介紹...
    E狼閱讀 1,031評(píng)論 2 6
  • 1.集群與分布式的概述 1.1 分布式 分布式是指將不同的業(yè)務(wù)分布在不同的地方. web應(yīng)用和數(shù)據(jù)庫服務(wù)分開 1....
    程序員Darker閱讀 476評(píng)論 1 1

友情鏈接更多精彩內(nèi)容