Recipient List Enterprise Integration Design Pattern using Azure Service Bus
Summary
The Recipient List Enterprise Integration Pattern is a very good architecture when multiple Receivers may act on a message. The Recipient List EIP doesn’t concern itself with understanding anything further than sending the message off from a Source System to a Message Channel.
In a Message Queue system, the order of messages is transacted in a FIFO sequence. Messages are often consumed by a single service; at this point, the message is removed from the Queue to prevent other Receivers from consuming the message. The Recipient List EIP differs in that a single message is delivered in a channel at which point Subscribers are free to consume any messages they have ‘subscribed’ to.
This EIP has many use cases; e.g. in a REST architecture where a state might be transferred to one or more systems, the target systems are then left to do whatever they want with a message.
Recipient List Integration pattern
This Integration Pattern routes a message from a Sender to a Receiver without using any middleware in a point-to-point message channel. The Sender can either use the AMQP protocol to define the ‘Recipient‘ in the message header or route to a Message Broker that will reroute to a target system. The Recipient List Integration Design pattern is similar to the Content-Based Routing, in that the contents of the messages define the destination. This EIP is also similar to the Dynamic Routing EIP, in that a route to a target endpoint can be defined at the Message Channel.
{
"MessageId": "001291922",
"CorrelationId": "903238-int-019",
"ContentType": "application/json",
"Subject": "Order id:100",
"ReplyTo": "orderapp-100",
"To": "InventoryControl",
"Body": "{message}")
}
This EIP can be used to solve various problems, the most common of all is routing messages to a destination in an event-driven architecture.
In a Recipient List EIP, there can be a single Receiver or multiple Receivers.
Conceptual Architecture
Recipient List is similar to Content-Based Routing or Dynamic Routing; messages can be routed based on message content or routing parameters.
The Recipient List EIP, like all other EIP architectures, will contain the following:
- Sender
- Message Construction
- Sender Endpoint
- Message Channel
- Message Router
- Message Transformation
- Receiver or Receiver Endpoints
- Systems Management
In a conceptual architecture, this will look like the following:
- A Sender will construct a message containing the Recipient (TO field correlation property in Azure Service Bus Topics)
- The Sender endpoint will submit the message to the Message Channel (Azure Service Bus Topics).
- The Message Channel being Azure Service Bus will contain Subscriptions to the Topics.
- Messages will be Routed based on Subscription Filters.
- Receiver Endpoint will Subscribe to the Topics based on Filters.
- Any transformations will be carried out by the Receiver Endpoints.
Azure Service Bus Topics
Creating a Recipient List EIP can be done in three steps:
- Create an Azure Topic
- Create a Subscription
- Create Filters
Azure Service Bus Topics provides an easy mechanism to implement Recipient List EIP. Topics are created with Subscriptions that contain filters. These filters can be either SQL syntax or based on the Message Correlation.
Creating Azure Service Bus Topics are created similarly to Queues. I’ve enabled some settings here that assist in managing messages on a Topic.
Azure Service Bus Topic Subscription
A Topic can have multiple Subscriptions. A Subscription has some basic properties:
Create a Subscription Filter
Once a Subscription has been created, a filter needs to be created so that Receivers can Subscribe to the topic.
Message Construction
The Sender is responsible for defining the message route or target system. The key here is to use the message correlation filter to set the destination.
ServiceBusMessage message = new ServiceBusMessage()
{
MessageId = Guid.NewGuid().ToString(),
CorrelationId = $"OrderApp-{Guid.NewGuid()}",
ContentType = "application/json",
Subject = $"Order id: {i}",
ReplyTo = "orderapp-100",
To = "InventoryControl",
Body = BinaryData.FromString($"{m.MessageTransformation()}")
};
The correlation filter used in this message construction is the TO field property.
To = "InventoryControl",
This property will ensure all messages are routed to this specific Topic Subscription.
Message Channel
Once a message has been sent to the Azure Service Bus Topic, the messages should be displayed in the topic. Running the sample code should show a list of messages in the Topic.
Recipient Subscribers
Receivers that have subscribed to the Topic Subscription pickup the messages as they would in a Queue. The Consumption of messages does not differ for a Consumer or a Receiver.
Sending Messages without Recipients
If the Sender doesn’t define a Receiver in the Azure Service Bus message, then the Topic Subscription simply doesn’t store any messages.
Source Code:
The source code for the Recipient List can be found here: https://github.com/sy-huss/EIP-RecipientList