我有一个SQS队列,一直由数据使用者填充,我现在正在尝试创建一个服务,使用Python的boto从SQS中提取这些数据。
我设计它的方式是我将有10-20个线程都尝试从SQS队列中读取消息,然后在返回队列获取之前对数据(业务逻辑)执行必须执行的操作他们完成后的下一批数据。如果没有数据,他们将等待一些数据可用。
我有两个方面我对这个设计不太确定
谢谢
答案 0 :(得分:14)
receive_message()
方法的长轮询功能是轮询SQS的最有效方法。如果返回没有任何消息,我会建议在重试之前短暂延迟,特别是如果你有多个读者。您甚至可能希望执行增量延迟,以便每个后续的空读取等待更长时间,这样您就不会受到AWS的限制。
是的,您必须在阅读后删除该消息,否则它将重新出现在队列中。在工作人员阅读消息然后在完全处理消息之前失败的情况下,这实际上非常有用。在这种情况下,它将被另一名工人重新排队并读取。您还需要确保将消息的不可见性超时设置为足够长,以使工作人员有足够的时间处理消息,然后再自动重新出现在队列中。如果需要的话,如果需要的时间超过预期,您的工作人员可以在处理时调整超时。
答案 1 :(得分:5)
另一个选择是使用AWS Beanstalk设置工作程序应用程序,如this blogpost中所述。
而不是使用boto3进行长轮询,您的烧瓶应用程序会在HTTP帖子中将该消息作为json对象接收。所设置的HTTP路径和消息类型可在AWS Elastic Beanstalk配置选项卡中进行配置:
AWS Elastic Beanstalk的另一个好处是能够根据SQS队列的大小动态扩展工作者数量及其部署管理优势。
This是我发现作为模板有用的示例应用程序。
答案 2 :(得分:5)
如果您想要一种简单的方法来设置一个侦听器,该侦听器包括在完成处理后自动删除消息,并自动将异常推送到指定队列,您可以使用pySqsListener包。
你可以像这样设置一个监听器:
from sqs_listener import SqsListener
class MyListener(SqsListener):
def handle_message(self, body, attributes, messages_attributes):
run_my_function(body['param1'], body['param2']
listener = MyListener('my-message-queue', 'my-error-queue')
listener.listen()
目前该软件包使用短轮询,但我正在考虑使轮询类型可配置。
免责声明:我是该套餐的作者。