如何处理JMS中的消息顺序?

我正在审查用Java编写的客户端 – 服务器应用程序。 服务器接收JMS消息并处理它们,但消息可能以意外的顺序出现,并且取消可以在订单消息之前到达。 你是如何处理这种情况的? 你在mdb中做到了吗?

这种情况有哪些策略或模式?

到目前为止,我知道,这被称为“无序”传递,并且是JMS系统的服务质量(QoS)属性的一部分。 我不认为它是JMS规范的一部分,但有些提供商可能支持它。 这取决于您使用的特定JMS实现。

但请注意,JMS旨在以分配负载的方式将消息分发给多个使用者。 如果必须以有序的方式传递消息,则这是不可能的 – 它基本上导致消息传递的序列化,并且消息不能同时处理。

维基百科说它比我好:

JMS队列一个临时区域,包含已发送且正在等待读取的消息。 请注意,与名称队列建议的内容相反,消息不必按发送的顺序传递。 如果消息驱动的bean池包含多个实例,则可以同时处理消息,因此可能比以前的消息更早地处理消息。 JMS队列仅保证每条消息只处理一次。

然后使用JMS很难实现带外取消请求。 两个想法:

  • 存储与数据库中的每条消息相对应的票证可用于轻松取消消息。 邮件传递时,MDB会检查相应的票证是否仍然有效。 如果是,则继续进行,如果没有,则删除该消息。
  • 尝试将MDB池大小设置为1。 也许在这种情况下,将订购交货。 更改池大小是应用程序。 特定于服务器,但大多数支持每个bean池大小。

否则,可以查看消息存储模式。 无论如何,这都值得检查EAI网站。

如果它可以处理无序消息,您的系统将更加灵活。 我过去用来解决这个问题的模式是使用延迟队列(在金融世界每天处理800万条消息的系统上)。

在您的示例中,如果我收到了尚未收到的订单的删除,我会将其延迟一段时间并重试。 如果我仍然不知道我被要求删除的顺序,我会提出某种错误(回复原始发件人,将消息发送到特殊错误队列,……)。

至于延迟队列的实现,这可以是具有可以接受要延迟的消息的服务的另一个JMS队列。 然后,它会定期读取延迟的消息,并检查延迟的时间段是否已过期,并将消息重新提交到原始目标队列。

我的第二个关于检查EAI网站的建议,以及它所依据的书(关于MOM和MOM模式的精彩文本)。

我个人会调查Resequencer 。

如何确保mdb收到的消息序列? 是关于服务器端的类似主题,有人指出ActiveMQ可能有一个保留订单的解决方案。 我想这会使它具有特定性。