diff --git a/src/docbkx/client.xml b/src/docbkx/client.xml
index d793549e..745c2201 100644
--- a/src/docbkx/client.xml
+++ b/src/docbkx/client.xml
@@ -447,9 +447,9 @@ public void marshalWithSoapActionHeader(final Source s) {
Web Services 2.0.
- Writing integration tests
+ Writing client-side integration tests
- Spring Web Services 2.0 introduced support for creating Web service client tests.
+ Spring Web Services 2.0 introduced support for creating Web service client integration tests.
In this context, a client is a class that uses the WebServiceTemplate
to access a Web service.
@@ -463,7 +463,7 @@ public void marshalWithSoapActionHeader(final Source s) {
The typical usage of the MockWebServiceServer is:
-
+
Create a MockWebServiceServer instance by calling
@@ -501,7 +501,7 @@ public void marshalWithSoapActionHeader(final Source s) {
expectations have been met.
-
+
@@ -554,7 +554,7 @@ public class CustomerClient extends WebServiceGatewaySupport {
CustomerCountRequest is an object supported by a marshaller.
- For instance, it could have a @XmlRootElement annotation
+ For instance, it can have a @XmlRootElement annotation
to be supported by JAXB2.
@@ -575,8 +575,8 @@ public class CustomerClient extends WebServiceGatewaySupport {
-
-
+
+
@@ -604,8 +604,8 @@ import org.junit.runner.RunWith;
import static org.junit.Assert.assertEquals;
import org.springframework.ws.test.client.MockWebServiceServer;
-import static org.springframework.ws.test.client.RequestMatchers.payload;
-import static org.springframework.ws.test.client.ResponseCreators.withPayload;
+import static org.springframework.ws.test.client.RequestMatchers.*;
+import static org.springframework.ws.test.client.ResponseCreators.*;
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration("integration-test.xml")
@@ -622,7 +622,7 @@ public class CustomerClientIntegrationTest {
}
@Test
- public void basic() throws Exception {
+ public void customerClient() throws Exception {
Source requestPayload = new StringSource(
"" +
"John Doe" +
@@ -651,7 +651,7 @@ public class CustomerClientIntegrationTest {
- This tests uses the standard testing facilities provided in the Spring Framework.
+ This test uses the standard testing facilities provided in the Spring Framework.
This is not required, but is generally the easiest way to set up the test.
diff --git a/src/docbkx/server.xml b/src/docbkx/server.xml
index 42b5ce8f..daa03262 100644
--- a/src/docbkx/server.xml
+++ b/src/docbkx/server.xml
@@ -149,7 +149,7 @@
[servlet-name]-servlet.xml in the WEB-INF directory
of your web application and create the beans defined there in a Spring container. In the example above,
that means that it looks for '/WEB-INF/spring-ws-servlet.xml'. This file will
- contain all of the SWS-specific beans such as endpoints, marshallers and suchlike.
+ contain all of the Spring Web Services beans such as endpoints, marshallers and suchlike.
Automatic WSDL exposure
@@ -583,7 +583,7 @@
-
+
Endpoints
Endpoints are the central concept in Spring-WS's server-side support. Endpoints provide access to the
@@ -1566,4 +1566,365 @@ public class MyBusinessException extends Exception {
]]>
+
+ Server-side testing
+
+ When it comes to testing your Web service endpoints, there are two possible approaches:
+
+
+
+
+ Write Unit Tests, where you provide (mock) arguments for your endpoint to
+ consume.
+
+
+ The advantage of this approach is that it's quite easy to accomplish (especially for classes
+ annotated with @Endpoint); the disadvantage is that
+ you are not really testing the exact content of the XML messages that are sent over the wire.
+
+
+
+
+ Write Integrations Tests, which do test the contents of the message.
+
+
+
+
+ The first approach can easily be accomplished with mocking frameworks such as EasyMock, JMock, etc.
+ The next section will focus on writing integration tests, using the test features introduced in Spring
+ Web Services 2.0.
+
+
+ Writing server-side integration tests
+
+ Spring Web Services 2.0 introduced support for creating endpoint integration tests.
+ In this context, an endpoint is class handles (SOAP) messages (see ).
+
+
+ The integration test support lives in the org.springframework.ws.test.server package.
+ The core class in that package is the MockWebServiceClient.
+ The underlying idea is that this client creates a request message, and then sends it over to the
+ endpoint(s) that are configured in a standard MessageDispatcherServlet
+ application context (see ).
+ These endpoints will handle the message, and create a response.
+ The client then receives this response, and verifies it against registered expectations.
+
+
+ The typical usage of the MockWebServiceClient is:
+
+
+
+ Create a MockWebServiceClient instance by calling
+ MockWebServiceClient.createClient(ApplicationContext) or
+ MockWebServiceClient.createClient(WebServiceMessageReceiver, WebServiceMessageFactory).
+
+
+
+
+ Send request messages by calling sendRequest(RequestCreator),
+ possibly by using the default RequestCreator implementations
+ provided in RequestCreators (which can be statically imported).
+
+
+
+
+ Set up response expectations by calling andExpect(ResponseMatcher),
+ possibly by using the default ResponseMatcher implementations
+ provided in ResponseMatchers (which can be statically imported).
+ Multiple expectations can be set up by chaining
+ andExpect(ResponseMatcher) calls.
+
+
+
+
+
+
+ Note that the MockWebServiceClient (and related classes) offers a
+ 'fluent' API, so you can typically use the Code Completion features (i.e. ctrl-space) in your IDE
+ to guide you through the process of setting up the mock server.
+
+
+
+
+ Also note that you rely on the standard logging features available in Spring Web Services in your
+ unit tests.
+ Sometimes it might be useful to inspect the request or response message to find out why a
+ particular tests failed.
+ See for more information.
+
+
+
+ Consider, for example, this simple Web service endpoint class:
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ The CustomerEndpoint in annotated with
+ @Endpoint.
+ See .
+
+
+
+
+ The getCustomerCount() method takes a
+ CustomerCountRequest as argument, and returns a
+ CustomerCountResponse.
+ Both of these classes are objects supported by a marshaller.
+ For instance, they can have a @XmlRootElement annotation
+ to be supported by JAXB2.
+
+
+
+
+
+ A typical test for CustomerEndpoint would look like this:
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ " +
+ "John Doe" +
+ "");
+ Source responsePayload = new StringSource(
+ "" +
+ "10" +
+ "");
+
+ mockClient.sendRequest(withPayload(requestPayload)).
+ andExpect(payload(responsePayload));
+ }
+}]]>
+
+
+
+ The CustomerEndpointIntegrationTest imports the
+ MockWebServiceClient, and statically imports
+ RequestCreators and ResponseMatchers.
+
+
+
+
+ This test uses the standard testing facilities provided in the Spring Framework.
+ This is not required, but is generally the easiest way to set up the test.
+
+
+
+
+ The application context is a standard Spring-WS application context (see
+ ), read from
+ spring-ws-servlet.xml.
+ In this case, the application context will contain a bean definition for
+ CustomerEndpoint (or a perhaps a
+ <context:component-scan /> is used).
+
+
+
+
+ In a @Before method, we create a
+ MockWebServiceClient by using the
+ createClient factory method.
+
+
+
+
+ We send a request by calling sendRequest() with a
+ withPayload() RequestCreator
+ provided by the statically imported RequestCreators (see ).
+
+
+ We also set up response expectations by calling andExpect() with a
+ payload() ResponseMatcher provided
+ by the statically imported ResponseMatchers (see ).
+
+
+ This part of the test might look a bit confusing, but the Code Completion features of your
+ IDE are of great help.
+ After typing sendRequest(, simply type ctrl-space, and your IDE
+ will provide you with a list of possible request creating strategies, provided you
+ statically imported RequestCreators.
+ The same applies to andExpect(, provided you statically imported
+ ResponseMatchers.
+
+
+
+
+
+
+ RequestCreator and RequestCreators
+
+ Initially, the MockWebServiceClient will need to create a request message for the
+ endpoint to consume.
+ The client uses the RequestCreator
+ strategy interface for this purpose:
+
+
+
+ You can write your own implementations of this interface, creating a request message
+ by using the message factory, but you certainly do not have to.
+ The RequestCreators class provides a way to create a
+ RequestCreator based on a given payload in the
+ withPayload() method.
+ You will typically statically import RequestCreators.
+
+
+
+ ResponseMatcher and ResponseMatchers
+
+ When the request message has been processed by the endpoint, and a response has been received,
+ the MockWebServiceClient can verify whether this response message meets certain
+ expectations.
+ The client uses the ResponseMatcher strategy interface for this purpose:
+
+
+
+ Once again you can write your own implementations of this interface, throwing
+ AssertionErrors when the message does not meet your expectations, but you
+ certainly do not have to, as the ResponseMatchers class provides standard
+ ResponseMatcher implementations for you to use in your tests.
+ You will typically statically import this class.
+
+
+ The ResponseMatchers class provides the following request matchers:
+
+
+
+
+ ResponseMatchers method
+ Description
+
+
+
+
+ payload()
+ Expects a given response payload.
+
+
+ validPayload()
+ Expects the response payload to validate against given XSD schema(s).
+
+
+ xpath()
+
+ Expects a given XPath expression to exist, not exist, or evaluate to a given
+ value.
+
+
+
+ soapHeader()
+ Expects a given SOAP header to exist in the response message.
+
+
+ noFault()
+ Expects that the response message does not contain a SOAP Fault.
+
+
+
+ mustUnderstandFault(),
+ clientOrSenderFault(),
+ serverOrReceiverFault(), and
+ versionMismatchFault()
+
+ Expects the response message to contain a specific SOAP Fault.
+
+
+
+
+ You can set up multiple response expectations by chaining andExpect() calls,
+ like so:
+ mockClient.sendRequest(...).
+ andExpect(payload(expectedResponsePayload)).
+ andExpect(validPayload(schemaResource));
+
+
+
+ For more information on the request matchers provided by ResponseMatchers,
+ refer to the class level Javadoc.
+
+
+