Redis Queue StreamとRedisマルチスレッドの詳細解説(1)

Redis キューとストリーム

Redis 5.0 の最大の新機能は、マルチキャストをサポートする新しい強力で耐久性のあるメッセージ キューであるデータ構造 Stream の追加です。著者は、Redis Stream が Kafka の設計を借用していると宣言しています。

Redis ストリームの構造は上の図に示されています。各ストリームには追加されたすべてのメッセージをまとめたメッセージ リストがあり、各メッセージには一意の ID と対応するコンテンツがあります。メッセージは永続的であり、Redis の再起動後も内容は残ります。

各ストリームには、Redis のキーとなる一意の名前があり、最初に xadd コマンドを使用してメッセージを追加するときに自動的に作成されます。

各ストリームは複数のコンシューマ グループにリンクでき、各コンシューマ グループには、現在のコンシューマ グループがどのメッセージを消費したかを示す、Stream 配列を前方に移動するカーソル last_delivered_id があります。各コンシューマ グループは、ストリーム内で一意の名前を持ちます。コンシューマ グループは自動的に作成されません。別のコマンド xgroup create で作成する必要があります。消費を開始するには、ストリームのメッセージ ID を指定する必要があります。この ID が使用されますlast_delivered_id 変数を初期化します。

各コンシューマ グループ (Consumer Group) の状態は独立しており、相互に影響を与えません。つまり、同じストリーム内のメッセージはすべてのコンシューマ グループによって消費されます。

同じコンシューマ グループ (Consumer Group) を複数のコンシューマ (Consumer) にアタッチすることができ、これらのコンシューマは競合関係にあり、メッセージを読むコンシューマはカーソル last_delivered_id を前方に移動します。各コンシューマには、グループ内で一意の名前が付けられます。

コンシューマー (Consumer) 内にはステータス変数 pending_ids があり、クライアントによって読み取られたがまだ確認されていないメッセージを記録します。クライアントが ACK を取得していない場合、この変数のメッセージ ID は増加し、メッセージが ACK されると減少し始めます。この pending_ids 変数は、Redis では正式に PEL、つまり保留エントリ リストと呼ばれます。これは非常に核となるデータ構造であり、クライアントがメッセージを少なくとも 1 回は消費し、メッセージの途中で失われないようにするために使用されます。ネットワーク送信も取り扱っております。

メッセージ ID の形式は timestampInMillis-sequence (たとえば、1527846880572-5) です。これは、現在のメッセージがミリ秒のタイムスタンプ 1527846880572 で生成され、これがこのミリ秒以内に生成される 5 番目のメッセージであることを示します。メッセージ ID はサーバーによって自動的に生成されるか、クライアント自体によって指定できますが、形式は整数-整数である必要があり、後で追加されるメッセージの ID は前のメッセージの ID より大きくなければなりません。

メッセージの内容はキーと値のペアであり、ハッシュ構造化されたキーと値のペアのような形をしていますが、これは特別なことではありません。

共通操作コマンド

制作側

xadd 追加メッセージ

xdel はメッセージを削除します。ここでの削除はフラグを設定するだけであり、実際にはメッセージは削除されません。

xrange はメッセージ リストを取得し、削除されたメッセージを自動的にフィルタリングします。

xlen メッセージの長さ

ストリームの削除

xadd streamtest * 名前マーク 18 歳

 

streamtest は、現在のキューの名前を示します。これは、一般的な意味での Redis のキーです。* 記号は、サーバーが自動的に ID を生成することを示し、その後に「name mark age 18」が続きます。これは、現在のキューに保存するメッセージです。 streamtest キュー。キー/値の保存形式でもあります。

戻り値 1626705954593-0 は生成されたメッセージ ID で、タイムスタンプとシリアル番号の 2 つの部分で構成されます。タイムスタンプはミリ秒単位で、メッセージを生成した Redis サーバーの時刻であり、64 ビットの整数です。シーケンス番号は、このミリ秒の時点でのメッセージのシーケンス番号です。これは 64 ビット整数でもあります。

メッセージが正しい順序であることを保証するために、Redis によって生成される ID は順番に単調増加します。ID にはタイムスタンプ部分が含まれるため、サーバー時刻のエラー (サーバー時刻が遅れるなど) によって引き起こされる問題を回避するために、Redis の各 Stream 型データには、最新の ID を記録するために使用される、latest_generated_id 属性が保持されます。メッセージ。現在のタイムスタンプが古い (latest_generated_id のレコードより小さい) ことが判明した場合は、タイムスタンプが変更されず、シリアル番号が新しいメッセージ ID としてインクリメントされるスキームを使用します (これが、シリアル番号が int64 を使用して確実にされる理由です)十分なシリアル番号があること)、したがって、ID の単調増加特性が保証されます。

非常に特別なニーズがない場合は、Redis スキームを使用してメッセージ ID を生成することを強くお勧めします。タイムスタンプ + シリアル番号の単調増加 ID スキームはほぼすべての要件を満たすことができますが、ID はカスタマイズをサポートしているためです。

 

xrange ストリームテスト - +

このうち、-は最小値、+は最大値を表します

 または、メッセージ ID のリストを指定することもできます。

 xdel ストリームテスト 1626706380924-0

xlen ストリームテスト

 

del streamtest はストリーム全体を削除します

 消費者

単一消費者

Stream にはコンシューマ グループの概念がありますが、コンシューマ グループを定義せずに Stream メッセージを独立して消費したり、Stream に新しいメッセージがないときにブロックして待機したりすることもできます。Redis は、Stream を通常のメッセージ キュー (リスト) として使用できる別個の消費命令 xread を設計しました。xread を使用する場合、Stream が通常のリストであるのと同様に、コンシューマ グループの存在を完全に無視できます。

xread カウント 1 ストリーム stream2 0-0

「count 1」は Stream から 1 つのメッセージを読み取ることを意味します。デフォルトはもちろんヘッダーです。「streams」は Redis キーワードとして理解できます。「stream2」は読み取られるキューの名前を示します。「0-0」は、最初から始めるという意味

 

xread カウント 2 ストリーム stream2 1626710882927-0

ストリームのメッセージIDから開始するように指定することもできます(コマンド内のメッセージIDは除く)。

 

xread カウント 1 ストリーム stream2 $

$ は最後からの読み取りを表し、上記は最新のメッセージを最後から読み取ることを意味し、現時点ではデフォルトではメッセージは返されません。

 

したがって、新しいメッセージが到着するまでブロックする方法で最新のメッセージを末尾で読むのが最善です。

xread ブロック 0 カウント 1 ストリーム stream2 $

ブロックの後の数字は、ブロック時間をミリ秒単位で表します。

 この時点で、新しいクライアントを開き、stream2 にメッセージを書き込みます。

 ブロックが解除され、新しいメッセージの内容が返され、待ち時間も表示されていることがわかります。ここでは 127.87 秒待機しました。

 一般に、クライアントが逐次消費に xread を使用したい場合は、現在の消費がどこにあるか、つまり返されたメッセージ ID を覚えておく必要があります。次回 xread の呼び出しを続けるときに、前回返された最後のメッセージ ID をパラメータとして渡すと、後続のメッセージを引き続き使用できます。

消費者団体

消費者グループを作成する

Stream は、xgroup create コマンドを使用してコンシューマ グループ (コンシューマ グループ) を作成し、初期メッセージ ID パラメータを渡して last_delivered_id 変数を初期化する必要があります。

xgroup 作成ストリーム 2 cg1 0-0

「stream2」は読み込むキュー名、「cg1」はコンシューマグループ名、「0-0」は先頭からの消費を示します。

 

xgroup 作成 stream2 cg2 $

$ は、最後から消費を開始することを意味します。新しいメッセージのみが受け入れられ、現在の Stream メッセージはすべて無視されます。

 

xinfo コマンドを使用して、stream2 の状況を確認できるようになりました。

xinfo ストリーム stream2

 xinfo グループ ストリーム 2

 メッセージの消費

コンシューマ グループでは、コンシューマが当然必要になります。Stream は、コンシューマ グループ内でコンシュームするための xreadgroup コマンドを提供します。コンシューマ グループ名、コンシューマ名、および初期メッセージ ID を指定する必要があります。

xread と同様に、新しいメッセージの待機をブロックすることもできます。新しいメッセージを読み取った後、対応するメッセージ ID がコンシューマの PEL (処理中のメッセージ) 構造に入り、クライアントは処理後に xack コマンドを使用してメッセージが処理されたことをサーバーに通知し、メッセージ ID が転送されます。から削除された PEL から。

xreadgroup GROUP cg1 c1 count 1 ストリーム stream2 >

「GROUP」はキーワード、「cg1」は消費グループの名前、「c1」は消費者の名前、「count 1」は消費量を示し、> 記号は、その last_delivered_id から読み取りを開始することを意味します。現在の消費グループ。コンシューマがメッセージを読み取るたびに、last_delivered_id 変数が進みます。

 

以前に cg1 を定義したときは、それを最初から使用したため、自然に最初のメッセージが Stream2 に取得されました。

上記のコマンドを再度実行します

 

当然、次のメッセージが読まれました。

Stream2 のメッセージの読み取りを終了します

xreadgroup GROUP cg1 c1 count 2 ストリーム stream2 >

当然、読み取るメッセージはありません。 xreadgroup GROUP cg1 c1 count 1 streams stream2 >

 

次に、ブロッキング待機を設定します

xreadgroup GROUP cg1 c1 ブロック 0 カウント 1 ストリーム stream2 >

 

新しいクライアントを開き、stream2 にメッセージを送信します。

xadd stream2 * ネーム リソン スコア 98

 元のクライアントに戻ると、ブロックが解除され、新しいメッセージが受信されることがわかります。

 

消費者団体の現状を観察してみよう

 

同じコンシューマ グループに複数のコンシューマが存在する場合は、xinfo Consumers コマンドを使用して各コンシューマのステータスを観察することもできます。

xinfo コンシューマー stream2 cg1

コンシューマ c1 には現在 ACK を待機している 5 つのメッセージがあり、441340 ミリ秒の間アイドル状態になった後、メッセージをまったく読み取っていないことがわかります。

メッセージを確認させていただきましたら

xack ストリーム 2 cg1 1626751586744-0

確認するメッセージが4になっているのが分かります

 xack では、次のような複数のメッセージ ID が許可されます。

 

同時に、Stream は、コンシューマ グループまたはコンシューマ内のコンシューマの未処理メッセージを取得するためのコマンド XPENDIING も提供します。各保留メッセージには、次の 4 つの属性があります。

メッセージID

消費者のもの

IDLE、読み取り時間

配信カウンター、メッセージが読まれた回数

コマンド XCLAIM は、メッセージ転送操作を実行し、メッセージを独自の保留リストに転送するために使用されます。グループ、転送対象コンシューマ、メッセージIDを設定するとともに、IDLE(読み取られた時間)を設定する必要があり、この時間が経過した後にのみ送信可能となります。転送される。

Redis Stream コマンドの詳細については、Redis の公式ドキュメントを参照してください。

https://redis.io/topics/streams-intro

コマンド | レディス

同時に、Redis ドキュメントでは、各コマンドの詳細ページの右側に「関連コマンド」が表示され、この一覧から関連コマンドをすぐに知り、特定のコマンドの詳細ページにアクセスできます。

おすすめ

転載: blog.csdn.net/yaya_jn/article/details/130098107