【发布时间】:2017-09-26 16:28:41
【问题描述】:
我们计划使用 AWS SQS 服务对从 Web 服务创建的事件进行排队,然后使用多个工作器来处理这些事件。一个事件只能处理一次。根据 AWS SQS 文档,AWS SQS 标准队列可以“偶尔”产生重复的消息,但吞吐量不受限制。 AWS SQS FIFO 队列不会产生重复的消息,但吞吐量限制为每秒 300 个 API 调用(batchSize=10,相当于每秒 3000 条消息)。我们目前的高峰时段流量仅为每秒 80 条消息。因此,就吞吐量要求而言,两者都很好。但是,当我开始使用 AWS SQS FIFO 队列时,我发现我需要做一些额外的工作,比如提供额外的参数 “MessageGroupId”和“MessageDeduplicationId”或需要启用“ContentBasedDeduplication”设置。所以,我不确定哪个是更好的解决方案。我们只需要不重复的消息。我们不需要消息是先进先出的。
解决方案 #1: 使用 AWS SQS FIFO 队列。对于每条消息,需要为“MessageGroupId”和“MessageDeduplicationId”参数生成一个UUID。
解决方案 #2: 使用启用了“ContentBasedDeduplcation”的 AWS SQS FIFO 队列。对于每条消息,需要为“MessageGroupId”生成一个UUID。
解决方案 #3: 将 AWS SQS 标准队列与 AWS ElasticCache(Redis 或 Memcached)结合使用。对于每条消息,“MessageId”字段将保存在缓存服务器中并稍后检查是否重复。存在意味着此消息已被处理。 (顺便说一句,“MessageId”应该在缓存服务器中存在多长时间。AWS SQS 文档没有提到消息可以复制多远。)
【问题讨论】:
-
我不确定这些是否“更好”。最简单的肯定是使用启用 ContentBasedDeduplcation 的 FIFO 队列。选择您最满意的解决方案。
-
具有 FIFO 的 SQS 保证在特定时间范围内(可能 5 分钟)内没有重复消息,因此如果有重复条目出现,您将收到重复消息。所以你需要通过设计来解决这个问题。
-
生产者(网络服务)通常在几百毫秒内完成。那么,5分钟就够了吗?基本上,我想看看在我们的代码逻辑/缓存服务器中执行“重复数据删除”还是依靠 FIFO 队列更好?
-
在非 FIFO 队列中多次传递消息的异常情况下,ReceiptHandle 几乎肯定不相同,但 MessageId 将是一样。
-
参见my answer to this related question -- “您要求保证 - 您不会得到保证。您可以将消息被多次处理的可能性降低到非常小的数量,但是您不会得到保证。”,以及您可以做什么的详细说明。希望对您有所帮助。
标签: amazon-web-services queue message-queue amazon-sqs