Number result = (Number) msgGateway.sendAndReceive(new Operands(22, 4));
System.out.println("Result: " + result.floatValue());
The interface is very straightforward. The SimpleMessagingGateway needs a request and a response
channel, and it coordinates the rest. In this case, you're doing nothing but forwarding the request to a
service-activator , which in turn adds the operands and sends them out on the reply channel. The
configuration XML is sparse because most of the work is done in those five lines of Java code.
<?xml version="1.0" encoding="UTF-8"?>
<beans:beans … >
<beans:bean id="additionService " class="com.apress.springenterpriserecipes.
<channel id="request" />
<channel id="response" />
Breaking the Interface Dependency
The previous example demonstrates what's happening behind the scenes. You're dealing only with
Spring Integration interfaces and are isolated from the nuances of the endpoints. However, there are still
plenty of inferred constraints that a client might easily fail to comply with. The simplest solution is to
hide the messaging behind an interface. Let's look at building a fictional hotel reservation search engine.
Searching for a hotel might take a long time, and ideally processing should be offloaded to a separate
server. An ideal solution is JMS because you could implement the aggressive consumer pattern and scale
simply by adding more consumers. The client would still block waiting for the result, in this example, but
the server(s) would not be overloaded or in a blocking state.
You'll build two Spring Integration solutions. One for the client (which will in turn contain the
gateway) and one for the service itself, which, presumably, is on a separate host connected to the client
only by way of well-known message queues.
Let's look at the client configuration first. The first thing that the client configuration does is import
a shared application context (to save typing if nothing else) that declares a JMS connection factory that
you reference in the client and service application contexts. (I won't repeat all of that here because it's
not relevant or noteworthy.)
Then you declare two channels, imaginatively named requests and responses . Messages sent on the
requests channel are forwarded to the jms:outbound-gateway that you've declared. The jms:outbound
gateway is the component that does most of the work. It takes the message you created and sends it to
the request JMS destination, setting up the reply headers and so on. Finally you declare a generic
gateway element , which does most of the magic. The gateway element simply exists to identify the
component and the interface, to which the proxy is cast and made available to clients.