SQSの標準キューとFIFOキューの違いを検証してみた

AWS

SQSには「標準キュー」と「FIFOキュー」という2つのタイプが存在します。
それぞれのタイプについて動作の違いを検証してみました。

標準キューとFIFOキューの特徴

まず、標準キューとFIFOキューの違いとしてそれぞれ以下の特徴があります。

項目標準キューFIFOキュー
メッセージの順序性メッセージが送信されたときと
異なる順序で配信されることがある。
メッセージが送信または受信された順序が
厳密に保持される。 (先入れ先出し)。 
スループット 1 秒あたりのほぼ無制限の数のトランザクション (TPS) をサポート。デフォルトだと毎秒最大 300 件のメッセージをサポート。
高スループットモードを有効にすると、
バッチ処理ありで 1 秒あたり最大 30,000 件のメッセージ、バッチ処理なしで 1 秒あたり最大 3,000 件のメッセージをサポート。
メッセージの配信メッセージは少なくとも 1回は確実に配信されるが、1回以上配信されることもある。1回しか配信されない。ユーザーがそれを処理して削除するまでは使用可能な状態に保たれる。
コスト月々100万リクエストまで無料。
100万リクエスト以上は0.3$~0.4$の料金が発生。
月々100万リクエストまで無料。
100万リクエスト以上は0.4$~0.5$の料金が発生。
メッセージの重複排除キューに同じ内容のメッセージを連続して送信した場合、重複した分もキューの格納できる。キューに同じ内容のメッセージを連続して送信した場合、
重複した分についてはキューに格納不可。

実機検証

今回は標準キューとFIFOキューそれぞれで「メッセージの順序性」、「メッセージの配信」、「メッセージの重複排除」について実機検証してきます。

【検証の流れ】

  1. メッセージの順序性の検証
  2. メッセージの配信時の挙動に関する検証
  3. メッセージの重複排除の検証

【前提】

・標準キューとStandardキューの準備。
・キューに対して操作(送信/受信)するEC2インスタンスの準備。

1.メッセージの順序性の検証

キュー(標準/FIFO)にメッセージを順番に送信後、キューからメッセージを連続して取り出した時にどういう順番になるか。

標準キュー

標準キューに対して、メッセージ1~4を順番に送信する。

# aws sqs send-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXXX/sqs-standard --message-body messages1

# aws sqs send-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXX/sqs-standard --message-body messages2

# aws sqs send-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXX/sqs-standard --message-body messages3

# aws sqs send-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXX/sqs-standard --message-body messages4

標準キューに対してメッセージを取得してみる。

# aws sqs receive-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXXX/sqs-standard
【出力結果】
"Body": "messages1"

# aws sqs receive-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXXX/sqs-standard
【出力結果】
"Body": "messages3"

# aws sqs receive-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXXX/sqs-standard
【出力結果】
"Body": "messages4"

# aws sqs receive-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXXX/sqs-standard
【出力結果】
"Body": "messages2"

# aws sqs receive-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXXX/sqs-standard
【出力結果】
無し

標準キューでは出力の順番がばらばらであることがわかる。
また、1つめのメッセージを取り出してから連続でメッセージを取り出すことが可能。
メッセージを取り出すと「可視性タイムアウト」が発生し、タイムアウトになるまでそのメッセージをキューから削除することができます。
5回目のreceive-messageコマンドで出力結果が無しなのは、キューに入っている取り出し可能なメッセージが無いからです。一度取り出したメッセージは「可視性タイムアウト」になるまで再度取り出すことはできません。
ただしタイムアウト後は取り出し可能なメッセージとして再度利用することができます。

FIFOキュー

FIFOキューにも同様にメッセージを送信する。
※FIFOキューの場合は–message-group-idを指定する必要がある。

# aws sqs send-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXXX/sqs-standard --message-body messages1 --message-group-id group-fifo

# aws sqs send-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXXX/sqs-standard --message-body messages2 --message-group-id group-fifo

# aws sqs send-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXXX/sqs-standard --message-body messages3 --message-group-id group-fifo

# aws sqs send-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXXX/sqs-standard --message-body messages4 --message-group-id group-fifo

FIFOキューからメッセージを取り出してみます。

# aws sqs receive-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/336137140379/sqs-fifo.fifo
【出力結果】
"Body": "messages1"

# aws sqs receive-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/336137140379/sqs-fifo.fifo
【出力結果】
無し

FIFOキューの場合は1つ目のメッセージを取り出し後に2つ目のメッセージを取得しようとすると何も出力されませんでした。
1つ目のメッセージを可視性タイムアウト期間内に削除してみます。
キューからメッセージを削除するにはdelete-messageを使います。

# aws sqs delete-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXXX/sqs-fifo.fifo --receipt-handle AQEBAapcxe9htdZ9JPXD5wCx4FoLDqtofoJe46mMBSXfOHtgFmgu4YobUJAKFE0wn6qwQlfz0WJICWMgzGLc6fjPmsYMiS1BKxCG9paxC+Ag6KKDP35l/FLdcwE/7Z7jAa9NuUmlzpmacxI1W8ZGYLhD4aHFufPPTwxVj+O9HwUqu8Lf3UBj4Veey+NNeqHo5EqA346qow7FuwX0RYVbFXxUyy40ZM8Gp1yBoHm9UJM0H5oPjXoaheCGq930s8s2yofo+fOEnh9kitqUD82DH7GO63yFMBmTg/dR41q4KMFCfy8=

削除後に再度メッセージを取得してみます。
【補足】
可視性タイムアウトを過ぎるとそのメッセージについては削除できなくなります。
削除する場合は再度メッセージを取得し、新しいreceipt-handle値を取得する必要があります。
(この仕様は標準キューでも同様です。)

# aws sqs receive-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXXX/sqs-fifo.fifo

【出力結果】
"Body": "messages2"

2つ目のメッセージを取得することができました。
FIFOキューの仕様として、取り出したメッセージを削除しないと次のメッセージを取得できないようです。

同様にメッセージ取得⇒削除を繰り返しFIFOキューのメッセージを取得してみます。

# aws sqs receive-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXXX/sqs-fifo.fifo
【出力結果】
"Body": "messages2"
# aws sqs delete-message (省略)

# aws sqs receive-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXXX/sqs-fifo.fifo
【出力結果】
"Body": "messages3"
# aws sqs delete-message (省略)

# aws sqs receive-message --queue-url https://sqs.ap-northeast-1.amazonaws.com/XXXXX/sqs-fifo.fifo
【出力結果】
"Body": "messages4"

FIFOキューの場合はメッセージの取り出し順が送信順に保たれていました。

2.メッセージの配信時の挙動に関する検証

標準キューとFIFOキューのメッセージ配信時の挙動は「1.メッセージの順序性の検証」で大体わかりました。
FIFOキューの場合はメッセージグループIDというものが存在するため、複数メッセージグループIDがある場合のメッセージ配信について検証していきます。

下記図のとおりFIFOキューにメッセージグループ1~3に対してそれぞれメッセージを1~3を送信している状態です。

メッセージを順番に取り出すとそれぞれのメッセージグループの1つ目のメッセージを取得することができました。(メッセージ 1⇒4⇒7の順に取得。)

上記状態で2つ目以降のメッセージを取得しようしてもFIFOの仕様により
1つ目のメッセージを削除しないと取得できない。

次はメッセージ1~9を番号順にそれぞれのメッセージグループに送信した状態から、
メッセージを1つずつ取得&削除を繰り返すと取得するメッセージの順番がどうなるか確認。

メッセージの送信順と同じ順番で取得することができました。

キューからメッセージを1件ずつ取得&削除を実施するとメッセージグループに限らず、キューに対して送信した順番に取り出せることがわかりました。
同時にメッセージグループ内の取り出し順も保持されています。

次は、キューからメッセージを取得する際に件数も指定することができました。
※最大10件まで1回のreceive-messageで取得可能。
メッセージ取得結果をみると、メッセージグループ1内のメッセージが優先して取得されていることわかりました。
①メッセージグループ1のメッセージを全て取得。
②メッセージグループ2のメッセージを全て取得。
➂メッセージグループ3のメッセージを全て取得。

キューからまとめて(件数を指定して)メッセージを取得しようとするとメッセージグループ単位で取得しようとすることが分かりました。

3.メッセージの重複排除の検証

標準キューとFIFOキューにそれぞれ同じ内容のメッセージを送信してみます。

標準キュー

標準キューでは同じメッセージを連続してキューに送信することが可能。

FIFOキュー

同一メッセージグループ内に対して同じメッセージを連続して送信することができませんでした。
重複排除期間は 5 分と決められており、5分後には同じメッセージを送信することができました。

また、別のメッセージグループに対してメッセージ1を送信することもできませんでした。
ただし、5分後は送信可能。

コメント

タイトルとURLをコピーしました