Redisson 分散ロック ソースコード 1: 再入可能ロック

Redisson 分散ロック ソースコード 1: 再入可能ロック

[[407548]]

序文

誰もが分散サービスを使用しているため、分散サービスでの同時データ更新の問題は避けられないと思います。

単一システムの場合、synchronize、ReentrantLock などのさまざまな Java ロックを考えるのは簡単ですが、分散システムではこれをどのように処理するのでしょうか。

もちろん、分散ロックを使用します。

分散ロックが何であるかわからない場合は、Shi Shan 教授の短期集中講座をご覧いただくか、オンラインで関連情報を検索することをお勧めします。

Redis を分散ロックとして使用する場合、最もよく使用されるフレームワークは Redisson です。

もちろん、Redisson はロックとしてだけでなく、他の多くの機能も備えています。公式ドキュメントをご覧になり、ご自身で実践してみてください。

Redisson関連のメモを記録し始めましょう!間違いがありましたら訂正してください。

1. 環境設定

  • ローカル環境に構築された疑似クラスター:

  • レディソン 3.15.6

バージョンによって異なる場合もありますが、中核となる考え方はそれほど変わりません。大きな変更がある場合はメッセージを残してください。

  1. <依存関係>
  2. <グループID>org.redisson</グループID>
  3. <artifactId>redisson</artifactId>
  4. <バージョン>3.15.6</バージョン>
  5. </依存関係>

  • プロジェクト準備

単純な Maven プロジェクトでは Main メソッドのみが必要です。

2. 再入可能ロック

lock.lock() ブレークポイントで、ソース コード エントリとして。

デフォルトではロックされており、パラメータは渡されません。しかし、ここではleaseTime = -1が設定されています。リースタイムの意味はロック時間です。

残りはただ前進するだけです。

tryAcquire メソッドを呼び出す前に、現在のスレッドの ID である long 型の正の数値である追加のパラメータ threadId が追加されます。

非同期ロック

tryAcquireAsync 非同期ロック メソッドに直接移動します。

取得非同期処理

先ほども述べたように、leaseTime は -1 なので、ここでは次の方法に進みます。

この時点で、いくつかのパラメータが明確になっています。

  1. 待機時間: -1;
  2. internalLockLeaseTime: デフォルトの時間 30000 ミリ秒を使用します。
  3. TimeUnit.MILLISECONDS: 単位はミリ秒です。
  4. threadId: スレッド ID;
  5. RedisCommands.EVAL_LONG:eval.

Redis eval コマンドのドキュメントは、https://redis.io/commands/eval で読むことができます。

ロックロジック

実際のロックは、まさにこのような Lua スクリプトです。

まず、lua スクリプトのパラメータ情報を説明します。

  1. KEYS[1]: getRawName()、anyLockなどのロックされたキー。
  2. ARGV[1]: unit.toMillis(leaseTime)、ロック時間(ミリ秒単位、例:30000)。
  3. ARGV[2]: getLockName(threadId)、これはUUIDとスレッドIDで構成される文字列です(例:931573de-903e-42fd-baa7-428ebb7eda80:1)。

Lua スクリプトを使用しているため、この Lua スクリプトのアトミック性が保証されます。

最初のロック分析:

  1. exists コマンドは、redis anyLock が存在するかどうかを判断します。
  2. 存在しない場合は、hincrby コマンドを使用して anyLock データを作成します。
  3. anyLock の有効期限を設定します。

ロック後の Redis のデータ形式は次のとおりです。

Redis のハッシュ データ構造の詳細については、https://redis.io/topics/data-types#hashes をご覧ください。

抽象的に言えば、anyLock は、その下にぶら下がっている KV 構造化データとして理解できます。

  1. 「anyLock」 : {
  2. "f400aad5-4b1f-4246-a81e-80c2717c3afb:1" : "1"  
  3. }

スクリプトを実行する

以降の内容は、Lua スクリプトの実行をリクエストする内容です。注意する必要があるのは、ハッシュ スロット ルーティングがあることだけです。

このコードは、NodeSource を取得するために CommandAsyncService#evalWriteAsync メソッドで呼び出されます。

もちろん、この NodeSource には 1 つのスロット (ハッシュ スロット値) のみが格納されます。

このスロット値は、ロックされたキーの CRC16 アルゴリズムを使用して計算されます。

  1. // MAX_SLOT のデフォルトは 16384 です
  2. int結果 = CRC16.crc16(キー.getBytes()) % MAX_SLOT;

スロットを計算することの用途は何ですか?

追跡を続けてください!

BaseRedisBatchExecutor#addBatchCommandData はソースからソルトを取得し、次に MasterSlaveEntry を取得します。

これは、この Redis キーに対応するノードを取得することであると大まかに理解できます。

再入性

再入可能ロックであるため、このブロックは再入可能性をサポートします。再入可能性がどのように保証されるかを見てみましょう。

  1. exists コマンドは、redis キー フィールドが存在するかどうかを判断します。
  2. 存在する場合は、hincrby コマンドを使用して、キー フィールドに対応する値を増分します。
  3. 現在の Redis キーの有効期限を設定します。

ロックミューテックス

上記では 2 つの状況が確認されています。

  1. redis キーが存在しません。
  2. Redis キーとキーのフィールドが存在します。

残りのケースは、キーは存在するがフィールドが存在しないときです。

キー フィールドには UUID:ThreadId が含まれていることに注意してください。これは、ロックされているスレッドが現在のスレッドではないことを意味します。このとき、現在のロックの残り時間がそのまま返されます。

3. まとめ

この記事では、主に Redisson 再入可能ロックのロック、ロック再入、およびロック相互排他ロジックについて説明します。

主な焦点は lua スクリプトにあります。 Redis のハッシュ データ構造も理解する必要があります。

また、ロック時間が指定されていない場合は、デフォルトは 30 秒になることに注意してください。

最後に、この記事のロックロジックを図で紹介します。

<<:  Longxingyoufengは、Beanオブジェクトの初期化と破棄のメソッドを実装するために仮想マシンにフックを登録します。

>>:  Tekton を使用した自動化パイプラインのリファクタリング

推薦する

bacloud-26 ユーロ/i3-3220/8g メモリ/2x1T ハードディスク/100M/無制限トラフィック

リトアニアのホスティング プロバイダー bacloud には、安価な独立サーバーが複数あります。プロ...

オリンピック中に登場したマーケティング手法を共有する

いつの間にか、オリンピックの16日間の開催が始まりました。今回のオリンピックでは、オリンピックイベン...

クラウドコンピューティングは AI を民主化するための鍵となるのでしょうか?

日本の収穫期には、農家の中には毎日多くの時間を費やして、農場で収穫したキュウリを種類ごとに仕分けする...

新規ドメイン名に含まれるキーワードが即日9位にランクインした体験談共有

今日は、Baidu への参入に関する経験を皆さんと共有したいと思います。最近は暇だったので、自分でた...

インテリジェント検索エンジンが主流の最適化方向になります。

グーグルや百度などの検索エンジンのアルゴリズムがここ数日継続的に調整されていることから判断すると、モ...

#ウェブサイトホスティング# webhostinghub-3.3% オフ/仮想ホスト/cpanel パネル/ロサンゼルス

2001年設立のインモーションホスティング傘下の仮想ホスティングブランド、Webhostinghub...

新しいウェブマスターがウェブサイトのプロモーションで注意すべき点を分析する

新しいウェブマスターのウェブサイトの開発が遅かったり、満足のいく結果が得られなかったりする主な理由の...

キャメルは、3億8000万本の売上でダブルイレブン市場をリードするために何をしたのでしょうか?

2012年の天猫ダブルイレブンで売上高が1億元を超えた最初のアパレルブランドとして、今年のダブルイレ...

あなたはまだ Google の PR 価値を重視していますか?それはもう重要ではないかもしれません。

最近、GoogleのPRアップデートにより、主要なウェブマスターフォーラムやQQグループのウェブマス...

戦場では相手を理解しなければならない

著者は歴史書、特に皇帝に関する本を読むのが好きです。私の意見では、古代の皇帝の思想は常に非常に深いた...

Microsoft Azure SQL Database Managed Instance は、SQL Server から PaaS サービスへのシームレスな移行の時代を切り開きます。

2019 年 6 月 12 日、顧客のデータベースのクラウド移行を支援する Microsoft In...

Bilibili、iQiyi 広告およびコンテンツ IP

11月17日、ビリビリ(以下、「ビリビリ」)とiQiyiは、2019年9月30日までの第3四半期の財...

周囲のリソースを活用してウェブサイト開発のレベルを決定する方法

私は3年間ウェブサイトを作ってきました。何も知らない小さなウェブマスターから、5つのウェブサイトを所...

SEO実践体験:ウェブサイトがKになる問題を解決する方法

1. ブロックされたウェブサイトとは何ですか?ウェブサイトがブロックされると、ウェブマスターはそれを...

ショッピングモールのウェブサイト運営でトラフィックを集める方法

立ち上げたばかりのショッピングモールのウェブサイトを運営するのは少し難しいです。ショッピングモールの...