当前位置: 首页 > 知识库问答 >
问题:

AWS SQS标准队列的并行轮询-消息处理太慢

穆丁雨
2023-03-14

我有一个模块,它用ReceiveMessageRequest以指定的时间间隔轮询AWS SQS队列,每次一条消息。方法如下:

public static ReceiveMessageResult receiveMessageFromQueue() {

    String targetedQueueUrl = sqsClient.getQueueUrl("myAWSqueueName").getQueueUrl();
    ReceiveMessageRequest receiveMessageRequest = new ReceiveMessageRequest(targetedQueueUrl)
            .withWaitTimeSeconds(10).withMaxNumberOfMessages(1);
    return sqsClient.receiveMessage(receiveMessageRequest);
}

接收并处理消息后,使用DeleteMessageResult将其从队列中删除。

public static DeleteMessageResult deleteMessageFromQueue(String receiptHandle) {

    log.info("Deleting Message with receipt handle - [{}]", receiptHandle);
    String targetedQueueUrl = sqsClient.getQueueUrl("myAWSqueueName").getQueueUrl();
    return sqsClient.deleteMessage(new DeleteMessageRequest(targetedQueueUrl, receiptHandle));

}

我已经创建了一个可执行的jar文件,它部署在大约40个实例中,并且正在积极地轮询队列。我能看到他们每个人都收到信息。但在AWS SQS控制台中,我只能在“飞行中的消息”栏中看到数字0、1、2或3。为什么即使有40多个不同的消费者正在从队列接收消息呢?此外,队列中可用的消息数量减少得非常缓慢。

Default Visibility Timeout: 30 seconds
Message Retention Period:   4 days
Maximum Message Size:   256 KB
Receive Message Wait Time:  0 seconds
Messages Available (Visible):   4,776
Delivery Delay: 0 seconds
Messages in Flight (Not Visible):   2
Queue Type: Standard
Messages Delayed:   0
Content-Based Deduplication:    N/A 

共有1个答案

长孙谦
2023-03-14

我会尽我所能提供给你的信息。更多关于您的处理循环逻辑、区域设置和度量(见下文)的详细信息将有助于改进这个答案。

我已经创建了一个可执行的jar文件,它部署在大约40个实例中,并且正在积极地轮询队列。我能看到他们每个人都收到信息。但在AWS SQS控制台中,我只能在“飞行中的消息”栏中看到数字0、1、2或3。为什么即使有40多个不同的消费者正在从队列接收消息呢?此外,队列中可用的消息数量减少得非常缓慢。

为什么即使有多个消费者,消息也得不到快速处理?我是否需要修改接收消息/删除消息请求中的任何队列参数或其他内容?

    null
  • CloudWatch将为您提供部分功能,但实际的客户端度量标准总是有用的。
  • 推荐以下基本度量:(1)接收延迟,(2)处理延迟,(3)删除延迟,(4)整个消息循环延迟(5)成功/失败计数器
  • 确保这些主机有足够的CPU/内存资源来进行处理
  • 作为一种优化,我建议每台主机使用更多的线程,而使用更少的主机--重用客户端连接&最大限度地利用您的计算资源总是更好的。
  • 这实际上是我在您的代码中注意到的第一件事,但它在这里是因为上面的问题如果是原因的话会产生更大的影响。
    null

进一步注意:

  • 另一个答案认为可见性超时是一个潜在原因--这完全是错误的。可见性超时不会阻塞队列--它只会影响消息在另一个receiveMessageRequest能够接收到该消息之前“正在运行”的时间。
  • 如果您希望在出现错误/处理速度慢的情况下更快地重新处理消息,您可以考虑减少这一点。
 类似资料:
  • 需求:构建一个基于。NET的应用程序,该应用程序可以定期从IBM Websphere消息队列读取消息,并将这些消息保存到数据库中

  • 我有两个消费者(不同的应用程序)连接到Azure队列。我可以或消息,在消费过程中,我可以或消息。裁判:http://msdn.microsoft.com/en-us/library/azure/hh851750.aspx. 我确定我想使用,然后消息,因为我希望它们在两个应用程序中被接收。我想我应该将队列上的消息生存期设置为10秒,作为删除机制。 然而,由于消息似乎在10秒钟后被删除,因此在这10秒

  • 我将与一起使用中的这个库。所有使用者均为,所有队列均为(4小时)。 我有很多队列没有任何挂起的ack,但仍然保存着数百条消息。此外,队列不会在应该过期时过期,这将在几天后产生性能问题。我没有找到任何理由来解释为什么消息在ack处理之后仍然在队列中。 谢谢 管理工具中的一些快照:

  • 问题内容: 正在寻找一种简单的方法(即,不需要我设置单独的服务器来处理消息队列的方法)来对运行计算并生成图形的小型Web界面进行长轮询。这是我的网络界面需要执行的操作: 用户在Web界面中请求图形/数据 服务器运行一些计算。 当服务器运行计算时,将随计算进度更新一个小容器(可能通过AJAX / jQuery)(类似于您在使用consol进行打印时所做的操作(即打印“计算密度函数…”)) 计算完成并

  • 我可以在solace JMS队列中搜索任何特定的消息,然后在其他消息之前处理吗?我们有这样的功能w. r. t慰藉队列。

  • 为什么已经拥有了共享内存时需要消息队列呢? 这将是多种原因,让我们将其分解为多个点来简化 - 据了解,一旦消息被一个进程接收到,它将不再可用于任何其他进程。 而在共享内存中,数据可供多个进程访问。 如果想使用小信息格式进行通信。 当多个进程同时进行通信时,共享内存数据需要同步保护。 使用共享内存的写入和读取频率很高,那么实现功能将会非常复杂。 在这种情况下不值得使用。 如果所有的进程不需要访问共享