About Siva Reddy

Katamreddy Siva Prasad is a Senior Software Engineer working in E-Commerce domain. His areas of interest include Object Oriented Design, SOLID Design principles, RESTful WebServices and OpenSource softwares including Spring, MyBatis and Jenkins.

Web Services with JAX-WS on Tomcat

Let us assume an enterprise is maintaining user authentication details in a centralized system. We need to create an AuthenticationService which will take credentials, validate them and return the status. The rest of the applications will use the AuthenticationService to authenticate the Users.









Create AuthenticationService interface as follows:

package com.sivalabs.caas.services;
import javax.jws.WebService;

import com.sivalabs.caas.domain.AuthenticationStatus;
import com.sivalabs.caas.domain.Credentials;
import com.sivalabs.caas.exceptions.AuthenticationServiceException;

@WebService
public interface AuthenticationService
{
public AuthenticationStatus authenticate(Credentials credentials) throws AuthenticationServiceException;
}
package com.sivalabs.caas.domain;
/**
 * @author siva
 *
 */
public class Credentials 
{
 private String userName;
 private String password;
 public Credentials() 
{
 }
 public Credentials(String userName, String password) {
  super();
  this.userName = userName;
  this.password = password;
 }
 //setters and getters
 
}
package com.sivalabs.caas.domain;

/**
 * @author siva
 *
 */
public class AuthenticationStatus
{
 private String statusMessage;
 private boolean success;
 //setters and getters
 
}
package com.sivalabs.caas.exceptions;

/**
 * @author siva
 *
 */
public class AuthenticationServiceException extends RuntimeException
{
 
 private static final long serialVersionUID = 1L;
 public AuthenticationServiceException()
 {
 }
 public AuthenticationServiceException(String msg)
 {
  super(msg);
 }
}

Now let us implement the AuthenticationService.

package com.sivalabs.caas.services;

import java.util.HashMap;
import java.util.Map;

import javax.jws.WebService;

import com.sivalabs.caas.domain.AuthenticationStatus;
import com.sivalabs.caas.domain.Credentials;
import com.sivalabs.caas.exceptions.AuthenticationServiceException;

/**
 * @author siva
 *
 */
@WebService(endpointInterface="com.sivalabs.caas.services.AuthenticationService",
   serviceName="AuthenticationService", 
   targetNamespace="http://sivalabs.blogspot.com/services/AuthenticationService")
public class AuthenticationServiceImpl implements AuthenticationService
{
 private static final Map<string, string> CREDENTIALS = new HashMap<string, string>();
 static
 {
  CREDENTIALS.put("admin", "admin");
  CREDENTIALS.put("test", "test");  
 }
 
 @Override
 public AuthenticationStatus authenticate(Credentials credentials) throws AuthenticationServiceException
 {
  if(credentials == null)
  {
   throw new AuthenticationServiceException("Credentials is null");
  }
  AuthenticationStatus authenticationStatus = new AuthenticationStatus();
  String userName = credentials.getUserName();
  String password = credentials.getPassword();
  
  if(userName==null || userName.trim().length()==0 || password==null || password.trim().length()==0)
  {
   authenticationStatus.setStatusMessage("UserName and Password should not be blank");
   authenticationStatus.setSuccess(false);
  }
  else
  {
   if(CREDENTIALS.containsKey(userName) && password.equals(CREDENTIALS.get(userName)))
   {
    authenticationStatus.setStatusMessage("Valid UserName and Password");
    authenticationStatus.setSuccess(true);
   }
   else
   {
    authenticationStatus.setStatusMessage("Invalid UserName and Password");
    authenticationStatus.setSuccess(false);
   }
  }
  return authenticationStatus;
 }
}

Here for simplicity we are checking the credentials against the static data stored in HashMap. In real applications this check will be done against database.

Now we are going to publish the WebService.

package com.sivalabs.caas.publisher;

import javax.xml.ws.Endpoint;

import com.sivalabs.caas.services.AuthenticationServiceImpl;

public class EndpointPublisher
{
 public static void main(String[] args)
 {
  Endpoint.publish("http://localhost:8080/CAAS/services/AuthenticationService", new AuthenticationServiceImpl());
 }

}

Run this standalone class to publish the AuthenticationService.

To check whether the Service published successfully point the browser to URL http://localhost:8080/CAAS/services/AuthenticationService?wsdl. If the service published successfully you will see the WSDL content.

Now let us create a Standalone test client to test the webservice.

package com.sivalabs.caas.client;

import java.net.URL;

import javax.xml.namespace.QName;
import javax.xml.ws.Service;

import com.sivalabs.caas.domain.AuthenticationStatus;
import com.sivalabs.caas.domain.Credentials;
import com.sivalabs.caas.services.AuthenticationService;

/**
 * @author siva
 *
 */
public class StandaloneClient
{

 public static void main(String[] args) throws Exception
 {
  URL wsdlUrl = new URL("http://localhost:8080/CAAS/services/AuthenticationService?wsdl");
  QName qName = new QName("http://sivalabs.blogspot.com/services/AuthenticationService", "AuthenticationService");
  Service service = Service.create(wsdlUrl,qName);
  AuthenticationService port = service.getPort(AuthenticationService.class);
  Credentials credentials=new Credentials();
  credentials.setUserName("admin1");
  credentials.setPassword("admin");
  AuthenticationStatus authenticationStatus = port.authenticate(credentials);
  System.out.println(authenticationStatus.getStatusMessage());
  
  credentials.setUserName("admin");
  credentials.setPassword("admin");
  authenticationStatus = port.authenticate(credentials);
  System.out.println(authenticationStatus.getStatusMessage());
 }

}

Instead of writing StandaloneClient by our-self we can generate the Client using wsimport commandline tool.

wsimport tool is there in JDK/bin directory.

Go to your project src directory and execute the following command.

wsimport -keep -p com.sivalabs.caas.client http://localhost:8080/CAAS/services/AuthenticationService?wsdl

It will generate the following java and class files in com.sivalabs.caas.client package.

Authenticate.java
AuthenticateResponse.java
AuthenticationService_Service.java
AuthenticationService.java
AuthenticationServiceException_Exception.java
AuthenticationServiceException.java
AuthenticationStatus.java
Credentials.java
ObjectFactory.java
package-info.java

Now you can use the generated Java files to test the Service.

public static void main(String[] args) throws Exception
{
  AuthenticationService_Service service = new AuthenticationService_Service();
  com.sivalabs.caas.client.AuthenticationService authenticationServiceImplPort = service.getAuthenticationServiceImplPort();
  com.sivalabs.caas.client.Credentials credentials = new com.sivalabs.caas.client.Credentials();
  
  credentials.setUserName("admin1");
  credentials.setPassword("admin");
  com.sivalabs.caas.client.AuthenticationStatus authenticationStatus = authenticationServiceImplPort.authenticate(credentials);
  System.out.println(authenticationStatus.getStatusMessage());
  
  credentials.setUserName("admin");
  credentials.setPassword("admin");
  authenticationStatus = authenticationServiceImplPort.authenticate(credentials);
  System.out.println(authenticationStatus.getStatusMessage());
}

Now we are going to see how to deploy JAX-WS WebService on Tomcat Server.

We are going to deploy The AuthenticationService developed in http://sivalabs.blogspot.com/2011/09/developing-webservices-using-jax-ws.html on apache-tomcat-6.0.32.

To deploy our AuthenticationService we need to add the following configuration.

1.web.xml

<web-app>
 <listener>
  <listener-class>com.sun.xml.ws.transport.http.servlet.WSServletContextListener</listener-class>
 </listener>
 
 <servlet>
  <servlet-name>authenticationService</servlet-name>
  <servlet-class>com.sun.xml.ws.transport.http.servlet.WSServlet</servlet-class>
  <load-on-startup>1</load-on-startup>
 </servlet>
 <servlet-mapping>
  <servlet-name>authenticationService</servlet-name>
  <url-pattern>/services/AuthenticationService</url-pattern>
 </servlet-mapping>
</web-app> 

2. Create a new file WEB-INF/sun-jax-ws.xml

<?xml version="1.0" encoding="UTF-8"?>
<endpoints
  xmlns="http://java.sun.com/xml/ns/jax-ws/ri/runtime"
  version="2.0">
  
  <endpoint
      name="AuthenticationService"
      implementation="com.sivalabs.caas.services.AuthenticationServiceImpl"
      url-pattern="/services/AuthenticationService"/>
      
</endpoints>

3. Download the JAX-WS Reference Implementation from http://jax-ws.java.net/

Copy all the jar files from jaxws-ri/lib folder to WEB-INF/lib.

Now deploy the application on Tomcat server.
You don’t need to publish the Service by our-self as we did using EndpointPublisher.
Once the tomcat is up and running see the generated wsdl at http://localhost:8080/CAAS/services/AuthenticationService?wsdl.

Now if you test the AuthenticationService using standalone client it will work fine.

public static void testAuthenticationService()throws Exception
{
  URL wsdlUrl = new URL("http://localhost:8080/CAAS/services/AuthenticationService?wsdl");
  QName qName = new QName("http://sivalabs.blogspot.com/services/AuthenticationService", "AuthenticationService");
  Service service = Service.create(wsdlUrl,qName);
  AuthenticationService port = service.getPort(AuthenticationService.class);
  Credentials credentials=new Credentials();
  credentials.setUserName("admin");
  credentials.setPassword("admin");
  AuthenticationStatus authenticationStatus = port.authenticate(credentials);
  System.out.println(authenticationStatus.getStatusMessage());
}

But if you try to test with the wsimport tool generated client code make sure that you dont have jax-ws-ri jars in Client classpath.

Otherwise you will get the below error:

Exception in thread "main" java.lang.NoSuchMethodError: javax.xml.ws.WebFault.messageName()Ljava/lang/String;
 at com.sun.xml.ws.model.RuntimeModeler.processExceptions(RuntimeModeler.java:1162)
 at com.sun.xml.ws.model.RuntimeModeler.processDocWrappedMethod(RuntimeModeler.java:898)

Reference: Developing WebServices using JAX-WS & Deploying JAX-WS WebService on Tomcat-6 from our JCG partner Siva Reddy at the My Experiments on Technology blog.

Related Whitepaper:

Functional Programming in Java: Harnessing the Power of Java 8 Lambda Expressions

Get ready to program in a whole new way!

Functional Programming in Java will help you quickly get on top of the new, essential Java 8 language features and the functional style that will change and improve your code. This short, targeted book will help you make the paradigm shift from the old imperative way to a less error-prone, more elegant, and concise coding style that’s also a breeze to parallelize. You’ll explore the syntax and semantics of lambda expressions, method and constructor references, and functional interfaces. You’ll design and write applications better using the new standards in Java 8 and the JDK.

Get it Now!  

2 Responses to "Web Services with JAX-WS on Tomcat"

  1. disqus_PAlG3PY2Eh says:

    is the password sent unencrypted? how prevent?

  2. Nilesh says:

    Hi

    I was able to run the webservice from the eclipse but facing problem when the same gets deployed on TOMCAT can u please help me on this .. i m getting below error..

    Exception in thread “main” javax.xml.ws.WebServiceException: Failed to access the WSDL at: http://localhost:9001/CAAS/services/AuthenticationService?wsdl. It failed with:

    http://localhost:9001/CAAS/services/AuthenticationService?wsdl.

    at com.sun.xml.ws.wsdl.parser.RuntimeWSDLParser.tryWithMex(RuntimeWSDLParser.java:252)

    at com.sun.xml.ws.wsdl.parser.RuntimeWSDLParser.parse(RuntimeWSDLParser.java:229)

    at com.sun.xml.ws.wsdl.parser.RuntimeWSDLParser.parse(RuntimeWSDLParser.java:192)

    at com.sun.xml.ws.wsdl.parser.RuntimeWSDLParser.parse(RuntimeWSDLParser.java:161)

    at com.sun.xml.ws.client.WSServiceDelegate.parseWSDL(WSServiceDelegate.java:328)

    at com.sun.xml.ws.client.WSServiceDelegate.(WSServiceDelegate.java:290)

    at com.sun.xml.ws.client.WSServiceDelegate.(WSServiceDelegate.java:217)

    at com.sun.xml.ws.client.WSServiceDelegate.(WSServiceDelegate.java:199)

    at com.sun.xml.ws.client.WSServiceDelegate.(WSServiceDelegate.java:195)

    at com.sun.xml.ws.spi.ProviderImpl.createServiceDelegate(ProviderImpl.java:112)

    at javax.xml.ws.Service.(Service.java:57)

    at javax.xml.ws.Service.create(Service.java:687)

    at com.sivalabs.caas.client.StandaloneClient.callWebserviceBySkeleton(StandaloneClient.java:47)

    at com.sivalabs.caas.client.StandaloneClient.main(StandaloneClient.java:15)

    Caused by: java.io.FileNotFoundException: http://localhost:9001/CAAS/services/AuthenticationService?wsdl

    at sun.net.www.protocol.http.HttpURLConnection.getInputStream(Unknown Source)

    at java.net.URL.openStream(Unknown Source)

    at com.sun.xml.ws.wsdl.parser.RuntimeWSDLParser.createReader(RuntimeWSDLParser.java:994)

    at com.sun.xml.ws.wsdl.parser.RuntimeWSDLParser.resolveWSDL(RuntimeWSDLParser.java:395)

    at com.sun.xml.ws.wsdl.parser.RuntimeWSDLParser.parse(RuntimeWSDLParser.java:214)

    … 12 more

Leave a Reply


− 5 = one



Java Code Geeks and all content copyright © 2010-2014, Exelixis Media Ltd | Terms of Use | Privacy Policy
All trademarks and registered trademarks appearing on Java Code Geeks are the property of their respective owners.
Java is a trademark or registered trademark of Oracle Corporation in the United States and other countries.
Java Code Geeks is not connected to Oracle Corporation and is not sponsored by Oracle Corporation.

Sign up for our Newsletter

20,709 insiders are already enjoying weekly updates and complimentary whitepapers! Join them now to gain exclusive access to the latest news in the Java world, as well as insights about Android, Scala, Groovy and other related technologies.

As an extra bonus, by joining you will get our brand new e-books, published by Java Code Geeks and their JCG partners for your reading pleasure! Enter your info and stay on top of things,

  • Fresh trends
  • Cases and examples
  • Research and insights
  • Two complimentary e-books