sorenpoulsen.com header

Create A Spring Web Service Client With Maven

This description on how to create a Spring web service client is based on a sample Maven project hosted on GitHub. You are welcome to clone the project, it's linked in the bottom section.

The web service client is built "contract-first" from a WSDL file and a number of XSD files. It uses the Spring-WS API and marshals and unmarshals the SOAP body content with JAXB. The JAXB annotated Java classes are compiled from XML schema using the jaxb2-maven-plugin.

First let's take a look at the sample project's web service.

The Customer Service

The sample project has a Customer Service with a single operation called GetCustomer. GetCustomer sends a customer ID and receives a response with details on the customer like name and address.

This is a GetCustomer request:

And here's the reponse:

The WSDL is stored in /src/main/schemas/CustomerService.wsdl. The content of the WSDL file is shown below. It's a Document/literal Wrapped service bound to SOAP 1.2 and HTTP. Document/Literal means the content of the SOAP body is an XML document constrained by regular XML schema. Wrapped means the SOAP body can only have one child element, the "Wrapper" element, and it is named after the operation that is being invoked. The Wrapper element in a SOAP body response is also named after the operation, but with the word "Response" appended.

Although the request and response messages in the SOAP body are quite simple, their XML schemas are not embedded directly in the <types> section of the WSDL, but are instead included from separate XSD files. This is to demonstrate that the schema compiler XJC can traverse all the XML schemas starting from the WSDL file.

Compile XML schema to JAXB annotated Java classes

XML Schemas are compiled to JAXB annotated Java classes with the XJC tool that comes bundled with the JDK. The JAXB classes are used to marshal and unmarshal the SOAP body.

Diagram showing how WSDL and XML schemas are compiled to JAXB annotated Java classes with the XJC tool

Since it's a Maven project we will only use XJC indirectly through the jaxb2-maven-plugin. The plugin is configured in this section of the projects pom.xml file:

The source parameter points to the WSDL file from which the JAXB classes are generated.

The sourceType configures the plugin to accept WSDL files.

The plugin scans the <types> section of the WSDL and traverses any XSD files that are included or imported.

All the possible jaxb2-maven-plugin parameters for the xjc goal are documented here.

Building the Spring web service client

The web service client CustomerServiceClient.java is a subclass of WebServiceGatewaySupport from the Spring-WS API. WebServiceGatewaySupport produces an instance of the WebServiceTemplate that the client uses to call the service.

The client invokes WebServiceTemplate.marshalSendAndReceive() that opens a connection to the service, then marshals the SOAP body request from the GetCustomer JAXB class and unmarshals the SOAP body response to the GetCustomerResponse JAXB class.

There are two pieces of the of WebServiceGatewaySupport base class that we need to configure in the Spring context CustomerServiceConfiguration.java. First we need to inject a MessageFactory with SOAP 1.2 support because the WSDL file uses SOAP 1.2 and the default MessageFactory only supports SOAP 1.1. Secondly we need to inject a JAXB marshaller.

I assume familiarity with Spring's context configuration, so I'm not going into details, but do notice that we need to provide the Java namespace of the JAXB classes to Jaxb2Marshaller in the setContextPath() method. If there are multiple Java namespaces then they are separated with ":".

In the sample project the Java namespace was mapped directly from the XML schema namespace, but it can be overwritten by the jaxb2-maven-plugin with the packageName configuration parameter.

Test the client

The integration test CustomerServiceTest.java simply calls the GetCustomer operation and asserts that the response is as expected. The client call is directed to a SoapUI mock service that is launched just before Maven's test phase using the soapui-maven-plugin. You don't have to install SoapUI to run the test. Maven will fetch all the dependencies that are needed. I have a separate post on how to create such a mock service here: https://sorenpoulsen.com/mock-services-for-maven-integration-tests-with-the-soapui-plugin

The GitHub project

The project is available at https://github.com/SorenPoulsen/spring-web-service-client-with-maven.

Prerequisites:

  • Maven 3.5.0 installed and its /bin folder on PATH.
  • JDK 1.8 installed and JAVA_HOME set to the root folder of the JDK.

To clone, build and run the project, hit the terminal and run these commands:

$ git clone https://github.com/SorenPoulsen/spring-web-service-client-with-maven.git
$ cd spring-web-service-client-with-maven
$ mvn clean test

{{model.usr.name}}
{{cmt.user.name}}
{{cmt.user.name}}
{{childcmt.user.name}}
{{childcmt.user.name}}