diff --git a/spring-integration-ws/src/main/java/org/springframework/integration/ws/AbstractWebServiceOutboundGateway.java b/spring-integration-ws/src/main/java/org/springframework/integration/ws/AbstractWebServiceOutboundGateway.java index 3320ed1bff..6fd436227b 100644 --- a/spring-integration-ws/src/main/java/org/springframework/integration/ws/AbstractWebServiceOutboundGateway.java +++ b/spring-integration-ws/src/main/java/org/springframework/integration/ws/AbstractWebServiceOutboundGateway.java @@ -228,7 +228,7 @@ public abstract class AbstractWebServiceOutboundGateway extends AbstractReplyPro Object resultObject = this.doExtractData(message); - if (message instanceof SoapMessage){ + if (resultObject != null && message instanceof SoapMessage){ Map mappedMessageHeaders = AbstractWebServiceOutboundGateway.this.headerMapper.toHeadersFromReply((SoapMessage) message); return MessageBuilder.withPayload(resultObject).copyHeaders(mappedMessageHeaders).build(); diff --git a/spring-integration-ws/src/main/java/org/springframework/integration/ws/SimpleWebServiceOutboundGateway.java b/spring-integration-ws/src/main/java/org/springframework/integration/ws/SimpleWebServiceOutboundGateway.java index 03083fd1d9..bd218b09d8 100644 --- a/spring-integration-ws/src/main/java/org/springframework/integration/ws/SimpleWebServiceOutboundGateway.java +++ b/spring-integration-ws/src/main/java/org/springframework/integration/ws/SimpleWebServiceOutboundGateway.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2011 the original author or authors. + * Copyright 2002-2013 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -40,12 +40,13 @@ import org.springframework.xml.transform.TransformerObjectSupport; /** * An outbound Messaging Gateway for invoking a Web Service. - * + * * @author Mark Fisher * @author Oleg Zhurakousky + * @author Artem Bilan */ public class SimpleWebServiceOutboundGateway extends AbstractWebServiceOutboundGateway { - + private final SourceExtractor sourceExtractor; public SimpleWebServiceOutboundGateway(DestinationProvider destinationProvider) { @@ -85,23 +86,22 @@ public class SimpleWebServiceOutboundGateway extends AbstractWebServiceOutboundG else if (requestPayload instanceof Document) { responseResultInstance = new DOMResult(); } - Object reply = this.getWebServiceTemplate().sendAndReceive(uri, + return this.getWebServiceTemplate().sendAndReceive(uri, new SimpleRequestMessageCallback(requestCallback, requestMessage), new SimpleResponseMessageExtractor(responseResultInstance)); - return reply; } private class SimpleRequestMessageCallback extends RequestMessageCallback { - + public SimpleRequestMessageCallback(WebServiceMessageCallback requestCallback, Message requestMessage){ super(requestCallback, requestMessage); } - + @Override public void doWithMessageInternal(WebServiceMessage message, Object payload) throws IOException, TransformerException { Source source = this.extractSource(payload); this.transform(source, message.getPayloadResult()); } - + private Source extractSource(Object requestPayload) throws IOException, TransformerException{ Source source = null; @@ -123,15 +123,16 @@ public class SimpleWebServiceOutboundGateway extends AbstractWebServiceOutboundG "', and '" + Document.class.getName() + "'. Consider either using the '" + MarshallingWebServiceOutboundGateway.class.getName() + "' or a Message Transformer."); } - + return source; - } + } + } - + private class SimpleResponseMessageExtractor extends ResponseMessageExtractor { - + private final Result result; - + public SimpleResponseMessageExtractor(Result result){ super(); this.result = result; @@ -140,28 +141,26 @@ public class SimpleWebServiceOutboundGateway extends AbstractWebServiceOutboundG @Override public Object doExtractData(WebServiceMessage message) throws IOException, TransformerException{ Source payloadSource = message.getPayloadSource(); - Object payload = null; - - if (this.result != null){ + + if (payloadSource != null && this.result != null) { this.transform(payloadSource, this.result); if (this.result instanceof StringResult){ - payload = this.result.toString(); + return this.result.toString(); } else if (this.result instanceof DOMResult){ - payload = ((DOMResult)this.result).getNode(); + return ((DOMResult)this.result).getNode(); } else { - payload = this.result; + return this.result; } } - else { - payload = payloadSource; - } - return payload; + + return payloadSource; } + } - + private static class DefaultSourceExtractor extends TransformerObjectSupport implements SourceExtractor { public DOMSource extractData(Source source) throws IOException, TransformerException { @@ -172,5 +171,7 @@ public class SimpleWebServiceOutboundGateway extends AbstractWebServiceOutboundG this.transform(source, result); return new DOMSource(result.getNode()); } + } + } diff --git a/spring-integration-ws/src/test/java/org/springframework/integration/ws/SimpleWebServiceOutboundGatewayTests.java b/spring-integration-ws/src/test/java/org/springframework/integration/ws/SimpleWebServiceOutboundGatewayTests.java index f299801e9e..c1c8551c30 100644 --- a/spring-integration-ws/src/test/java/org/springframework/integration/ws/SimpleWebServiceOutboundGatewayTests.java +++ b/spring-integration-ws/src/test/java/org/springframework/integration/ws/SimpleWebServiceOutboundGatewayTests.java @@ -38,6 +38,8 @@ import org.springframework.context.support.ClassPathXmlApplicationContext; import org.springframework.integration.Message; import org.springframework.integration.MessageChannel; import org.springframework.integration.core.PollableChannel; +import org.springframework.integration.handler.ReplyRequiredException; +import org.springframework.integration.message.GenericMessage; import org.springframework.integration.support.MessageBuilder; import org.springframework.ws.WebServiceMessage; import org.springframework.ws.WebServiceMessageFactory; @@ -57,12 +59,17 @@ public class SimpleWebServiceOutboundGatewayTests { private static final String response = "Test Name"; - private static final String responseSoapMessage = " " + + public static final String responseSoapMessage = " " + " " + response + " " + ""; + public static final String responseEmptyBodySoapMessage = "\n" + + "\n" + + "\n" + + ""; + @Test // INT-1051 public void soapActionAndCustomCallback() { String uri = "http://www.example.org"; @@ -100,7 +107,16 @@ public class SimpleWebServiceOutboundGatewayTests { assertThat(replyMessage.getPayload().toString(), Matchers.endsWith(response)); } - public static WebServiceMessageSender createMockMessageSender() throws Exception { + @Test(expected = ReplyRequiredException.class) + public void testInt3022EmptyResponseBody() throws Exception { + SimpleWebServiceOutboundGateway gateway = new SimpleWebServiceOutboundGateway("http://testInt3022"); + gateway.setRequiresReply(true); + WebServiceMessageSender messageSender = createMockMessageSender(responseEmptyBodySoapMessage); + gateway.setMessageSender(messageSender); + gateway.handleMessage(new GenericMessage("foo")); + } + + public static WebServiceMessageSender createMockMessageSender(final String mockResponseMessage) throws Exception { WebServiceMessageSender messageSender = Mockito.mock(WebServiceMessageSender.class); WebServiceConnection wsConnection = Mockito.mock(WebServiceConnection.class); Mockito.when(messageSender.createConnection(Mockito.any(URI.class))).thenReturn(wsConnection); @@ -110,7 +126,7 @@ public class SimpleWebServiceOutboundGatewayTests { public Object answer(InvocationOnMock invocation) throws Exception{ Object[] args = invocation.getArguments(); WebServiceMessageFactory factory = (WebServiceMessageFactory) args[0]; - return factory.createWebServiceMessage(new ByteArrayInputStream(responseSoapMessage.getBytes())); + return factory.createWebServiceMessage(new ByteArrayInputStream(mockResponseMessage.getBytes())); }}).when(wsConnection).receive(Mockito.any(WebServiceMessageFactory.class)); return messageSender; diff --git a/spring-integration-ws/src/test/java/org/springframework/integration/ws/WebServiceOutboundGatewayInsideChainTests-context.xml b/spring-integration-ws/src/test/java/org/springframework/integration/ws/WebServiceOutboundGatewayInsideChainTests-context.xml index 24767d0edf..a94a57a978 100644 --- a/spring-integration-ws/src/test/java/org/springframework/integration/ws/WebServiceOutboundGatewayInsideChainTests-context.xml +++ b/spring-integration-ws/src/test/java/org/springframework/integration/ws/WebServiceOutboundGatewayInsideChainTests-context.xml @@ -1,9 +1,9 @@ + factory-method="createMockMessageSender"> + +