In this blog I’ll show you how you can create a WebService of your EJB3 objects by using anotations. I will also show you how to build and deploy the package with Maven2. Let’s start with the initial situation.
I have installed JBoss 4.2.1 and Maven2. In my settings.xml of Maven2 I have set a property pointing to my JBoss installation and I have defined a JBoss/Maven2 repository.
The settings.xml file looks like this:
<settings> <localRepository>d:/maven2/repo/</localRepository> <profiles> <profile> <id>default-repositories</id> <repositories> <repository> <id>global</id> <name>External Mirror of Central Repository</name> <url>http://repo1.maven.org/maven2</url> </repository> <repository> <id>repo.maven</id> <url>http://repo1.maven.org/maven2-repoclean-java.net</url> </repository> <repository> <id>jboss.maven</id> <url>http://repository.jboss.com/maven2/</url> </repository> </repositories> <pluginRepositories> <pluginRepository> <id>repo1org</id> <name>External Plugin Repository</name> <url>http://repo1.maven.org/maven2/</url> </pluginRepository> </pluginRepositories> </profile> <profile> <id>property-overrides</id> <properties> <jboss.home>C:\java\jboss-4.2.1.GA</jboss.home> </properties> </profile> </profiles> <activeProfiles> <activeProfile>property-overrides</activeProfile> <activeProfile>default-repositories</activeProfile> </activeProfiles> </settings>
Lateron we’ll see that Maven uses the JBoss plugin and the property for the deployment of our application.
I have created a project ‘my-ejb-project’ with a simple EJB session bean. The bean (and it’s interface) looks like this:
package net.pascalalma.services; import javax.ejb.Remote; @Remote public interface EchoService { public String sayHello(String subject); }
and the implementation:
package net.pascalalma.services.impl; import javax.ejb.Stateless; import net.pascalalma.services.EchoService; @Stateless public class EchoServiceBean implements EchoService { public String sayHello(String name) { return "Hi " + name + "!"; } }
To build this project I have this in the project’s pom.xml file:
<?xml version="1.0" encoding="UTF-8"?> <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>net.pascalalma</groupId> <artifactId>my-ejb-project</artifactId> <version>1.0</version> <packaging>ejb</packaging> <build> <sourceDirectory>src/main/java</sourceDirectory> <finalName>my-ejb-project</finalName> <plugins> <plugin> <artifactId>maven-compiler-plugin</artifactId> <configuration> <source>1.5</source> <target>1.5</target> </configuration> </plugin> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-javadoc-plugin</artifactId> <configuration> <classpath>/src/main/java</classpath> </configuration> </plugin> <plugin> <artifactId>maven-ejb-plugin</artifactId> <configuration> <ejbVersion>3.0</ejbVersion> <archive> <manifest> <addClasspath>true</addClasspath> </manifest> </archive> </configuration> </plugin> </plugins> </build> <dependencies> <dependency> <groupId>org.apache.geronimo.specs</groupId> <artifactId>geronimo-jpa_3.0_spec</artifactId> <version>1.1</version> <scope>provided</scope> </dependency> <dependency> <groupId>org.apache.geronimo.specs</groupId> <artifactId>geronimo-ejb_3.0_spec</artifactId> <version>1.0</version> <scope>provided</scope> </dependency> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>4.1</version> <scope>test</scope> </dependency> </dependencies> <reporting> <plugins> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-surefire-report-plugin</artifactId> </plugin> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-jxr-plugin</artifactId> </plugin> </plugins> </reporting> </project>
Besides this ejb-project I have also created a ear-project that is used to create an ear file containing the EJB’s jar file (and optionally other deliverables like war-file etc). The pom file of this project looks like (the project doesn’t contain anything else):
<?xml version="1.0" encoding="UTF-8"?> <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>net.pascalalma</groupId> <artifactId>my-ear-project</artifactId> <packaging>ear</packaging> <version>1.0</version> <name>my-ear-project</name> <dependencies> <dependency> <groupId>net.pascalalma</groupId> <artifactId>my-ejb-project</artifactId> <version>1.0</version> <type>ejb</type> </dependency> </dependencies> <build> <plugins> <plugin> <groupId>org.codehaus.mojo</groupId> <artifactId>jboss-maven-plugin</artifactId> <configuration> <jbossHome>${jboss.home}</jbossHome> <serverName>default</serverName> <port>8080</port> </configuration> </plugin> <plugin> <artifactId>maven-ear-plugin</artifactId> <configuration> <displayName>My EJB Component</displayName> <description>My EJB Component</description> <version>1.4</version> <modules> <ejbModule> <groupId>net.pascalalma</groupId> <artifactId>my-ejb-project</artifactId> </ejbModule> </modules> </configuration> </plugin> </plugins> </build> </project>
With all this in place we are able to build the EJB3 project with the command:
c:\workspace\my-ejb-project\mvn clean install
and to package and deploy the EAR project with:
c:\workspace\my-ear-project\mvn clean package jboss:harddeploy
To make our EJB3 bean available as a webservice, we have to add some annotations to the source, so the code of the interface and the bean will become something like this:
package net.pascalalma.services; import javax.ejb.Remote; import javax.jws.WebService; @Remote @WebService() public interface EchoService { public String sayHello(String subject); }
and the implementation class:
package net.pascalalma.services.impl; import javax.ejb.Stateless; import javax.jws.WebService; import javax.jws.soap.SOAPBinding; import net.pascalalma.services.EchoService; @Stateless @WebService(endpointInterface = "net.pascalalma.services.EchoService",serviceName="EchoService") @SOAPBinding(style = javax.jws.soap.SOAPBinding.Style.DOCUMENT) public class EchoServiceBean implements EchoService { @javax.jws.WebMethod() public String sayHello(String name) { return "Hi " + name + "!"; } }
That’s it! The only thing left is that we have to add a new dependency to the pom (for the javax.jws.*). The dependency looks like:
<dependency> <groupId>xfire</groupId> <artifactId>xfire-jsr181-api</artifactId> <version>1.0-M1</version> <scope>provided</scope> </dependency>
As you can see the dependency has the scope ‘provided’ because the library is already available in JBoss, so we don’t want to package it in our jar file.
Now rebuild and redeploy the packages and it is done!
To test the webservice I use my favorite tool ‘Soap UI‘. We can generate the necessary WSDL at runtime by going to the url: ‘http://127.0.0.1:8080/EchoServiceBeanService/EchoServiceBean?wsdl’. The result in SOAP UI looks like this:
After sending the request we will get this respone:
I hope this post makes clear that is easy to make your EJB3 session beans available as a webservice, by simply adding some annotations to your code.
If you get the next error while trying to invoke your webservice:
“ERROR [SOAPFaultHelperJAXWS] SOAP request exception
java.lang.UnsupportedOperationException: setProperty must be overridden by all subclasses of SOAPMessage”, then use jdk1.5 instead of jdk1.6 for JBoss. See: http://www.jboss.org/?module=bb&op=viewtopic&p=4020868
Hi, there. Is there a way to have Maven 2 deploy the EJB JAR itself, without having to package it as part of an EAR? Been trying the JBoss Maven Plugin but with my packaging set to “ejb” it attempts to deploy “project-0.1.ejb” (which, of course, doesn’t exist).
I get the following error :
[java] Exception in thread “main” org.jboss.ws.WSException: Cannot obtain java type mapping for: …
any clue whats going on ?
Congratulations, very nice and simple article. I managed to make a web service endpoint in 5-10 minutes using the listings in this article.
A continuation of this article would also be great. One that helps us build a web service client and using complex types.
Hi, thx for your comment! Always nice to see my efforts are appreciated 🙂
About the web client, I have got these articles for you:
http://www.pascalalma.net/2007/05/18/creating-a-webservice-client-with-xfire/
and, if you just want a client to test your service:
http://www.pascalalma.net/2007/05/23/using-soapui-for-testing-your-webservice/
I hope this helps.
Hey do you know why i am getting below error while i am trying to run my client programme.
Cannot obtain java type mapping
canany one solve please mail me the solution
Hi Revanth,
Is this still an issue? I found this post at the JBoss forum. It seems to be a problem with the client program that does not understand the JSR-181
I get the following error when jboss running:
DEPLOYMENTS IN ERROR:
Deployment “vfszip:/C:/java/jboss/server/default/deploy/my-ear-project-1.0.ear
/” is in error due to the following reason(s): javax.wsdl.WSDLException: WSDLExc
eption: faultCode=CONFIGURATION_ERROR: Unsupported Java encoding for writing wsd
l file: ‘Cp1252’.
Is very important i know why!!!!Im spanish. Thank you.
It’s clear it got something to do with encoding. It seams that the following could help:
“We succeded in deploying the sample and running the tests after modifying the JAVA_OPT in run.sh in order to set the VM default encoding ( -Dfile.encoding=ISO-8859-1 )”
Make sure that the encoding in your WSDL and/or XSD are set to a ‘valid’ value like ‘UTF-8’.
Hope this helps.
The problem is that i run jboss in windows. I want change the parameter’s run -Dsun.jnu.encoding=UTF-8 -Dfile.encoding=UTF-8 but i don´t change when running jboss. do you want running jboss changing this configuration?
Thank you
Hello, add the parameters -Dsun.jnu.encoding=UTF-8 -Dfile.encoding=UTF-8 in rut.bat is ok in jboss for compile ear corretly. Thank. But Now i have other problem, this:
org.jboss.ws.WSException: java.lang.UnsupportedOperationException: setProperty must be overridden by all subclasses of SOAPMessage
Do you Know this problem?
Thanks.
Hello, is all ok. But i dont can to work with soapUI:
java.lang.NoClassDefFoundError: org/jboss/util/id/SerialVersion
at javax.xml.soap.SOAPException.(SOAPException.java:36)
at javax.xml.soap.SAAJMetaFactory.getInstance(SAAJMetaFactory.java:64)
at javax.xml.soap.SOAPFactory.newInstance(SOAPFactory.java:74)
at org.jboss.ws.core.soap.SOAPFactoryImpl.createElement(SOAPFactoryImpl.java:121)
at org.jboss.ws.core.soap.EnvelopeBuilderDOM.build(EnvelopeBuilderDOM.java:136)
at org.jboss.ws.core.soap.EnvelopeBuilderDOM.build(EnvelopeBuilderDOM.java:96)
at org.jboss.ws.core.soap.MessageFactoryImpl.createMessage(MessageFactoryImpl.java:294)
at org.jboss.ws.core.soap.MessageFactoryImpl.createMessage(MessageFactoryImpl.java:193)
at org.jboss.wsf.stack.jbws.RequestHandlerImpl.processRequest(RequestHandlerImpl.java:455)
at org.jboss.wsf.stack.jbws.RequestHandlerImpl.handleRequest(RequestHandlerImpl.java:295)
at org.jboss.wsf.stack.jbws.RequestHandlerImpl.doPost(RequestHandlerImpl.java:205)
at org.jboss.wsf.stack.jbws.RequestHandlerImpl.handleHttpRequest(RequestHandlerImpl.java:131)
at org.jboss.wsf.common.servlet.AbstractEndpointServlet.service(AbstractEndpointServlet.java:85)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:717)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
at org.jboss.web.tomcat.filters.ReplyHeaderFilter.doFilter(ReplyHeaderFilter.java:96)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:235)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:191)
at org.jboss.web.tomcat.security.SecurityAssociationValve.invoke(SecurityAssociationValve.java:190)
at org.jboss.web.tomcat.security.JaccContextValve.invoke(JaccContextValve.java:92)
at org.jboss.web.tomcat.security.SecurityContextEstablishmentValve.process(SecurityContextEstablishmentValve.java:126)
at org.jboss.web.tomcat.security.SecurityContextEstablishmentValve.invoke(SecurityContextEstablishmentValve.java:70)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127)
at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102)
at org.jboss.web.tomcat.service.jca.CachedConnectionValve.invoke(CachedConnectionValve.java:158)
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:330)
at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:829)
at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:598)
at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:447)
at java.lang.Thread.run(Thread.java:619)
Now Its all ok.
Hi Jose,
Good to see your problems are solved.
And if you need more info about the use of SoapUI see our other posts about soapUI here:
https://pragmaticintegrator.wordpress.com/tag/soap-ui/