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

骆驼vs ActiveMQ中的死信队列?

谷良弼
2023-03-14

我正在使用死信频道EIP与骆驼文件中描述的死信频道完全相同。这是我的camel.xml(删除头)

<camelContext id="camel"  xmlns="http://camel.apache.org/schema/spring">

            <!-- this is the Dead Letter Channel error handler, where we send failed message to a log endpoint -->




    <route  errorHandlerRef="myDeadLetterErrorHandler">

        <from uri="jms:q1" />
                    <doTry>
                            <validate><simple>${body[subsc]} regex '[a-z0-9]{8}' </simple> </validate>
                            <choice>
                                    <when>
                                            <simple>${body[key1]} regex '^(v1)$'</simple>
                                            <choice>
                                                <when>
                                                       <simple>${body[key2]} == 'v2'</simple>
                                                           <to uri="jms:getInfo" />
                                                 </when>
                                            </choice>        
                                    </when>
                                    <otherwise>
                                    <to uri="jms:invalid" />
                                    <stop />
                                    </otherwise>
                            </choice>
                    <doCatch>
                            <exception>org.apache.camel.ValidationException</exception>
                            <to uri="jms:invalid"/>
                    </doCatch>
                    </doTry>

    </route>

    <route>
        <from uri="jms:queue:deadlc" />
        <log message="Got ${body}" loggingLevel="ERROR" logName="cool" />
    </route>

</camelContext>

<!--
   Lets configure some Camel endpoints

   http://camel.apache.org/components.html
-->

<!-- configure the camel activemq component to use the current broker -->

<bean id="confact" class="org.apache.activemq.ActiveMQConnectionFactory">
        <property name="brokerURL" value="vm://amq-broker?create=false"/>
        <property name="userName" value="${activemq.username}"/>
        <property name="password" value="${activemq.password}"/>
</bean>

<bean id="activemq" class="org.apache.activemq.camel.component.ActiveMQComponent" >
    <property name="connectionFactory" ref="confact" />

</bean>

<bean id="pooledConnectionFactory" 
      class="org.apache.activemq.pool.PooledConnectionFactory" 
      init-method="start" 
      destroy-method="stop">
    <property name="maxConnections" value="8" />
    <property name="connectionFactory" ref="confact" />
     <property name="expiryTimeout" value="-1" />  
    <property name="idleTimeout" value="-1" />
</bean>

<bean id="jmsConfig"  class="org.apache.camel.component.jms.JmsConfiguration">
    <property name="connectionFactory" ref="pooledConnectionFactory"/>
    <property name="concurrentConsumers" value="8"/>
</bean>

<bean id="jms" class="org.apache.activemq.camel.component.ActiveMQComponent">
    <property name="configuration" ref="jmsConfig"/>
</bean>


<bean id="myDeadLetterErrorHandler" class="org.apache.camel.builder.DeadLetterChannelBuilder">
        <property name="deadLetterUri" value="jms:queue:deadlc"/>
        <property name="redeliveryPolicy" ref="myRedeliveryPolicyConfig"/>
    </bean>

    <bean id="myRedeliveryPolicyConfig" class="org.apache.camel.processor.RedeliveryPolicy">
        <property name="maximumRedeliveries" value="3"/>
        <property name="redeliveryDelay" value="5000"/>
    </bean>

我只有一条路由具有基于内容的路由器,其实质是,如果消息体具有getInfo,则从jms:foo路由到jms:getInfo,如果消息体具有performAction,则从jms.foo路由到jms:performAction

我预计,当jms:getInfo使用者没有运行时,交付将失败,重新交付尝试将与spring XML中指定的一样。但是没有任何事情发生,也没有任何事情进入死信队列,相反,activemq抛出异常,如下所示。

有人能解释一下为什么它不起作用吗?我的理解是,当使用者(它是将从基于内容的路由器接收消息的目的地)未运行时,acivemq知道它甚至不应该传递消息,并且应该立即抛出一个异常,然后按照配置由camel的死信通道处理。

我使用的是camel 2.10.3和activemq 5.8.0。

我怀疑activemq正在处理失败的消息传递,忽略死信队列的骆驼xml配置,因为这些失败的消息显示在activemq web控制台中的activemq.dlq中。如果使用者正在运行,那么消息将根据camel.xml中指定的路由成功传递。

共有1个答案

栾和风
2023-03-14

您的JMS消息具有replyTo=temp-queue:/id:myhost-57639-1382233787365-3:3:6。骆驼期望收到回复消息,这就是为什么你会得到20000毫秒的超时。

 类似资料:
  • 我使用deadLetterChannel来处理异常,并将它们发送到错误队列。 是否可以使用其他邮件标头来丰富邮件?还是我必须为此使用 onException?

  • 我有一个Camel路由,在Karaf中运行,为此我添加了一个死信通道。这是为了处理路由失败的情况,我想保留问题消息并记录原因。我不能将异常抛回调用应用程序,因为我正在异步处理一些处理。 通过阅读文档和尝试大量案例,我不清楚如何将异常记录到Karaf的日志中,并将原始消息存放到死信队列中。 以下是我的摘录:- 如果我删除“onExcgon”结构,那么在所有异常情况下,源消息都会出现在死信队列中,但不

  • 我有一个lambda函数,我想为它创建一个SQS死信队列。我首先在Terraform中创建SQS: 这是来自Terraform的例子。但是,我被redrive_policy卡住了。 我是否正确理解,这为SQS队列设置了一个死信队列? 如果我设置了redrive_policy,这意味着我在一个DLQ上设置了一个DLQ。我觉得可以在DLQ上设置DLQ,在DLQ上设置DLQ,以此类推。 我找不到这方面的

  • 死信队列(Dead Letter Queue)本质上同普通的Queue没有区别,只是它的产生是为了隔离和分析其他Queue(源Queue)未成功处理的消息。 创建死信队列的方法参见createQueue() API,与创建普通队列无异, 死信队列不可调用deadMessage(), deadMessageBatch API,其他操作都与对普通Queue的操作无异。 为了将源Queue的未能成功处理

  • 对于异步的触发器,平台会对函数失败的任务进行最多3次重试。 在新建触发器的时候,为触发器配置一条死信队列,从用户的EMQ队列中选择一条,用于接收函数失败的任务。 在设置死信队列前,请对group: CIf76b0600-24e9-42c4-acf3-d491fbd9fd71​ 授予 FULL_CONTROL 权限,若不授予权限,平台将丢弃失败的任务信息。 消息的内容如下,以后可能增加字段,请用户在

  • 我想在我的 Camel 2.23.2 路由上实现一些内容缓存。在研究过程中,我遇到了骆驼的JCache组件,根据文档,它应该有一个JCache政策,它将: JCachePolicy是路由周围的拦截器,它在路由完成后缓存“路由结果”(消息正文)。如果下次使用“类似”Exchange调用路由,则在Exchange上使用缓存的值,而不是执行路由 这基本上正是我正在寻找的。然而,事实证明,该策略仅适用于C