From 9376403f0268ff08fe185853f17d8ccdb9f0e91a Mon Sep 17 00:00:00 2001 From: Arjen Poutsma Date: Tue, 18 Dec 2007 19:09:47 +0000 Subject: [PATCH] SWS-255 --- .../ws/transport/jms/JmsMessageReceiver.java | 27 +++++- .../ws/transport/jms/JmsMessageSender.java | 40 +++++--- .../transport/jms/JmsReceiverConnection.java | 95 ++++++++++++++++--- .../ws/transport/jms/JmsSenderConnection.java | 81 +++++++++++++--- .../transport/jms/JmsTransportConstants.java | 14 ++- .../jms/support/JmsTransportUtils.java | 20 ++++ .../jms/JmsMessageSenderIntegrationTest.java | 45 ++++++++- ...ServiceMessageListenerIntegrationTest.java | 15 ++- .../jms/support/JmsTransportUtilsTest.java | 16 ++++ 9 files changed, 302 insertions(+), 51 deletions(-) diff --git a/support/src/main/java/org/springframework/ws/transport/jms/JmsMessageReceiver.java b/support/src/main/java/org/springframework/ws/transport/jms/JmsMessageReceiver.java index 7f1e93fd..0519e057 100644 --- a/support/src/main/java/org/springframework/ws/transport/jms/JmsMessageReceiver.java +++ b/support/src/main/java/org/springframework/ws/transport/jms/JmsMessageReceiver.java @@ -19,6 +19,7 @@ package org.springframework.ws.transport.jms; import javax.jms.BytesMessage; import javax.jms.Message; import javax.jms.Session; +import javax.jms.TextMessage; import org.springframework.ws.transport.WebServiceConnection; import org.springframework.ws.transport.WebServiceMessageReceiver; @@ -26,7 +27,9 @@ import org.springframework.ws.transport.support.SimpleWebServiceMessageReceiverO /** * Convenience base class for JMS server-side transport objects. Contains a {@link WebServiceMessageReceiver}, and has - * methods for handling incoming JMS {@link Message} requests. + * methods for handling incoming JMS {@link BytesMessage} and {@link TextMessage} requests. Also contains a + * textMessageEncoding property, which determines the encoding used to read from and write to + * TextMessages. This property defaults to UTF-8. *

* Used by {@link WebServiceMessageListener} and {@link WebServiceMessageDrivenBean}. * @@ -35,6 +38,16 @@ import org.springframework.ws.transport.support.SimpleWebServiceMessageReceiverO */ public class JmsMessageReceiver extends SimpleWebServiceMessageReceiverObjectSupport { + /** Default encoding used to read fromn and write to {@link TextMessage} messages. */ + public static final String DEFAULT_TEXT_MESSAGE_ENCODING = "UTF-8"; + + private String textMessageEncoding = DEFAULT_TEXT_MESSAGE_ENCODING; + + /** Sets the encoding used to read from and write to {@link TextMessage} messages. Defaults to UTF-8. */ + public void setTextMessageEncoding(String textMessageEncoding) { + this.textMessageEncoding = textMessageEncoding; + } + /** * Handles an incoming message. Uses the given session to create a response message. * @@ -43,13 +56,17 @@ public class JmsMessageReceiver extends SimpleWebServiceMessageReceiverObjectSup * @throws IllegalArgumentException when request is not a {@link BytesMessage} */ protected final void handleMessage(Message request, Session session) throws Exception { + WebServiceConnection connection; if (request instanceof BytesMessage) { - WebServiceConnection connection = new JmsReceiverConnection((BytesMessage) request, session); - handleConnection(connection); + connection = new JmsReceiverConnection((BytesMessage) request, session); + } + else if (request instanceof TextMessage) { + connection = new JmsReceiverConnection((TextMessage) request, textMessageEncoding, session); } else { - throw new IllegalArgumentException( - "Wrong message type: [" + request.getClass() + "]. Only BytesMessages can be handled."); + throw new IllegalArgumentException("Wrong message type: [" + request.getClass() + + "]. Only BytesMessages or TextMessages can be handled."); } + handleConnection(connection); } } diff --git a/support/src/main/java/org/springframework/ws/transport/jms/JmsMessageSender.java b/support/src/main/java/org/springframework/ws/transport/jms/JmsMessageSender.java index c0e31809..0f0d8974 100644 --- a/support/src/main/java/org/springframework/ws/transport/jms/JmsMessageSender.java +++ b/support/src/main/java/org/springframework/ws/transport/jms/JmsMessageSender.java @@ -23,10 +23,12 @@ import javax.jms.Connection; import javax.jms.ConnectionFactory; import javax.jms.Destination; import javax.jms.JMSException; +import javax.jms.Message; import javax.jms.MessageConsumer; import javax.jms.MessageProducer; import javax.jms.Queue; import javax.jms.Session; +import javax.jms.TextMessage; import javax.jms.Topic; import org.springframework.jms.connection.ConnectionFactoryUtils; @@ -38,7 +40,7 @@ import org.springframework.ws.transport.WebServiceMessageSender; import org.springframework.ws.transport.jms.support.JmsTransportUtils; /** - * {@link WebServiceMessageSender} implementation that uses JMS {@link BytesMessage}s. Requires a JMS {@link + * {@link WebServiceMessageSender} implementation that uses JMS {@link Message}s. Requires a JMS {@link * ConnectionFactory} to operate. *

* This message sender supports URI's of the following format:

jms:destination[?param-name=param-value][&param-name=param-value]* @@ -49,18 +51,23 @@ import org.springframework.ws.transport.jms.support.JmsTransportUtils; *
* - * - *
param-nameDescription
deliveryModeIndicates whether the request message is persistent or not. This may be * PERSISTENT or NON_PERSISTENT. See {@link MessageProducer#setDeliveryMode(int)}
timeToLiveThe lifetime, in milliseconds, of the request message. See {@link - * MessageProducer#setTimeToLive(long)}
priorityThe JMS priority (0-9) associated - * with the request message. See {@link MessageProducer#setPriority(int)}
replyToNameThe name of the destination to which the response message must be sent, that - * will be resolved by the {@link #getDestinationResolver() destination resolver}.
+ * messageTypeThe message type. This may be BINARY_MESSAGE (the default) or + * TEXT_MESSAGE priorityThe JMS priority (0-9) associated with the request + * message. See {@link MessageProducer#setPriority(int)} replyToNameThe name of the + * destination to which the response message must be sent, that will be resolved by the {@link #getDestinationResolver() + * destination resolver}. timeToLiveThe lifetime, in milliseconds, of the request + * message. See {@link MessageProducer#setTimeToLive(long)}
*

* If the replyToName is not set, a {@link Session#createTemporaryQueue() temporary queue} is used. *

+ * This class uses {@link BytesMessage} messages by default, but can be configured to send {@link TextMessage} messages + * instead. Note that BytesMessages are prefered, since TextMessages do not support + * attachments and charactering encodings reliably. + *

* Some examples of JMS URIs are: *

*

jms:SomeQueue
jms:SomeTopic?priority=3&deliveryMode=NON_PERSISTENT
- * jms:RequestQueue?replyToName=ResponseQueueName
+ * jms:RequestQueue?replyToName=ResponseQueueName
jms:Queue?messageType=TEXT_MESSAGE * * @author Arjen Poutsma * @see IRI Scheme for Java(tm) Message @@ -69,18 +76,27 @@ import org.springframework.ws.transport.jms.support.JmsTransportUtils; */ public class JmsMessageSender extends JmsDestinationAccessor implements WebServiceMessageSender { - /** - * Default timeout for receive operations: -1 indicates a blocking receive without timeout. - */ + /** Default timeout for receive operations: -1 indicates a blocking receive without timeout. */ public static final long DEFAULT_RECEIVE_TIMEOUT = -1; + /** Default encoding used to read fromn and write to {@link TextMessage} messages. */ + public static final String DEFAULT_TEXT_MESSAGE_ENCODING = "UTF-8"; + private long receiveTimeout = DEFAULT_RECEIVE_TIMEOUT; + private String textMessageEncoding = DEFAULT_TEXT_MESSAGE_ENCODING; + + /** Sets the encoding used to read from {@link TextMessage} messages. Defaults to UTF-8. */ + public void setTextMessageEncoding(String textMessageEncoding) { + this.textMessageEncoding = textMessageEncoding; + } + /** * Create a new JmsMessageSender *

* Note: The ConnectionFactory has to be set before using the instance. This constructor can be used to - * prepare a JmsTemplate via a BeanFactory, typically setting the ConnectionFactory via setConnectionFactory. + * prepare a JmsTemplate via a BeanFactory, typically setting the ConnectionFactory via {@link + * #setConnectionFactory(ConnectionFactory)}. * * @see #setConnectionFactory(ConnectionFactory) */ @@ -119,6 +135,8 @@ public class JmsMessageSender extends JmsDestinationAccessor implements WebServi wsConnection.setReceiveTimeout(receiveTimeout); wsConnection.setResponseDestination(resolveResponseDestination(jmsSession, uri)); wsConnection.setTimeToLive(JmsTransportUtils.getTimeToLive(uri)); + wsConnection.setMessageType(JmsTransportUtils.getMessageType(uri)); + wsConnection.setTextMessageEncoding(textMessageEncoding); return wsConnection; } catch (JMSException ex) { diff --git a/support/src/main/java/org/springframework/ws/transport/jms/JmsReceiverConnection.java b/support/src/main/java/org/springframework/ws/transport/jms/JmsReceiverConnection.java index 185a39f9..9e51e7f3 100644 --- a/support/src/main/java/org/springframework/ws/transport/jms/JmsReceiverConnection.java +++ b/support/src/main/java/org/springframework/ws/transport/jms/JmsReceiverConnection.java @@ -16,6 +16,8 @@ package org.springframework.ws.transport.jms; +import java.io.ByteArrayInputStream; +import java.io.ByteArrayOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; @@ -23,8 +25,10 @@ import java.util.Collections; import java.util.Iterator; import javax.jms.BytesMessage; import javax.jms.JMSException; +import javax.jms.Message; import javax.jms.MessageProducer; import javax.jms.Session; +import javax.jms.TextMessage; import org.springframework.jms.support.JmsUtils; import org.springframework.util.Assert; @@ -35,37 +39,70 @@ import org.springframework.ws.transport.support.EnumerationIterator; /** * Implementation of {@link WebServiceConnection} that is used for server-side JMS access. Exposes a {@link - * BytesMessage} request and response message. + * BytesMessage} or {@link TextMessage} request and response message. + *

+ * The response message type is equal to the request message type, i.e. if a BytesMessage is received as + * request, a BytesMessage is created as response, and if a TextMessage is received, a + * TextMessage response is created. * * @author Arjen Poutsma * @since 1.5.0 */ public class JmsReceiverConnection extends AbstractReceiverConnection { - private final BytesMessage requestMessage; + private final Message requestMessage; private final Session session; - private BytesMessage responseMessage; + private Message responseMessage; - /** Constructs a new JMS connection with the given parameters. */ - protected JmsReceiverConnection(BytesMessage requestMessage, Session session) { + private String textMessageEncoding; + + private JmsReceiverConnection(Message requestMessage, Session session) { Assert.notNull(requestMessage, "requestMessage must not be null"); Assert.notNull(session, "session must not be null"); this.requestMessage = requestMessage; this.session = session; } - /** Returns the request message for this connection. */ - public BytesMessage getRequestMessage() { + /** + * Constructs a new JMS connection with the given {@link BytesMessage}. + * + * @param requestMessage the JMS request message + * @param session the JMS session + */ + protected JmsReceiverConnection(BytesMessage requestMessage, Session session) { + this((Message) requestMessage, session); + } + + /** + * Constructs a new JMS connection with the given {@link TextMessage}. + * + * @param requestMessage the JMS request message + * @param session the JMS session + */ + protected JmsReceiverConnection(TextMessage requestMessage, String encoding, Session session) { + this(requestMessage, session); + this.textMessageEncoding = encoding; + } + + /** Returns the request message for this connection. Returns either a {@link BytesMessage} or a {@link TextMessage}. */ + public Message getRequestMessage() { return requestMessage; } - /** Returns the response message, if any, for this connection. */ - public BytesMessage getResponseMessage() { + /** + * Returns the response message, if any, for this connection. Returns either a {@link BytesMessage} or a {@link + * TextMessage}. + */ + public Message getResponseMessage() { return responseMessage; } + /* + * Errors + */ + public String getErrorMessage() throws IOException { return null; } @@ -98,7 +135,20 @@ public class JmsReceiverConnection extends AbstractReceiverConnection { } protected InputStream getRequestInputStream() throws IOException { - return new BytesMessageInputStream(requestMessage); + if (requestMessage instanceof BytesMessage) { + return new BytesMessageInputStream((BytesMessage) requestMessage); + } + else { + TextMessage textMessage = (TextMessage) requestMessage; + try { + String text = textMessage.getText(); + byte[] contents = text != null ? text.getBytes(textMessageEncoding) : new byte[0]; + return new ByteArrayInputStream(contents); + } + catch (JMSException ex) { + throw new JmsTransportException(ex); + } + } } /* @@ -107,7 +157,12 @@ public class JmsReceiverConnection extends AbstractReceiverConnection { protected void onSendBeforeWrite(WebServiceMessage message) throws IOException { try { - responseMessage = session.createBytesMessage(); + if (requestMessage instanceof BytesMessage) { + responseMessage = session.createBytesMessage(); + } + else { + responseMessage = session.createTextMessage(); + } responseMessage.setJMSCorrelationID(requestMessage.getJMSMessageID()); } catch (JMSException ex) { @@ -125,7 +180,23 @@ public class JmsReceiverConnection extends AbstractReceiverConnection { } protected OutputStream getResponseOutputStream() throws IOException { - return new BytesMessageOutputStream(responseMessage); + if (responseMessage instanceof BytesMessage) { + return new BytesMessageOutputStream((BytesMessage) responseMessage); + } + else { + return new ByteArrayOutputStream() { + + public void close() throws IOException { + String text = new String(toByteArray(), textMessageEncoding); + try { + ((TextMessage) responseMessage).setText(text); + } + catch (JMSException ex) { + throw new JmsTransportException(ex); + } + } + }; + } } protected void onSendAfterWrite(WebServiceMessage message) throws IOException { diff --git a/support/src/main/java/org/springframework/ws/transport/jms/JmsSenderConnection.java b/support/src/main/java/org/springframework/ws/transport/jms/JmsSenderConnection.java index 6c0a0f61..97da2044 100644 --- a/support/src/main/java/org/springframework/ws/transport/jms/JmsSenderConnection.java +++ b/support/src/main/java/org/springframework/ws/transport/jms/JmsSenderConnection.java @@ -16,6 +16,8 @@ package org.springframework.ws.transport.jms; +import java.io.ByteArrayInputStream; +import java.io.ByteArrayOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; @@ -31,6 +33,7 @@ import javax.jms.MessageConsumer; import javax.jms.MessageProducer; import javax.jms.Session; import javax.jms.TemporaryQueue; +import javax.jms.TextMessage; import org.springframework.jms.connection.ConnectionFactoryUtils; import org.springframework.jms.support.JmsUtils; @@ -59,9 +62,9 @@ public class JmsSenderConnection extends AbstractSenderConnection implements Web private Destination responseDestination; - private BytesMessage requestMessage; + private Message requestMessage; - private BytesMessage responseMessage; + private Message responseMessage; private long receiveTimeout; @@ -71,6 +74,10 @@ public class JmsSenderConnection extends AbstractSenderConnection implements Web private int priority; + private String textMessageEncoding; + + private int messageType; + /** Constructs a new JMS connection with the given parameters. */ protected JmsSenderConnection(ConnectionFactory connectionFactory, Connection connection, @@ -85,19 +92,22 @@ public class JmsSenderConnection extends AbstractSenderConnection implements Web this.requestDestination = requestDestination; } - /** Returns the request message for this connection. */ - public BytesMessage getRequestMessage() { + /** Returns the request message for this connection. Returns either a {@link BytesMessage} or a {@link TextMessage}. */ + public Message getRequestMessage() { return requestMessage; } - /** Returns the response message, if any, for this connection. */ - public BytesMessage getResponseMessage() { + /** + * Returns the response message, if any, for this connection. Returns either a {@link BytesMessage} or a {@link + * TextMessage}. + */ + public Message getResponseMessage() { return responseMessage; } /* - * Package-friendly setters - */ + * Package-friendly setters + */ void setResponseDestination(Destination responseDestination) { this.responseDestination = responseDestination; @@ -119,6 +129,14 @@ public class JmsSenderConnection extends AbstractSenderConnection implements Web this.receiveTimeout = receiveTimeout; } + void setTextMessageEncoding(String textMessageEncoding) { + this.textMessageEncoding = textMessageEncoding; + } + + void setMessageType(int messageType) { + this.messageType = messageType; + } + /* * Errors */ @@ -137,7 +155,12 @@ public class JmsSenderConnection extends AbstractSenderConnection implements Web protected void onSendBeforeWrite(WebServiceMessage message) throws IOException { try { - requestMessage = session.createBytesMessage(); + if (messageType == JmsTransportConstants.BYTES_MESSAGE_TYPE) { + requestMessage = session.createBytesMessage(); + } + else { + requestMessage = session.createTextMessage(); + } } catch (JMSException ex) { throw new JmsTransportException(ex); @@ -154,7 +177,23 @@ public class JmsSenderConnection extends AbstractSenderConnection implements Web } protected OutputStream getRequestOutputStream() throws IOException { - return new BytesMessageOutputStream(requestMessage); + if (requestMessage instanceof BytesMessage) { + return new BytesMessageOutputStream((BytesMessage) requestMessage); + } + else { + return new ByteArrayOutputStream() { + + public void close() throws IOException { + String text = new String(toByteArray(), textMessageEncoding); + try { + ((TextMessage) requestMessage).setText(text); + } + catch (JMSException ex) { + throw new JmsTransportException(ex); + } + } + }; + } } protected void onSendAfterWrite(WebServiceMessage message) throws IOException { @@ -188,11 +227,13 @@ public class JmsSenderConnection extends AbstractSenderConnection implements Web try { messageConsumer = session.createConsumer(responseDestination); Message message = receiveTimeout >= 0 ? messageConsumer.receive(receiveTimeout) : messageConsumer.receive(); - if (!(message instanceof BytesMessage)) { + if (message instanceof BytesMessage || message instanceof TextMessage) { + responseMessage = message; + } + else { throw new IllegalArgumentException( "Wrong message type: [" + message.getClass() + "]. Only BytesMessages can be handled."); } - responseMessage = (BytesMessage) message; } catch (JMSException ex) { throw new JmsTransportException(ex); @@ -239,7 +280,20 @@ public class JmsSenderConnection extends AbstractSenderConnection implements Web } protected InputStream getResponseInputStream() throws IOException { - return new BytesMessageInputStream(responseMessage); + if (responseMessage instanceof BytesMessage) { + return new BytesMessageInputStream((BytesMessage) responseMessage); + } + else { + TextMessage textMessage = (TextMessage) responseMessage; + try { + String text = textMessage.getText(); + byte[] contents = text != null ? text.getBytes(textMessageEncoding) : new byte[0]; + return new ByteArrayInputStream(contents); + } + catch (JMSException ex) { + throw new JmsTransportException(ex); + } + } } protected void onClose() throws IOException { @@ -247,5 +301,4 @@ public class JmsSenderConnection extends AbstractSenderConnection implements Web ConnectionFactoryUtils.releaseConnection(connection, connectionFactory, true); } - } diff --git a/support/src/main/java/org/springframework/ws/transport/jms/JmsTransportConstants.java b/support/src/main/java/org/springframework/ws/transport/jms/JmsTransportConstants.java index 29fb5375..500b40a4 100644 --- a/support/src/main/java/org/springframework/ws/transport/jms/JmsTransportConstants.java +++ b/support/src/main/java/org/springframework/ws/transport/jms/JmsTransportConstants.java @@ -16,6 +16,9 @@ package org.springframework.ws.transport.jms; +import javax.jms.BytesMessage; +import javax.jms.TextMessage; + import org.springframework.ws.transport.TransportConstants; /** @@ -26,9 +29,14 @@ import org.springframework.ws.transport.TransportConstants; */ public interface JmsTransportConstants extends TransportConstants { - /** - * The "jms" URI scheme" - */ + /** The "jms" URI scheme" */ String JMS_URI_SCHEME = "jms"; + /** Indicates a {@link BytesMessage} type. */ + int BYTES_MESSAGE_TYPE = 1; + + /** Indicates a {@link TextMessage} type. */ + int TEXT_MESSAGE_TYPE = 2; + + } diff --git a/support/src/main/java/org/springframework/ws/transport/jms/support/JmsTransportUtils.java b/support/src/main/java/org/springframework/ws/transport/jms/support/JmsTransportUtils.java index ca63748f..148b486e 100644 --- a/support/src/main/java/org/springframework/ws/transport/jms/support/JmsTransportUtils.java +++ b/support/src/main/java/org/springframework/ws/transport/jms/support/JmsTransportUtils.java @@ -23,6 +23,8 @@ import javax.jms.DeliveryMode; import javax.jms.Destination; import javax.jms.Message; +import org.springframework.ws.transport.jms.JmsTransportConstants; + /** * Collection of utility methods to work with JMS transports. Includes methods to retrieve JMS properties from an {@link * URI}. @@ -36,6 +38,8 @@ public class JmsTransportUtils { private static final Pattern DELIVERY_MODE_PATTERN = Pattern.compile("deliveryMode=(PERSISTENT|NON_PERSISTENT)"); + private static final Pattern MESSAGE_TYPE_PATTERN = Pattern.compile("messageType=(BYTES_MESSAGE|TEXT_MESSAGE)"); + private static final Pattern TIME_TO_LIVE_PATTERN = Pattern.compile("timeToLive=(\\d+)"); private static final Pattern PRIORITY_PATTERN = Pattern.compile("priority=(\\d)"); @@ -69,6 +73,22 @@ public class JmsTransportUtils { } } + /** + * Returns the message type of the given URI. Defaults to {@link JmsTransportConstants#BYTES_MESSAGE_TYPE}. + * + * @see JmsTransportConstants#BYTES_MESSAGE_TYPE + * @see JmsTransportConstants#TEXT_MESSAGE_TYPE + */ + public static int getMessageType(URI uri) { + String deliveryMode = getStringParameter(MESSAGE_TYPE_PATTERN, uri); + if ("TEXT_MESSAGE".equals(deliveryMode)) { + return JmsTransportConstants.TEXT_MESSAGE_TYPE; + } + else { + return JmsTransportConstants.BYTES_MESSAGE_TYPE; + } + } + /** * Returns the lifetime, in milliseconds, of the given URI. * diff --git a/support/src/test/java/org/springframework/ws/transport/jms/JmsMessageSenderIntegrationTest.java b/support/src/test/java/org/springframework/ws/transport/jms/JmsMessageSenderIntegrationTest.java index 1145e395..8499c9c2 100644 --- a/support/src/test/java/org/springframework/ws/transport/jms/JmsMessageSenderIntegrationTest.java +++ b/support/src/test/java/org/springframework/ws/transport/jms/JmsMessageSenderIntegrationTest.java @@ -22,6 +22,7 @@ import javax.jms.BytesMessage; import javax.jms.JMSException; import javax.jms.Message; import javax.jms.Session; +import javax.jms.TextMessage; import javax.xml.soap.MessageFactory; import javax.xml.soap.SOAPConstants; @@ -43,12 +44,9 @@ public class JmsMessageSenderIntegrationTest extends AbstractDependencyInjection private MessageFactory messageFactory; - private URI requestQueueUri; - private static final String SOAP_ACTION = "\"http://springframework.org/DoIt\""; protected void onSetUp() throws Exception { - requestQueueUri = new URI("jms:RequestQueue?deliveryMode=NON_PERSISTENT"); messageFactory = MessageFactory.newInstance(SOAPConstants.SOAP_1_1_PROTOCOL); } @@ -64,10 +62,11 @@ public class JmsMessageSenderIntegrationTest extends AbstractDependencyInjection this.messageSender = messageSender; } - public void testSendAndReceiveQueue() throws Exception { + public void testSendAndReceiveQueueBytesMessage() throws Exception { WebServiceConnection connection = null; try { - connection = messageSender.createConnection(requestQueueUri); + URI uri = new URI("jms:RequestQueue?deliveryMode=NON_PERSISTENT"); + connection = messageSender.createConnection(uri); SoapMessage soapRequest = new SaajSoapMessage(messageFactory.createMessage()); soapRequest.setSoapAction(SOAP_ACTION); connection.send(soapRequest); @@ -99,4 +98,40 @@ public class JmsMessageSenderIntegrationTest extends AbstractDependencyInjection } } + public void testSendAndReceiveQueueTextMessage() throws Exception { + WebServiceConnection connection = null; + try { + URI uri = new URI("jms:RequestQueue?deliveryMode=NON_PERSISTENT&messageType=TEXT_MESSAGE"); + connection = messageSender.createConnection(uri); + SoapMessage soapRequest = new SaajSoapMessage(messageFactory.createMessage()); + soapRequest.setSoapAction(SOAP_ACTION); + connection.send(soapRequest); + + TextMessage request = (TextMessage) jmsTemplate.receive(); + ByteArrayOutputStream bos = new ByteArrayOutputStream(); + messageFactory.createMessage().writeTo(bos); + final String text = new String(bos.toByteArray(), "UTF-8"); + jmsTemplate.send(request.getJMSReplyTo(), new MessageCreator() { + + public Message createMessage(Session session) throws JMSException { + TextMessage response = session.createTextMessage(); + response.setStringProperty(TransportConstants.HEADER_SOAP_ACTION, SOAP_ACTION); + response.setStringProperty(TransportConstants.HEADER_CONTENT_TYPE, + SoapVersion.SOAP_11.getContentType()); + response.setText(text); + return response; + } + }); + SoapMessage response = (SoapMessage) connection.receive(new SaajSoapMessageFactory(messageFactory)); + assertNotNull("No response received", response); + assertEquals("Invalid SOAPAction", SOAP_ACTION, response.getSoapAction()); + assertFalse("Message is fault", response.hasFault()); + } + finally { + if (connection != null) { + connection.close(); + } + } + } + } \ No newline at end of file diff --git a/support/src/test/java/org/springframework/ws/transport/jms/WebServiceMessageListenerIntegrationTest.java b/support/src/test/java/org/springframework/ws/transport/jms/WebServiceMessageListenerIntegrationTest.java index 7aa5c214..621f6f71 100644 --- a/support/src/test/java/org/springframework/ws/transport/jms/WebServiceMessageListenerIntegrationTest.java +++ b/support/src/test/java/org/springframework/ws/transport/jms/WebServiceMessageListenerIntegrationTest.java @@ -21,6 +21,7 @@ import javax.jms.JMSException; import javax.jms.Message; import javax.jms.Queue; import javax.jms.Session; +import javax.jms.TextMessage; import javax.jms.Topic; import org.springframework.jms.core.JmsTemplate; @@ -66,7 +67,7 @@ public class WebServiceMessageListenerIntegrationTest extends AbstractDependency return new String[]{"classpath:org/springframework/ws/transport/jms/jms-receiver-applicationContext.xml"}; } - public void testReceiveQueue() throws Exception { + public void testReceiveQueueBytesMessage() throws Exception { final byte[] b = CONTENT.getBytes("UTF-8"); jmsTemplate.send(requestQueue, new MessageCreator() { public Message createMessage(Session session) throws JMSException { @@ -80,6 +81,18 @@ public class WebServiceMessageListenerIntegrationTest extends AbstractDependency assertNotNull("No response received", response); } + public void testReceiveQueueTextMessage() throws Exception { + jmsTemplate.send(requestQueue, new MessageCreator() { + public Message createMessage(Session session) throws JMSException { + TextMessage request = session.createTextMessage(CONTENT); + request.setJMSReplyTo(responseQueue); + return request; + } + }); + TextMessage response = (TextMessage) jmsTemplate.receive(responseQueue); + assertNotNull("No response received", response); + } + public void testReceiveTopic() throws Exception { final byte[] b = CONTENT.getBytes("UTF-8"); jmsTemplate.send(requestTopic, new MessageCreator() { diff --git a/support/src/test/java/org/springframework/ws/transport/jms/support/JmsTransportUtilsTest.java b/support/src/test/java/org/springframework/ws/transport/jms/support/JmsTransportUtilsTest.java index 9f2ac769..a0630115 100644 --- a/support/src/test/java/org/springframework/ws/transport/jms/support/JmsTransportUtilsTest.java +++ b/support/src/test/java/org/springframework/ws/transport/jms/support/JmsTransportUtilsTest.java @@ -22,6 +22,8 @@ import javax.jms.Message; import junit.framework.TestCase; +import org.springframework.ws.transport.jms.JmsTransportConstants; + public class JmsTransportUtilsTest extends TestCase { public void testGetDestinationName() throws Exception { @@ -48,6 +50,20 @@ public class JmsTransportUtilsTest extends TestCase { assertEquals("Invalid deliveryMode", Message.DEFAULT_DELIVERY_MODE, deliveryMode); } + public void testGetMessageType() throws Exception { + URI uri = new URI("jms:RequestQueue?messageType=BYTESMESSAGE"); + int messageType = JmsTransportUtils.getMessageType(uri); + assertEquals("Invalid messageType", JmsTransportConstants.BYTES_MESSAGE_TYPE, messageType); + + uri = new URI("jms:RequestQueue?messageType=TEXT_MESSAGE"); + messageType = JmsTransportUtils.getMessageType(uri); + assertEquals("Invalid messageType", JmsTransportConstants.TEXT_MESSAGE_TYPE, messageType); + + uri = new URI("jms:RequestQueue?replyToName=RESP_QUEUE"); + messageType = JmsTransportUtils.getMessageType(uri); + assertEquals("Invalid messageType", JmsTransportConstants.BYTES_MESSAGE_TYPE, messageType); + } + public void testGetTimeToLive() throws Exception { URI uri = new URI("jms:RequestQueue?timeToLive=100"); long timeToLive = JmsTransportUtils.getTimeToLive(uri);