handoff

Source processor that receives messages handed over from other flows.

Handoffs enable flows to add a new tier of persistent message processing and can be useful in situations where you have a flow that distributes a stream of messages to two sub flows, where one flow is fast and the other is slow. Without a handoff, the throughput of the fast flow can not exceed the throughput of the slow flow. The buffering and stashing caused by the slow flow would also limit the fast flow. By handing off the processing of messages on the slow flow to a separate OneWay flow, the bottleneck for the fast flow can be eliminated.

It is also possible to use the RequestResponse exchange pattern for handoff flows, but this should only be done in very special cases since it adds the following complexity:

  • The handoff flow will get two tiers of resilience: redelivery and dead letter handling.

  • Errors will be propagated from the handoff flow to the upstream flow.

  • Dead letter flows will be executed from both flows.

  • The total processing time of the upstream flow is affected by the processing time of the handoff. This means that the processing time of the handoff flow must be taken into consideration when configuring the redelivery timeout of the upstream flow.

  • Redelivery semantics become more complex in the following ways:

    • If the propagateErrorTransience processor property is true, the handoff flow will report a transient failure back to the upstream flow after running out of redeliveries. This will then trigger redeliveries from the upstream flow, making the possible number of redeliveries to the handoff flow "upstream-redeliveries * handoff-redeliveries".

    • If the propagateErrorTransience processor property is false (the default), the handoff flow will report a non-transient failure back to the upstream flow after running out of redeliveries. This will cause the upstream flow to stop redeliveries and fail with the non-transient error.

Messages can be handed off by processors that support distribution of messages (such as distribute and split). Note that this requires the handoff flow’s ID to include the suffix -handoff to signify to the upstream processor that a handoff is taking place.

Properties

Name Summary

propagateErrorTransience

Determines whether to mark errors as transient when they are propagated back to the upstream flow. This only applies to the rare case where a handoff flow uses the RequestResponse exchange pattern. Note that only transient errors will trigger message redeliveries.

name

Optional, descriptive name for the processor.

id

Required identifier of the processor, unique across all processors within the flow. Must be between 3 and 30 characters long; contain only lower and uppercase alphabetical characters (a-z and A-Z), numbers, dashes ("-"), and underscores ("_"); and start with an alphabetical character. In other words, it adheres to the regex pattern [a-zA-Z][a-zA-Z0-9_-]{2,29}.

exchangeProperties

Optional set of custom properties in a simple jdk-format, that are added to the message exchange properties before processing the incoming payload. Any existing properties with the same name will be replaced by properties defined here.

retainPayloadOnFailure

Whether the incoming payload is available for error processing on failure. Defaults to false.

Sub-builders

Name Summary

messageLoggingStrategy

Strategy for describing how a processor’s message is logged on the server.

payloadArchivingStrategy

Strategy for archiving payloads.

inboundTransformationStrategy

Strategy that customizes the conversion of an incoming payload by a processor (e.g., string to object). Should be used when the processor’s default conversion logic cannot be used.

Details

Usage

Both the distribute and split processors support handoffs to flows when the flow ID contains the suffix -handoff. This naming pattern is what signals to the main flow that a handoff is taking place. The handoff flow would then be configured in a manner similar to the following:

flowConfig {
    id = "message-handoff"
    description = "Message Handoff Flow"
    ownerId = "my-company"
    exchangePattern = FlowExchangePattern.OneWay

    handoff {
        id = "handoff-source"
    }

    test {
        id = "log-handoff"
        messageLoggingStrategy {
            logDescription = true
            logFullMessage = true
        }
    }
}

In the main flow, the initiating processor then references the same -handoff flow ID. For example:

distribute {
    id = "distribute-message"
    flowId("message-handoff")
}