简体   繁体   English

ule子持久性ActiveMQ重新交付政策

[英]Mule Persistent ActiveMQ RedeliveryPolicy

I am using Mule as ESB solution. 我正在使用Mule作为ESB解决方案。 I have a queue, from where i am getting messages and trying to make http request to service that is failing all the time. 我有一个队列,我从那里获取消息并尝试向一直失败的服务发出http请求。

I have configured the RedeliveryPolicy on ActiveMQ like this: 我已经在ActiveMQ上配置了RedeliveryPolicy,如下所示:

    <spring:bean id="retryRedeliveryPolicy" class="org.apache.activemq.RedeliveryPolicy"
        name="retryRedeliveryPolicy">
        <spring:property name="maximumRedeliveries" value="76" />
        <spring:property name="initialRedeliveryDelay" value="300000" />
        <spring:property name="maximumRedeliveryDelay" value="3600000" />
        <spring:property name="useExponentialBackOff" value="true" />
        <spring:property name="backOffMultiplier" value="2" />
        <spring:property name="queue" value="*" />
    </spring:bean>

It retries after 5min. 5分钟后重试。 then 10min ,20,40,60,60,60... For about ~ 3days 然后10min,20,40,60,60,60 ...大约〜3天

The problem is, that Retry logic is non persistent. 问题是,重试逻辑不是持久性的。

Lets say, message was retrying for 2 days. 可以说,邮件正在重试2天。 And i have deployed new version of mule app, or restarted server... In this case, retry logic will start all over again from 5min, 10min.... Because retry state is kept in RAM memory by the Client. 而且我已经部署了新版本的Mule App或重新启动的服务器...在这种情况下,重试逻辑将从5分钟,10分钟重新开始。...因为客户端将重试状态保存在RAM内存中。

Hot to make RedeliveryPolicy persistent ? 能否使RedeliveryPolicy 持久存在 It must keep retrying for 1 more day after i will restart the server after 2 days. 我将在2天后重新启动服务器后,必须继续重试1天。

One solution i think might be to set timeToLive for 72 hours for message. 我认为一种解决方案可能是将timeToLive设置为72小时以发送消息。 But even then after restarting server. 但是即使重启服务器之后也是如此。 It will not retry every hour from start. 从启动开始,它不会每小时重试一次。 It will start from 5min... 从5分钟开始...

You can use the JMSXDeliveryCount property of the JMS message to check how many times it has been retried already. 您可以使用JMS消息的JMSXDeliveryCount属性来检查它已被重试了多少次。 The retry time interval logic should rely on the JMSXDeliveryCount variable. 重试时间间隔逻辑应依赖于JMSXDeliveryCount变量。

message.getIntProperty("JMSXDeliveryCount ")

http://activemq.apache.org/activemq-message-properties.html http://activemq.apache.org/activemq-message-properties.html

ActiveMQ has a way to do persistent redelivery, but it's not built in using the RedeliveryPolicy on the ConnectionFactory, which is intended for short periods of redelivery before failing. ActiveMQ有一种方法可以进行持久重新交付,但是它不是使用ConnectionFactory上的RedeliveryPolicy内置的,该方法旨在在失败之前进行短暂的重新交付。

Persistent redelivery can be built using the the ActiveMQ scheduler and delayed messages however. 可以使用ActiveMQ调度程序和延迟的消息来建立持久的重新交付。 A bit manual, but doable. 有点手动,但可行。 Make sure you turn on schedulerSupport="true" in ActiveMQ before trying this. 在尝试执行此操作之前,请确保在ActiveMQ中打开schedulerSupport =“ true”。

A JMS property: "delivery" keeps track of number of retries and if things go wrong a catch exception strategy redelivers the message a number of times with a delay. JMS属性:“传递”跟踪重试次数,如果出现问题,则捕获异常策略会延迟多次重新发送消息。 The actual delay is handled by ActiveMQ, so this flow can handle delays of hours, days etc and withstand restarts of both ActiveMQ and Mule. 实际的延迟由ActiveMQ处理,因此此流程可以处理数小时,数天等的延迟,并可以承受ActiveMQ和Mule的重启。

<?xml version="1.0" encoding="UTF-8"?>

<mule xmlns:scripting="http://www.mulesoft.org/schema/mule/scripting"
    xmlns:jms="http://www.mulesoft.org/schema/mule/jms" xmlns:metadata="http://www.mulesoft.org/schema/mule/metadata"
    xmlns="http://www.mulesoft.org/schema/mule/core" xmlns:doc="http://www.mulesoft.org/schema/mule/documentation"
    xmlns:spring="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-current.xsd
http://www.mulesoft.org/schema/mule/core http://www.mulesoft.org/schema/mule/core/current/mule.xsd
http://www.mulesoft.org/schema/mule/jms http://www.mulesoft.org/schema/mule/jms/current/mule-jms.xsd
http://www.mulesoft.org/schema/mule/scripting http://www.mulesoft.org/schema/mule/scripting/current/mule-scripting.xsd">

    <spring:beans>
        <spring:bean name="redeliveryPolicy" class="org.apache.activemq.RedeliveryPolicy">
            <spring:property name="maximumRedeliveries" value="0" />
        </spring:bean>

        <spring:bean name="cf"
            class="org.apache.activemq.ActiveMQConnectionFactory">
            <spring:property name="brokerURL" value="tcp://localhost:61616" />
            <spring:property name="redeliveryPolicy" ref="redeliveryPolicy" />
        </spring:bean>
    </spring:beans>

    <jms:activemq-connector name="Active_MQ"
        specification="1.1" brokerURL="tcp://localhost:61616"
        validateConnections="true" doc:name="Active MQ" numberOfConsumers="1"
        maxRedelivery="-1" connectionFactory-ref="cf" />

    <flow name="testFlow">
        <jms:inbound-endpoint queue="IN" connector-ref="Active_MQ"
            doc:name="JMS">
            <jms:transaction action="ALWAYS_BEGIN" />
        </jms:inbound-endpoint>

        <set-property propertyName="delivery"
            value="#[message.inboundProperties['delivery'] or 0]" doc:name="Property" />

        <scripting:component doc:name="Throw Error">
            <scripting:script engine="Groovy"><![CDATA[throw new java.lang.RuntimeException("Error in processing")]]></scripting:script>
        </scripting:component>

        <choice-exception-strategy doc:name="Choice Exception Strategy">
            <catch-exception-strategy doc:name="Catch Exception Strategy"
                when="#[message.outboundProperties['delivery'] &lt; 5]">
                <logger level="ERROR"
                    message="Retry once more count #[message.outboundProperties['delivery']]"
                    doc:name="Logger" />

                <set-property propertyName="AMQ_SCHEDULED_DELAY" value="3000"
                    doc:name="Property" />
                <set-property propertyName="delivery"
                    value="#[message.outboundProperties['delivery'] + 1]" doc:name="Property" />
                <jms:outbound-endpoint queue="IN"
                    connector-ref="Active_MQ" doc:name="JMS">
                    <jms:transaction action="ALWAYS_JOIN" />
                </jms:outbound-endpoint>

            </catch-exception-strategy>

            <rollback-exception-strategy doc:name="Rollback Exception Strategy">
                <logger level="ERROR" message="Giving up retry. Do whatever needed here." doc:name="Logger" />
            </rollback-exception-strategy>
        </choice-exception-strategy>
    </flow>
</mule>

This is no way to make the RedeliveryPolicy persistent - it's controlled by the connection factory and the factory will get reset when you restart the server. 这无法使RedeliveryPolicy持久化-它由连接工厂控制,并且当您重新启动服务器时工厂将被重置。 The way you have it configured, it will carry on with the behaviour you see, as you have useExponentialBackOff set to true. 您将其配置的方式将继续使用您看到的行为,因为useExponentialBackOff设置为true。 You could set this to false to get the delay to be a regular amount, but that is the only change to make. 您可以将此值设置为false,以使延迟时间变为常规值,但这是唯一要做的更改。

I think you have the right idea with setting the message TTL, at least this will remove the message after the specified time. 我认为您对设置消息TTL有正确的想法,至少这将在指定时间后删除消息。 The JMSXDeliveryCount is great, but it will remove after a number attempts, not a defined time period, if you increase the delay between the retries. JMSXDeliveryCount很好,但是如果您增加重试之间的延迟,它将在尝试几次而不是定义的时间段后删除。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM