6

我目前正在将 JMS 支持添加到类似应用程序服务器的框架中。JMS 将由 HornetQ(独立代理,服务器类路径上的 hornetq jars)实现,但既没有 JBoss,也没有 spring,也没有任何其他可以提供 MDB 的东西。

下一步是将消息侦听器添加到允许并行处理传入消息的 xa 队列。一些消息会启动长时间运行的任务,所以基本思想是从onMessage方法中产生工作线程。

在我漫长的互联网之旅中,我遇到了这个讨论,其中一位参与者提到,他不会这样做,而是使用一个额外的内部队列来完成任务:(单线程)消息监听器然后会简单地从入站队列并为内部队列创建新消息,在该内部队列的另一端,一些工作线程争夺传入消息。一旦入站消息被“复制”到内部队列(这对我来说没问题),它们就会被确认。

不幸的是,他们没有说明为什么最好不要从该onMessage方法中产生工作线程 - 也许是因为如果池中的所有线程都忙,侦听器会阻塞。所以我正在寻找设计决策的利弊:

  • 从消息监听器的 onMessage 方法启动工作线程
  • 使用内部队列“向工作线程发送消息”
4

1 回答 1

3

撇开事务限制不谈,是否有多个线程(或进程)从队列中读取简单归结为消息顺序是否重要。显然,如果顺序很重要,那么单个线程自然会维护该顺序,而多个线程将不提供这样的保证。

您通常会发现,顺序很重要,但在所有消息的子集中。在这种情况下,如果单个线程不高效,您需要将这些消息从队列中取出并在尽可能短的时间内重新排队,因为为了保持顺序,您必须使用从初始值读取的单个线程queue - 因此使用一个或多个内部队列。这导致的问题是事务将在消息完全处理之前关闭,因此您需要某种临时存储来确保如果在处理发生之前进程发生故障,消息不会被丢弃。

如果正如您的问题所暗示的那样,您不太担心丢弃消息,那么java.util.concurrent.BlockingQueue听起来就像您需要的内部队列有一个单独的线程为每个队列提供服务。

于 2012-12-18T18:07:40.237 回答