From 3ea416bd8444cf665d0ba14598d941e55bc9703b Mon Sep 17 00:00:00 2001 From: Artem Bilan Date: Mon, 18 Jun 2012 23:14:17 +0300 Subject: [PATCH] INT-2623: document Delayer's changes JIRA: https://jira.springsource.org/browse/INT-2623 --- src/reference/docbook/delayer.xml | 89 ++++++++++++++++++++++++------- 1 file changed, 70 insertions(+), 19 deletions(-) diff --git a/src/reference/docbook/delayer.xml b/src/reference/docbook/delayer.xml index 0ed14b283f..9d341a7ba5 100644 --- a/src/reference/docbook/delayer.xml +++ b/src/reference/docbook/delayer.xml @@ -19,43 +19,94 @@
Configuring Delayer - The <delayer> element is used to delay the Message flow between two Message Channels. - As with the other endpoints, you can provide the "input-channel" and "output-channel" attributes, - but the delayer also requires at least the 'default-delay' attribute with the number of milliseconds - that each Message should be delayed. - ]]> + The <delayer> element is used to delay the Message flow between two Message Channels. + As with the other endpoints, you can provide the 'input-channel' and 'output-channel' attributes, + but the delayer also has 'default-delay' and 'delay-header-name' attributes that are used to + determine the number of milliseconds + that each Message should be delayed. The following delays all messages by 3 seconds: + ]]> If you need per-Message determination of the delay, then you can also provide the name of a header - within the 'delay-header-name' attribute: - ]]> In the example above the 3 second delay would only apply in the case that the header value is not present for a given inbound Message. If you only want to apply a delay to Messages that have - an explicit header value, then you can set the 'default-delay' to 0. For any Message that has a - delay of 0 (or less), the Message will be sent directly. In fact, if there is not a positive delay + an explicit header value, then you can set the 'default-delay' to 0 or don't use it at all (by default it is 0). + For any Message that has a delay of 0 (or less), the Message will be sent directly. In fact, if there is not a positive delay value for a Message, it will be sent to the output channel on the calling Thread. - The delay handler actually supports header values that represent an interval in milliseconds (any + The delay handler supports header values that represent an interval in milliseconds (any Object whose toString() method produces a value that can be parsed into a Long) as well as java.util.Date instances representing an absolute time. - In the former case, the milliseconds will be counted from the current time (e.g. a value of 5000 - would delay the Message for at least 5 seconds from the time it is received by the Delayer). In - the latter case, with an actual Date instance, the Message will not be released until that Date + In the first case, the milliseconds will be counted from the current time (e.g. a value of 5000 + would delay the Message for at least 5 seconds from the time it is received by the Delayer). + With a Date instance, the Message will not be released until that Date occurs. In either case, a value that equates to a non-positive delay, or a Date in the past, will - not result in any delay. Instead, it will be sent directly to the output channel in the original - sender's Thread. + not result in any delay. Instead, it will be sent directly to the output channel on the original + sender's Thread. If the header is not a Date, and can not be parsed as a Long, the default + delay (if any) will be applied. The delayer delegates to an instance of Spring's TaskScheduler abstraction. - The default scheduler used by the delayer is a ThreadPoolTaskScheduler instance with a pool size of 1. + The default scheduler used by the delayer is the ThreadPoolTaskScheduler instance + provided by Spring Integration on startup: . If you want to delegate to a different scheduler, you can provide a reference through the delayer element's 'scheduler' attribute: - - ]]> + ]]> + + If you configure an external ThreadPoolTaskScheduler + you can set on this scheduler property waitForTasksToCompleteOnShutdown = true. + It allows successful completion of 'delay' tasks, which already in the execution state (releasing the Message), + when the application is shutdown. Before Spring Integration 2.2 this property was available on + the <delayer> element, because DelayHandler could create its own + scheduler on the background. Since 2.2 delayer requires an external scheduler + instance and waitForTasksToCompleteOnShutdown was deleted; you should use the scheduler's own configuration. + + + Also keep in mind ThreadPoolTaskScheduler has a property errorHandler which + can be injected with some implementation of org.springframework.util.ErrorHandler. + This handler allows to process an Exception from the thread of the scheduled task sending + the delayed message. + By default it uses an org.springframework.scheduling.support.TaskUtils$LoggingErrorHandler + and you will see a stack trace in the logs. You might want to consider using an + org.springframework.integration.channel.MessagePublishingErrorHandler, + which sends an ErrorMessage into an error-channel, either from the failed Message's header or + into the default error-channel. +
+
+ Delayer and Message Store + + The DelayHandler persists delayed Messages into the Message Group in the provided + MessageStore. (The 'groupId' is based on required 'id' attribute of <delayer> element.) + A delayed message is removed from the MessageStore by the scheduled task just before + the DelayHandler sends the Message to the output-channel. If the provided + MessageStore is persistent (e.g. JdbcMessageStore) it provides + the ability to not lose Messages on the application shutdown. After application startup, the + DelayHandler reads Messages from its Message Group in the MessageStore + and reschedules them with a delay based on the original arrival time of the Message (if the delay is numeric). For messages + where the delay header was a Date, that is used when rescheduling. + If a delayed Message remained in the MessageStore more + than its 'delay', it will be sent immediately after startup. + + + The DelayHandler can be exported as a JMX MBean + with managed operations getDelayedMessageCount and reschedulePersistedMessages, + which allows the rescheduling of delayed persisted Messages at runtime, for example, if the + TaskScheduler has previously been stopped. These operations can be invoked via a Control Bus command: + delayerReschedulingMessage = MessageBuilder.withPayload("@'delayer.handler'.reschedulePersistedMessages()").build(); + controlBusChannel.send(delayerReschedulingMessage);]]> + + + For more information regarding the Message Store, JMX and the Control Bus, please read . + +