This article was originally written in October 2008 and posted on my old blog at wordpress.com. I’ve retired that blog, so I’ve reposted the original contents here in the hope someone finds it useful. As of December 2011 the code still works great. Note I’m an iOS developer nowadays, not a Java developer, so regretfully I can’t offer any support nor updates if it doesn’t work for you. Please feel free to read, comment, and link to the article here at its new home.

Background

About a week ago I needed to write a SOAP-based client for work. The SOAP framework I’m using is Apache CXF. I’m a total noob when it comes to SOAP services, and so I was a little apprehensive about this at first. My apprehension sprung from hearing horror stories a few years ago from coworkers who were writing Axis SOAP applications, and they were basically tearing their hair out over Axis.

However, word has it that CXF is much easier to use. Well, it took me a while to get it working correctly. In an effort to save other folks the same grief, I’ve posted my code here. If you’re reading this, I’m assuming you’re acquainted with Java and Maven, but fairly new to SOAP, WSDL, etc.

To keep things simple, I decided to write a “Hello World” type of application first to make sure I could get the technology stack working correctly. To keep things really simple, I decided to create a trivial Java “main” function that calls a SOAP service, logs the result to the console, and exits (no fancy web interface or anything like that).

The SOAP Service Provider

First I had to select an appropriate web service to test against. There are a bunch of free SOAP-based web services out there, and I chose the CDyne weather service. You can go read all about it if you want.

Obtain the Service’s WSDL

When you’re writing a new client in CXF for an existing web service, you start with the WSDL and work from there. This means you need to get a copy of the WSDL from the service provider. The WSDL for the CDyne weather service can be downloaded from their site. You can simply right-click that link and save the WSDL on your hard drive.

Once you have the WSDL in hand, you can build your client around it. Basically, you’ll use a CXF tool called wsdl2java to turn the WSDL into Java stub code that you then compile along with your application.

Create the Maven Project

As a recent convert to Maven, I set up a new Maven project. I created a new project directory called weather-client, which is the ${basedir}. Also, I put the WSDL file in ${basedir}/src/main/wsdl/weather.wsdl.

Yeah, I know Maven has its fancy archetype creator thingie to emit the initial POM file, but like most pragmatic programmers I simply copy and paste a similar POM from somewhere else and modify it to suit my needs. Here’s the project file I came up with.

weather-client/pom.xml

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0
                      http://maven.apache.org/maven-v4_0_0.xsd">
    
    <modelVersion>4.0.0</modelVersion>
    <groupId>com.logicsector</groupId>
    <artifactId>weather-client</artifactId>
    <version>1.0</version>
    <name>SOAP weather client</name>
    <packaging>jar</packaging>
    
    <dependencies>
        <dependency>
            <groupId>org.apache.cxf</groupId>
            <artifactId>cxf-rt-frontend-jaxws</artifactId>
            <version>2.1.2</version>
        </dependency>
        <dependency>
            <groupId>org.apache.cxf</groupId>
            <artifactId>cxf-rt-transports-http</artifactId>
            <version>2.1.2</version>
        </dependency>
        <dependency>
            <groupId>org.slf4j</groupId>
            <artifactId>slf4j-api</artifactId>
            <version>1.5.2</version>
        </dependency>
        <dependency>
            <groupId>org.slf4j</groupId>
            <artifactId>slf4j-log4j12</artifactId>
            <version>1.5.2</version>
        </dependency>
    </dependencies>
    
    <build>
        <finalName>weather-client</finalName>
        <plugins>
            <!-- Generate Java classes from WSDL during build -->
            <plugin>
                <groupId>org.apache.cxf</groupId>
                <artifactId>cxf-codegen-plugin</artifactId>
                <version>2.1.2</version>
                <executions>
                    <execution>
                        <id>generate-sources</id>
                        <phase>generate-sources</phase>
                        <configuration>
                            <sourceRoot>${basedir}/target/generated/src/main/java</sourceRoot>
                            <wsdlOptions>
                                <wsdlOption>
                                    <wsdl>${basedir}/src/main/wsdl/weather.wsdl</wsdl>
                                    <extraargs>
                                        <extraarg>-client</extraarg>
                                    </extraargs>
                                </wsdlOption>
                            </wsdlOptions>
                        </configuration>
                        <goals>
                            <goal>wsdl2java</goal>
                        </goals>
                    </execution>
                </executions>
            </plugin>
            <!-- Add generated sources - avoids having to copy generated sources to build location -->
            <plugin>
                <groupId>org.codehaus.mojo</groupId>
                <artifactId>build-helper-maven-plugin</artifactId>
                <executions>
                    <execution>
                        <id>add-source</id>
                        <phase>generate-sources</phase>
                        <goals>
                            <goal>add-source</goal>
                        </goals>
                        <configuration>
                            <sources>
                                <source>${basedir}/target/generated/src/main/java</source>
                            </sources>
                        </configuration>
                    </execution>
                </executions>
            </plugin>
            <!-- Build the JAR with dependencies -->
            <plugin>
                <artifactId>maven-assembly-plugin</artifactId>
                <configuration>
                    <descriptorRefs>
                        <descriptorRef>jar-with-dependencies</descriptorRef>
                    </descriptorRefs>
                </configuration>
            </plugin>
        </plugins>
        <!-- Build with Java 1.5 -->
        <pluginManagement>
            <plugins>
                <plugin>
                    <groupId>org.apache.maven.plugins</groupId>
                    <artifactId>maven-compiler-plugin</artifactId>
                    <configuration>
                        <source>1.5</source>
                        <target>1.5</target>
                    </configuration>
                </plugin>
            </plugins>
        </pluginManagement>
    </build>
    
</project>

The only items of interest in the POM are:

  • We depend on the CXF v2.1.2 client libraries and the (most excellent) SLF4J logging system
  • We invoke the cxf-codegen-plugin to run wsdl2java to generate our Java stub code into ${basedir}/target/generated/src/main/java
  • We use the build-helper-maven-plugin so that Maven can compile from two source directories (normally Maven just compiles what’s in ${basedir}/src/main and not ${basedir}/target/generated/src, so we tell Maven to go compile the generated stub code too)
  • We use the maven-assembly-plugin to create a final JAR containing all necessary dependencies, which Maven will create as weather-client-jar-with-dependencies.jar when we perform a mvn assembly:assembly

At this point, even though I had no code in the project, I ran mvn assembly:assembly to build the Java stubs from the WSDL file. The output is in the generated source directory mentioned earlier, in case you want to go poke at it.

The Client Code

Once we have the autogenerated stubs we can use them in a real Java program. Before you can use the stubs, you have to identify what the actual service object is. You can find out by looking at the generated stub code and see which Java class extends Service. That will be the service interface that you call in your client. In this case, the service is called simply “Weather”.

Without further ado, here’s the code I wrote to invoke the SOAP service:

weather-client/src/main/java/com/logicsector/soapclient/SoapClient.java

package com.logicsector.soapclient;

import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.cdyne.ws.weatherws.Forecast;
import com.cdyne.ws.weatherws.ForecastReturn;
import com.cdyne.ws.weatherws.POP;
import com.cdyne.ws.weatherws.Temp;
import com.cdyne.ws.weatherws.Weather;
import com.cdyne.ws.weatherws.WeatherSoap;

public class SoapClient {
    private static final Logger           LOGGER      = LoggerFactory.getLogger(SoapClient.class);
    private static final SimpleDateFormat DATE_FORMAT = new SimpleDateFormat("EEEE, MMMM d yyyy");

    public static void main(String[] args) {
        try {
            LOGGER.debug("Creating weather service instance (Note: Weather = Service subclass)...");
            long start = new Date().getTime();
            // Get a reference to the SOAP service interface.
            Weather weatherService = new Weather();
            WeatherSoap weatherSoap = weatherService.getWeatherSoap();
            // An alternate way to get the SOAP service interface; includes logging interceptors.
            // JaxWsProxyFactoryBean factory = new org.apache.cxf.jaxws.JaxWsProxyFactoryBean();
            // factory.setServiceClass(WeatherSoap.class);
            // factory.setAddress("http://ws.cdyne.com/WeatherWS/Weather.asmx");
            // factory.getInInterceptors().add(new org.apache.cxf.interceptor.LoggingInInterceptor());
            // factory.getOutInterceptors().add(new org.apache.cxf.interceptor.LoggingOutInterceptor());
            // WeatherSoap weatherSoap = (WeatherSoap) factory.create();
            long end = new Date().getTime();
            LOGGER.debug("...Done! weatherService instance: {}", weatherService);
            LOGGER.debug("Time required to initialize weather service interface: {} seconds", (end - start) / 1000f);

            // Send a SOAP weather request for zip code 94025 (Menlo Park, CA, USA).
            LOGGER.debug("weatherSoap instance: {}", weatherSoap);
            start = new Date().getTime();
            ForecastReturn forecastReturn = weatherSoap.getCityForecastByZIP("94025");
            end = new Date().getTime();
            LOGGER.debug("Time required to invoke 'getCityForecastByZIP': {} seconds", (end - start) / 1000f);
            LOGGER.debug("forecastReturn: {}", forecastReturn);
            LOGGER.debug("forecastReturn city: {}", forecastReturn.getCity());
            LOGGER.debug("forecastReturn state: {}", forecastReturn.getState());
            LOGGER.debug("forecastReturn result: {}", forecastReturn.getForecastResult());
            LOGGER.debug("forecastReturn response text: {}", forecastReturn.getResponseText());
            LOGGER.debug("");
            List<Forecast> forecasts = forecastReturn.getForecastResult().getForecast();
            for (Forecast forecast : forecasts) {
                LOGGER.debug("  forecast date: {}", DATE_FORMAT.format(forecast.getDate().toGregorianCalendar().getTime()));
                LOGGER.debug("  forecast description: {}", forecast.getDesciption());
                Temp temps = forecast.getTemperatures();
                LOGGER.debug("  forecast temperature high: {}", temps.getDaytimeHigh());
                LOGGER.debug("  forecast temperature low: {}", temps.getMorningLow());
                POP pop = forecast.getProbabilityOfPrecipiation();
                LOGGER.debug("  forecast precipitation day: {}%", pop.getDaytime());
                LOGGER.debug("  forecast precipitation night: {}%", pop.getNighttime());
                LOGGER.debug("");
            }
            LOGGER.debug("Program complete, exiting");
        }
        catch (Exception e) {
            LOGGER.error("An exception occurred, exiting", e);
        }
    }

}

Note that we’re importing the stubs as import com.cdyne.ws.weatherws.Forecast, etc, within the client program. The client is also hard-coded to get the weather report from the 94025 zip code, although you could easily alter the client to take the zip code as a command-line argument.

The All-Important CXF Client Configuration File

This is the part of the development process that threw me for a loop. I didn’t see any CXF documentation that indicated a cxf.xml file needs to be in the classpath of the client, so I hadn’t included one in the project. My client program kept failing with a (very cryptic, very unhelpful) CXF BusException (the complete message was org.apache.cxf.BusException: No binding factory for namespace http://schemas.xmlsoap.org/soap/ registered, which I’m mentioning here in case anyone else is Googling with the same problem).

Sure, there are plenty of CXF tutorials on the Internet, but they mostly seem to build a client and a service in the same project (sharing a cxf.xml file) and I had assumed the configuration file was for configuring only the server. Silly me.

It took me several days of Googling, trying different JAR dependencies, Googling again, testing various source code modifications, Googling some more, asking for help on the cxf-user mail list — all to no avail.

Eventually, while reading the solution to an unrelated problem, I finally discovered the cause. On start-up for a server OR A CLIENT, the CXF system looks for a cxf.xml file, and fails without it. Just for the record, the BusException message is incredibly unhelpful. Grrr!! I think it should read something like org.apache.cxf.BusException: No binding factory for namespace http://schemas.xmlsoap.org/soap/ registered (did you include a cxf.xml file somewhere in the classpath?), or some such.

Anyhoo, here’s the CXF configuration file I used. Not much to it. It’s basically just a trivial Spring configuration with three lines of imports.

weather-client/src/main/resources/cxf.xml

<beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:http-conf="http://cxf.apache.org/transports/http/configuration"
    xsi:schemaLocation="http://cxf.apache.org/transports/http/configuration
           http://cxf.apache.org/schemas/configuration/http-conf.xsd
           http://www.springframework.org/schema/beans
           http://www.springframework.org/schema/beans/spring-beans.xsd">
    
    <import resource="classpath:META-INF/cxf/cxf.xml"/>
    <import resource="classpath:META-INF/cxf/cxf-extension-soap.xml"/>
    <import resource="classpath:META-INF/cxf/cxf-servlet.xml"/>
    
</beans>

Good thing this is easier than Axis.

Logging Configuration

For completeness, I’ve included the logging file I used. Since we’re using LOG4J as the logging layer under SLF4J, we need to supply a log4j.properties file.

weather-client/src/main/resources/log4j.properties

log4j.rootCategory=WARN, CONSOLE
log4j.appender.CONSOLE=org.apache.log4j.ConsoleAppender
log4j.appender.CONSOLE.layout=org.apache.log4j.PatternLayout
log4j.appender.CONSOLE.layout.ConversionPattern=[%d{ABSOLUTE} %-5p %c{1}]: %m%n
log4j.logger.com.logicsector=DEBUG

Building and Running the Client

Once you have all the code in order, it’s time to build it. From within the weather-client directory, just use the previously-mentioned Maven build command to create a JAR file with dependencies:

mvn assembly:assembly

Now we can run the client. As mentioned previously, the client is hard-coded to get the weather report for the 94025 zip code (Menlo Park, California). From within the weather-client directory, the following command will start the client and invoke the service:

java -cp target/weather-client-jar-with-dependencies.jar com.logicsector.soapclient.SoapClient

The command above should all be on a single line. Note you may need to change your path separator if you’re not on a Unix-based system. If everything went smoothly you should see output something like this:

[17:31:06,278 DEBUG SoapClient]: Creating weather service instance (Note: Weather = Service subclass)...
Oct 18, 2008 5:31:08 PM org.apache.cxf.service.factory.ReflectionServiceFactoryBean buildServiceFromWSDL
INFO: Creating Service {http://ws.cdyne.com/WeatherWS/}Weather from WSDL: file:/c:/Projects/weather-client/src/main/wsdl/weat
her.wsdl
[17:31:08,325 DEBUG SoapClient]: ...Done! weatherService instance: com.cdyne.ws.weatherws.Weather@754fc
[17:31:08,325 DEBUG SoapClient]: Time required to initialize weather service interface: 2.047 seconds
[17:31:08,325 DEBUG SoapClient]: weatherSoap instance: org.apache.cxf.jaxws.JaxWsClientProxy@6458a6
[17:31:08,825 DEBUG SoapClient]: Time required to invoke 'getCityForecastByZIP': 0.5 seconds
[17:31:08,825 DEBUG SoapClient]: forecastReturn: com.cdyne.ws.weatherws.ForecastReturn@aea710
[17:31:08,825 DEBUG SoapClient]: forecastReturn city: Menlo Park
[17:31:08,825 DEBUG SoapClient]: forecastReturn state: CA
[17:31:08,825 DEBUG SoapClient]: forecastReturn result: com.cdyne.ws.weatherws.ArrayOfForecast@5a2eaa
[17:31:08,825 DEBUG SoapClient]: forecastReturn response text: City Found
[17:31:08,825 DEBUG SoapClient]:
[17:31:08,825 DEBUG SoapClient]:   forecast date: Friday, October 17 2008
[17:31:08,825 DEBUG SoapClient]:   forecast description: Sunny
[17:31:08,825 DEBUG SoapClient]:   forecast temperature high: 82
[17:31:08,825 DEBUG SoapClient]:   forecast temperature low: 58
[17:31:08,825 DEBUG SoapClient]:   forecast precipitation day: 00%
[17:31:08,825 DEBUG SoapClient]:   forecast precipitation night: 00%
[17:31:08,825 DEBUG SoapClient]:
[17:31:08,825 DEBUG SoapClient]:   forecast date: Saturday, October 18 2008
[17:31:08,825 DEBUG SoapClient]:   forecast description: Sunny
[17:31:08,841 DEBUG SoapClient]:   forecast temperature high: 73
[17:31:08,841 DEBUG SoapClient]:   forecast temperature low: 55
[17:31:08,841 DEBUG SoapClient]:   forecast precipitation day: 00%
[17:31:08,841 DEBUG SoapClient]:   forecast precipitation night: 00%
[17:31:08,841 DEBUG SoapClient]:
[17:31:08,841 DEBUG SoapClient]:   forecast date: Sunday, October 19 2008
[17:31:08,841 DEBUG SoapClient]:   forecast description: Partly Cloudy
[17:31:08,841 DEBUG SoapClient]:   forecast temperature high: 70
[17:31:08,841 DEBUG SoapClient]:   forecast temperature low: 55
[17:31:08,841 DEBUG SoapClient]:   forecast precipitation day: 00%
[17:31:08,841 DEBUG SoapClient]:   forecast precipitation night: 00%
[17:31:08,841 DEBUG SoapClient]:
[17:31:08,841 DEBUG SoapClient]:   forecast date: Monday, October 20 2008
[17:31:08,841 DEBUG SoapClient]:   forecast description: Partly Cloudy
[17:31:08,841 DEBUG SoapClient]:   forecast temperature high: 70
[17:31:08,841 DEBUG SoapClient]:   forecast temperature low: 53
[17:31:08,841 DEBUG SoapClient]:   forecast precipitation day: 00%
[17:31:08,841 DEBUG SoapClient]:   forecast precipitation night: 00%
[17:31:08,841 DEBUG SoapClient]:
[17:31:08,841 DEBUG SoapClient]:   forecast date: Tuesday, October 21 2008
[17:31:08,856 DEBUG SoapClient]:   forecast description: Sunny
[17:31:08,856 DEBUG SoapClient]:   forecast temperature high: 73
[17:31:08,856 DEBUG SoapClient]:   forecast temperature low: 54
[17:31:08,856 DEBUG SoapClient]:   forecast precipitation day: 00%
[17:31:08,856 DEBUG SoapClient]:   forecast precipitation night: 10%
[17:31:08,856 DEBUG SoapClient]:
[17:31:08,856 DEBUG SoapClient]:   forecast date: Wednesday, October 22 2008
[17:31:08,856 DEBUG SoapClient]:   forecast description: Sunny
[17:31:08,856 DEBUG SoapClient]:   forecast temperature high: 74
[17:31:08,856 DEBUG SoapClient]:   forecast temperature low: 55
[17:31:08,856 DEBUG SoapClient]:   forecast precipitation day: 00%
[17:31:08,856 DEBUG SoapClient]:   forecast precipitation night: 00%
[17:31:08,856 DEBUG SoapClient]:
[17:31:08,856 DEBUG SoapClient]:   forecast date: Thursday, October 23 2008
[17:31:08,856 DEBUG SoapClient]:   forecast description: Sunny
[17:31:08,856 DEBUG SoapClient]:   forecast temperature high: 73
[17:31:08,856 DEBUG SoapClient]:   forecast temperature low: 55
[17:31:08,856 DEBUG SoapClient]:   forecast precipitation day: 00%
[17:31:08,856 DEBUG SoapClient]:   forecast precipitation night: 00%
[17:31:08,856 DEBUG SoapClient]:
[17:31:08,856 DEBUG SoapClient]: Program complete, exiting

Interestingly, it takes 2 seconds on my machine to initialize the interface, which seems like a really long time. CXF is probably doing a lot of stuff under the covers, but still, 2 seconds is forever in computer time.

The call to the weather service interface, once initialized, takes about half a second every time, which includes marshalling a SOAP request, sending it over the internet, receiving the response, and unmarshalling its contents. Not too bad I guess.

Concluding Thoughts

Hopefully this example will form the basis of your next SOAP client. It really is pretty easy once you see a complete and working example.

If you were ambitious, parts of this code could easily be incorporated into a web application that provides a weather report for the user. You’d simply create a servlet that takes the zip code as a parameter, invokes the SOAP service, and shows the weather report in the response. In other words, the technique of calling the SOAP service would be the same even if this was a web application.

Well, that’s the end of my post about creating a CXF client with Maven. I’d love to read your comments if you found this post helpful.

EDIT: Download the Source!

All the code necessary to build the project is listed above. However, to save time, you can simply download the code from my web site. Happy coding!

Tagged with:  

29 Responses to How to create a WSDL-first SOAP client in Java with CXF and Maven

  1. Damian says:

    Thanks for this post Justin! It was very useful!

  2. Thank you very much for this! I have to create something similar and this is helping me =)

  3. Albert says:

    Thanks for the simplified explanation. Very helpful to start using CXF.

  4. Boris says:

    Justin, thanks a lot for this post! Unfortunately, I found it when I already created WS client, but you saved “several days of Googling, trying different JAR dependencies, Googling again, testing various source code modifications, Googling some more, asking for help on the cxf-user mail list” describing BusException solution.

    HUGE THANKS!

  5. David says:

    This is great!! How do I get it to work in eclipse? thanks in advance.

    • Justin says:

      Hi David, glad you found this post helpful. I’ve transitioned away from Java development (to iPhone development) but IIRC it should be pretty easy to use this with Eclipse. First you’ll need a Maven plugin for Eclipse (there are a couple out there, a quick Google search should find them). Once you have the Maven plugin installed, just use it to load the Maven pom.xml file that’s shown above–the plugin will import the entire project. Then you can use Eclipse to build and run the project. Good luck w/ it!

  6. Victor says:

    Thanks, nice post!

  7. shannu says:

    very gud example to understand the cxf client using maven. thank u very much…

  8. mesut says:

    Great explanation, simple and clear. Thanks

  9. Amit R says:

    HI,

    I see the example uses CXF 2.1.2 I am wondering did you ever tried cxf client using any version 2.4 or later

    Thanks

    • Justin says:

      Hi Amit, no I never tried it with a later version of CXF. I used the version of CXF when I used to be a Java developer. If the information in the blog post above is no longer needed, that’s great.

  10. Agnes says:

    Hi Justin,

    Thank you very much for the tutorial! It really helps a lot! I am struggling to create a web service client (cxf) with WSSE for days and never get it works.

    I generate a maven project just for the generated client from the CXF plugin. I create a separated maven web application project, using jsp to collect input and call the web service directly in the jsp (just for demo purpose). Without the web service security (username/password), it can be done easily. But with the WSSE (have to create callbackhandler), it is a totally different story.

    Can you give me some guidance?

    Here is the error I got when trying to call the web service in the jsp:

    exception

    org.apache.jasper.JasperException: javax.xml.ws.WebServiceException: org.apache.cxf.service.factory.ServiceConstructionException
    org.apache.jasper.servlet.JspServletWrapper.service(JspServletWrapper.java:413)
    org.apache.jasper.servlet.JspServlet.serviceJspFile(JspServlet.java:322)
    org.apache.jasper.servlet.JspServlet.service(JspServlet.java:249)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:717)
    org.jboss.web.tomcat.filters.ReplyHeaderFilter.doFilter(ReplyHeaderFilter.java:96)

    root cause

    javax.xml.ws.WebServiceException: org.apache.cxf.service.factory.ServiceConstructionException
    org.apache.cxf.jaxws.ServiceImpl.getPort(ServiceImpl.java:298)
    org.apache.cxf.jaxws.ServiceImpl.getPort(ServiceImpl.java:291)
    javax.xml.ws.Service.getPort(Service.java:44)
    client.AccountLookupServiceBean.lookupAccountings(AccountLookupServiceBean.java:64)
    org.apache.jsp.accountLookupResultSECCall_jsp._jspService(accountLookupResultSECCall_jsp.java:103)
    org.apache.jasper.runtime.HttpJspBase.service(HttpJspBase.java:70)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:717)
    org.apache.jasper.servlet.JspServletWrapper.service(JspServletWrapper.java:369)
    org.apache.jasper.servlet.JspServlet.serviceJspFile(JspServlet.java:322)
    org.apache.jasper.servlet.JspServlet.service(JspServlet.java:249)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:717)
    org.jboss.web.tomcat.filters.ReplyHeaderFilter.doFilter(ReplyHeaderFilter.java:96)

    root cause

    org.apache.cxf.service.factory.ServiceConstructionException
    org.apache.cxf.jaxb.JAXBDataBinding.initialize(JAXBDataBinding.java:337)
    org.apache.cxf.service.factory.ReflectionServiceFactoryBean.buildServiceFromClass(ReflectionServiceFactoryBean.java:467)
    org.apache.cxf.jaxws.support.JaxWsServiceFactoryBean.buildServiceFromClass(JaxWsServiceFactoryBean.java:550)
    org.apache.cxf.service.factory.ReflectionServiceFactoryBean.initializeServiceModel(ReflectionServiceFactoryBean.java:530)
    org.apache.cxf.service.factory.ReflectionServiceFactoryBean.create(ReflectionServiceFactoryBean.java:278)
    org.apache.cxf.jaxws.support.JaxWsServiceFactoryBean.create(JaxWsServiceFactoryBean.java:178)
    org.apache.cxf.jaxws.ServiceImpl.createPort(ServiceImpl.java:411)
    org.apache.cxf.jaxws.ServiceImpl.getPort(ServiceImpl.java:296)
    org.apache.cxf.jaxws.ServiceImpl.getPort(ServiceImpl.java:291)
    javax.xml.ws.Service.getPort(Service.java:44)
    client.AccountLookupServiceBean.lookupAccountings(AccountLookupServiceBean.java:64)
    org.apache.jsp.accountLookupResultSECCall_jsp._jspService(accountLookupResultSECCall_jsp.java:103)
    org.apache.jasper.runtime.HttpJspBase.service(HttpJspBase.java:70)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:717)
    org.apache.jasper.servlet.JspServletWrapper.service(JspServletWrapper.java:369)
    org.apache.jasper.servlet.JspServlet.serviceJspFile(JspServlet.java:322)
    org.apache.jasper.servlet.JspServlet.service(JspServlet.java:249)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:717)
    org.jboss.web.tomcat.filters.ReplyHeaderFilter.doFilter(ReplyHeaderFilter.java:96)

    root cause

    com.sun.xml.bind.v2.runtime.IllegalAnnotationsException: 1 counts of IllegalAnnotationExceptions
    Two classes have the same XML type name “{https://www.nih.gov/xmlns/financial/lookupprojects112007.wsdl/lookupProjectsImpl/Financials/Etravel}ReferenceType”. Use @XmlType.name and @XmlType.namespace to assign different names to them.
    this problem is related to the following location:
    at org.oasis_open.docs.wss._2004._01.oasis_200401_wss_wssecurity_secext_1_0.ReferenceType
    at public javax.xml.bind.JAXBElement org.oasis_open.docs.wss._2004._01.oasis_200401_wss_wssecurity_secext_1_0.ObjectFactory.createReference(org.oasis_open.docs.wss._2004._01.oasis_200401_wss_wssecurity_secext_1_0.ReferenceType)
    at org.oasis_open.docs.wss._2004._01.oasis_200401_wss_wssecurity_secext_1_0.ObjectFactory
    this problem is related to the following location:
    at org.w3._2000._09.xmldsig_.ReferenceType
    at public javax.xml.bind.JAXBElement org.w3._2000._09.xmldsig_.ObjectFactory.createReference(org.w3._2000._09.xmldsig_.ReferenceType)
    at org.w3._2000._09.xmldsig_.ObjectFactory

    com.sun.xml.bind.v2.runtime.IllegalAnnotationsException$Builder.check(IllegalAnnotationsException.java:102)
    com.sun.xml.bind.v2.runtime.JAXBContextImpl.getTypeInfoSet(JAXBContextImpl.java:472)
    com.sun.xml.bind.v2.runtime.JAXBContextImpl.(JAXBContextImpl.java:302)
    com.sun.xml.bind.v2.runtime.JAXBContextImpl$JAXBContextBuilder.build(JAXBContextImpl.java:1136)
    com.sun.xml.bind.v2.ContextFactory.createContext(ContextFactory.java:154)
    com.sun.xml.bind.v2.ContextFactory.createContext(ContextFactory.java:121)
    sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    java.lang.reflect.Method.invoke(Method.java:597)
    javax.xml.bind.ContextFinder.newInstance(ContextFinder.java:211)
    javax.xml.bind.ContextFinder.find(ContextFinder.java:372)
    javax.xml.bind.JAXBContext.newInstance(JAXBContext.java:574)
    org.apache.cxf.jaxb.JAXBDataBinding.createContext(JAXBDataBinding.java:560)
    org.apache.cxf.jaxb.JAXBDataBinding.createJAXBContextAndSchemas(JAXBDataBinding.java:500)
    org.apache.cxf.jaxb.JAXBDataBinding.initialize(JAXBDataBinding.java:320)
    org.apache.cxf.service.factory.ReflectionServiceFactoryBean.buildServiceFromClass(ReflectionServiceFactoryBean.java:467)
    org.apache.cxf.jaxws.support.JaxWsServiceFactoryBean.buildServiceFromClass(JaxWsServiceFactoryBean.java:550)
    org.apache.cxf.service.factory.ReflectionServiceFactoryBean.initializeServiceModel(ReflectionServiceFactoryBean.java:530)
    org.apache.cxf.service.factory.ReflectionServiceFactoryBean.create(ReflectionServiceFactoryBean.java:278)
    org.apache.cxf.jaxws.support.JaxWsServiceFactoryBean.create(JaxWsServiceFactoryBean.java:178)
    org.apache.cxf.jaxws.ServiceImpl.createPort(ServiceImpl.java:411)
    org.apache.cxf.jaxws.ServiceImpl.getPort(ServiceImpl.java:296)
    org.apache.cxf.jaxws.ServiceImpl.getPort(ServiceImpl.java:291)
    javax.xml.ws.Service.getPort(Service.java:44)
    client.AccountLookupServiceBean.lookupAccountings(AccountLookupServiceBean.java:64)
    org.apache.jsp.accountLookupResultSECCall_jsp._jspService(accountLookupResultSECCall_jsp.java:103)
    org.apache.jasper.runtime.HttpJspBase.service(HttpJspBase.java:70)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:717)
    org.apache.jasper.servlet.JspServletWrapper.service(JspServletWrapper.java:369)
    org.apache.jasper.servlet.JspServlet.serviceJspFile(JspServlet.java:322)
    org.apache.jasper.servlet.JspServlet.service(JspServlet.java:249)
    javax.servlet.http.HttpServlet.service(HttpServlet.java:717)
    org.jboss.web.tomcat.filters.ReplyHeaderFilter.doFilter(ReplyHeaderFilter.java:96)

  11. Agnes says:

    Hi Justin,

    Another queston is that, when do we use the jar-with-dependencies plug-in? In my web application, which plugin shall I use instead?

    Thanks,
    Agnes

  12. jeniffer says:

    HI!
    i want create the WSDL
    i have a project in netbeans whith maven and cfx.
    eclipse and netbeans in a normal project on click rigth button can generate the wsdl for publish a webservice,
    now… with maven not exist it option

    (DAH sorry for my english, but i speak spanish)
    can you help me?

    • Justin says:

      Hi Jeniffer, sorry I can’t really help. It’s been years since I’ve developed in Java, and I’ve never used NetBeans. With luck, perhaps someone else will see your message and reply with a suggestion.

  13. Selman says:

    Thanks. Good explanation

  14. Adeel Ahmad says:

    Thanks, it helped a lot.

  15. […] How to create a WSDL -first SOAP client in Java with … – Thank you very much for this! I have to create something similar and this is helping me =)… […]

  16. Rath says:

    Hi.

    I tried the above example. I get the following error: It throws the error from cxf file.

    org.xml.sax.SAXParseException: schema_reference.4: Failed to read schema document ‘http://www.springframework.org/schema/beans/spring-beans.xsd’, because 1) could not find the document; 2) the document could not be read; 3) the root element of the document is not .

    I tried with including spring dependency. Still doesn’t work. The spring jar is classpath. Any suggestions.

  17. Mamuka says:

    Hi guys

    there is no need to have wsdl attached as separate file in your project.
    you can use wsdl address in your pom.xml file .
    runs and gives result

    regards

  18. Mamuka says:

    nice tutorial , thanks

  19. Mamuka says:

    forecast date: January 8 2013
    it gives old result
    it is not OK

  20. Praveen says:

    Hi Justin,
    I am new to maven an dmy WSDL file containing xsd so in that case I am not able to generate java code at build time so please provide maven dependies for that.

    Thanks,
    Praveen

  21. Joseph Lin says:

    I spent a few days to google for a SOAP client sample to build from a downloaded WSDL. This is the only one that is easy to understand and really works !! Thanks so much.

  22. Hans Kruse says:

    TLDR; Thank you.

    Just wondering how spring dependent this. I want it to run in a Glassfish environment.

    I am a .NET developer wandering around the Duke side of the force for a year now
    I am Certified ASP.NET WCF etc an now looking for something in Java that does generate a proxy that understands “MessageContracts”. It seems that CXF does that. A lot on the Java webservice stack is still “Greek” to me (and I do understand some Greek).

    I like your solution for code generation. Now trying to get it to work with wshttpbindings with message security:( I confirmed the server does work by generating a working .NET client first. So I know there are no other issues.

    • Justin says:

      Hello Hans, thanks for your comment. Apologies, but I haven’t done any Java development in about 4 years now (nowadays I write iOS code in Swift). So I don’t know the answer to your question.

      You might want to try the official CXF mailing list (the mailing list also has a searchable archive, which you might want to check first before sending email to the CXF list).

      Good luck, I hope you find a solution.

Leave a Reply

Your email address will not be published. Required fields are marked *