AWS SQSのSend Message API Batchでは、重複排除が行たとしてもSuccessfulとして扱われる
TL;DR
- AWS SQSのSend Message API Batchの挙動を確認した。
- 重複排除が行われるメッセージを登録する場合のレスポンス形式を調べた。
- 重複排除が行われるかどうかに関わらず、Successfulとして扱われる事が確認できた。
はじめに
今日、ミーティングでとある質問を受けた。それは僕が先日抱いた疑問と同じ内容だった。先日の僕はそれについて調査し、その内容を真似したダミーサーバをプログラミングするまでしていた。だから、その質問に自信満々に答えた。
しかし、よく思い出してみると、先週の僕は調査と呼べるほどの調査をしておらず、ChatGPTに挙動を聞いただけだった。今になって思えば、それを「調査」と言えるほどの確認ではなかったと反省している。
その時は「これは一旦この挙動が正しいと考え、後で確認する必要がある」と認識していたが、今日の僕はその事をすっかり忘れてしまっていた。
最近こういう事がよくある。ちゃんと確認した情報と、ChatGPTに聞いただけの情報の区別が曖昧になっている。それらの区別はおそらくもうできなさそうだ。それだけAIの回答を正しいものとして認識してしまっている節がある。自分がこういう振る舞いをするという事を認識し、今後は注意していきたい。
Sed Message Batch APIで重複排除が行われた場合のレスポンス形式
今回の質問の内容は、AWS SQSのAPIの挙動についての何気無い内容だった。SQSのSed Message Batch APIでメッセージを登録した時、そのメッセージが重複排除の機構によって取り除かれた場合、取り除かれたメッセージはAPIのレスポンスのSuccessfulとして扱われるのか、それともFailedとして扱われるのかという事だ。とりあえず、本稿では今日の僕がウソツキじゃなかったという事を、実際にSQSのAPIを呼出して確認しよう。
import os
import boto3
from pprint import pprint
env = os.environ
AWS_ACCESS_KEY_ID = env["AWS_ACCESS_KEY_ID"]
AWS_SECRET_ACCESS_KEY = env["AWS_SECRET_ACCESS_KEY"]
QUEUE_URL = env["QUEUE_URL"]
boto3_session = boto3.Session(
aws_access_key_id=AWS_ACCESS_KEY_ID,
aws_secret_access_key=AWS_SECRET_ACCESS_KEY,
region_name="ap-northeast-1",
)
sqs_client = boto3_session.client("sqs")1回目
まずはメッセージを登録する。
resp = sqs_client.send_message_batch(
QueueUrl=QUEUE_URL,
Entries=[
{
"Id": "0",
"MessageGroupId": "GROUP:NAME",
"MessageDeduplicationId": "DUP-1",
"MessageBody": "MESSAGE VALUE"
}
]
)
pprint(resp)
{'ResponseMetadata': {'HTTPHeaders': {'connection': 'keep-alive',
'content-length': '172',
'content-type': 'application/x-amz-json-1.0',
'date': 'Tue, 16 Sep 2025 20:45:05 GMT',
'x-amzn-requestid': '43fe9853-b6bc-5878-a475-f910782d8f39'},
'HTTPStatusCode': 200,
'RequestId': '43fe9853-b6bc-5878-a475-f910782d8f39',
'RetryAttempts': 0},
'Successful': [{'Id': '0',
'MD5OfMessageBody': 'fea4270f6a29d2f1243eff3ebe88d95c',
'MessageId': '027bd3ea-912b-44bc-9248-3a49563b880f',
'SequenceNumber': '18896806283192047616'}]}
2回目
同じメッセージを送信し、重複排除を行わせる。
resp = sqs_client.send_message_batch(
QueueUrl=QUEUE_URL,
Entries=[
{
"Id": "0",
"MessageGroupId": "GROUP:NAME",
"MessageDeduplicationId": "DUP-1",
"MessageBody": "MESSAGE VALUE"
}
]
)
pprint(resp)
{'ResponseMetadata': {'HTTPHeaders': {'connection': 'keep-alive',
'content-length': '172',
'content-type': 'application/x-amz-json-1.0',
'date': 'Tue, 16 Sep 2025 20:45:27 GMT',
'x-amzn-requestid': '0e9c96c2-d063-5ace-bb08-f7811ec41d8f'},
'HTTPStatusCode': 200,
'RequestId': '0e9c96c2-d063-5ace-bb08-f7811ec41d8f',
'RetryAttempts': 0},
'Successful': [{'Id': '0',
'MD5OfMessageBody': 'fea4270f6a29d2f1243eff3ebe88d95c',
'MessageId': '027bd3ea-912b-44bc-9248-3a49563b880f',
'SequenceNumber': '18896806283192047616'}]}
重複排除が行われるメッセージであってもSuccessfulとして扱われた。
同一のリクエストに2つの重複するメッセージ
それでは同一のMessageDeduplicationIdを持つメッセージが1つのリクエスト内に2つ存在する場合はどうなるのだろうか。
resp = sqs_client.send_message_batch(
QueueUrl=QUEUE_URL,
Entries=[
{
"Id": "0",
"MessageGroupId": "GROUP:NAME",
"MessageDeduplicationId": "DUP-1",
"MessageBody": "MESSAGE VALUE"
},
{
"Id": "1",
"MessageGroupId": "GROUP:NAME",
"MessageDeduplicationId": "DUP-1",
"MessageBody": "MESSAGE VALUE"
}
]
)
pprint(resp)
{'ResponseMetadata': {'HTTPHeaders': {'connection': 'keep-alive',
'content-length': '328',
'content-type': 'application/x-amz-json-1.0',
'date': 'Tue, 16 Sep 2025 20:47:09 GMT',
'x-amzn-requestid': 'dab7a61e-3076-58c9-ba55-c75dff7b02fe'},
'HTTPStatusCode': 200,
'RequestId': 'dab7a61e-3076-58c9-ba55-c75dff7b02fe',
'RetryAttempts': 0},
'Successful': [{'Id': '0',
'MD5OfMessageBody': 'fea4270f6a29d2f1243eff3ebe88d95c',
'MessageId': 'ca730bf2-1080-43ff-b0a3-6d22f79e0c01',
'SequenceNumber': '18896806314807535872'},
{'Id': '1',
'MD5OfMessageBody': 'fea4270f6a29d2f1243eff3ebe88d95c',
'MessageId': 'ca730bf2-1080-43ff-b0a3-6d22f79e0c01',
'SequenceNumber': '18896806314807535872'}]}
1つのリクエスト内で重複排除が行われるメッセージが複数あったとしてもSuccessfulとして扱われた。
結論
AWS SQSのSend Message Batch APIは、重複排除が行われるメッセージを登録したとしても、レスポンスとしてはSuccessfulとして扱われる。
また今日の僕は嘘つきではなかった。よかった