消息处理时长自适应

更新时间:2025-02-18 06:06:16

本文介绍在消息消费过程中实现消息处理时长自适应的背景概念、应用场景及解决方案。

背景概念

  • 可见状态:消息处于可见状态时,意味着消息可以被消费者(接收和处理消息的服务或应用程序)读取和接收。

  • 不可见状态:当消费者接收了一条消息后,这条消息会进入不可见状态,意味着其他消费者在此期间无法接收到这条消息,以免消息被多个消费者同时处理。

  • 可见性超时时间:是指从消费者接收消息开始到允许其它消费者再次接收该消息的时间段。

当消费者从队列接收消息时,消息仍然保留在队列中,但对其它消费者暂时不可见。暂时不可见状态由可见性超时机制控制,防止其它消费者在该消息正在处理时重复处理同一条消息。

关于可见性超时时间的更多信息,请参见可见性超时时间(Visibility Timeout)

应用场景

轻量消息队列(原 MNS)的规范中,每条消息都有默认的可见性超时时间。消费者在接收到消息后,立即开始计时。 如果消费者在可见性超时时间内没能处理完消息,那么消息就有可能被其他消费者接收到并处理。计时的好处在于消息处理完之后需要显式地删除消息,如果消费者进程停止等异常情况发生,这条消息还有机会被其他消费者处理。

一些用户会将队列的默认可见性超时时间设置得比较长,以确保消息在被消费者处理完之前不会超时释放。例如,队列的可见性超时时间是6个小时。一个消费者接收到了消息M1,但是消费者在处理完消息之后,进程发生了崩溃或者机器发生了重启。那么M1这条消息至少在6个小时之后才会被另一个消费者接收到并处理。如果自己写代码处理故障,程序又会变得比较复杂。

在一些即时性要求比较高,并且又希望尽快响应每一条消息的场景下,消息消费需要实现以下目标:

  • 队列的可见性超时时间比较短。在发生了进程崩溃后,未处理完的消息会在较短的可见性超时时间内被某个消费者接收到并处理。

  • 消息被处理时不能超时。消费者处理消息的过程中,耗时很有可能超过5分钟,那么消息在被处理的过程中不能超时。

解决方案

轻量消息队列(原 MNS)提供的C# SDK可以实现这样的场景。具体的做法是,在消费者处理消息的过程中,为消息定期检查是否需要做ChangeVisibility,消费者处理完之后依然是主动删除消息。

C# SDK的下载地址,请参见C++ SDK,如有Demo使用问题,可提交工单处理。

下面是对于程序的几点说明:

  • 运行前需要填写accessIdaccessKeyEndPoint

  • 变量说明:

    变量

    说明

    变量

    说明

    MessageMinimalLife

    消息注册时必须有的最少的Life长度。例如,消息注册的时候已经只剩下0.1秒的超时时间了,注册进来也来不及ChangeVisibility延长生命。所以,MessageMinimalLife是为了确保消息能存活到被ChangeVisibility,您可以根据业务压力自行设置。

    TimerInterval

    Manager内部的TimerInterval。只需要确保在Message到达MessageMinimalLife之前,Timer会被启动就足够了。时间可以设置得较短(时间设置得较短会导致频繁检查)。

    QueueMessageVisibilityTimeout

    消息的默认超时时间,是Queue的属性。每次ChangeVisibility的时候,会把消息的可见性超时时间设置为QueueMessageVisibilityTimeout,所以它的值需要大于TimerInterval+ MessageMinimalLife,以确保消息不会超时。

    MessageTimeout

    消息在Manager中的超时时间,例如某个消费者卡住了,消息在5个小时之后依然没有处理完毕(假设5个小时远远超出消息的正常处理时间),那么Manager就不会再为消息做ChangeVisibility了,而是会放任消息的Visibility超时。

  • 流程说明:

    • 消费者在接收消息之后,会先做注册消息,然后处理消息,最后再调用Manager的删除消息(deleteMessage)。

    • Manager在消息第一次注册进来之后,调用ThreadPool调度一个ChangeVisibilityTask检查是否需要ChangeVisibility,并且把Message添加到内部的messages列表中。

    • Manager内部的Timer,会定时调用Parallel启动 ChangeVisibilityTask检查消息列表里的所有消息。

    • Manager.ChangeMessageVisibility (ChangeVisibilityTask)相关的具体操作,在流程图里有显示。

      流程图如下所示:

      image
  • 本页导读 (1)
  • 背景概念
  • 应用场景
  • 解决方案