tutorial
4 pages
English
Le téléchargement nécessite un accès à la bibliothèque YouScribe
Tout savoir sur nos offres
4 pages
English
Le téléchargement nécessite un accès à la bibliothèque YouScribe
Tout savoir sur nos offres

Description

LeSCWiki . Internal . WebServiceTutorialJ2EE Web Service TutorialThe tutorial will equip you with the knowledge to start writing web services and client in a J2EE environment. It will guide you through the process of setting up yourdevelopment environment, understanding a WSDL document and its relationship with SOAP and the Java API to use to write a Web Service and client.RequirementsThe following software must be installedJ2EE SDK (a.k.a. Sun Application Server v.8) - Download the "All-in-one" bundle from the Java website. Install the package by following the on-screen instruction.After installation, add J2EE_HOME/bin to your PATH environment to gain instant access to the J2EE tools. Please ensure your CLASSPATH environment is not set. Tocheck your system is setup correctly, run[me@mybox ~]$ wscompile -versionJAX-RPC Standard Implementation (1.1.1, build R5)Apache ANT 1.6 or above - Download the Ant tool from Apache. Please ensure the ANT_HOME points to the right Ant directory, and ANT_HOME/bin is at thebeginning of your PATH to make sure you are not using other one. To check (version must be equal or greater than 1.6+),[wwhl@mybox ~]$ ant -versionApache Ant version 1.6.1 compiled on February 12 2004PreparationIn order to help you packaging up your service, an Ant script has been prepared for you. The Ant script utilises the ICENI build system and the ICENI wsdl-to-java Antplugin, which is used in the Markets Project and WS-JDML. It should take away ...

Informations

Publié par
Nombre de lectures 15
Langue English

Extrait

LeSCWiki . Internal .
WebServiceTutorial
J2EE Web Service Tutorial
The tutorial will equip you with the knowledge to start writing web services and client in a J2EE environment. It will guide you through the process of setting up your
development environment, understanding a WSDL document and its relationship with SOAP and the Java API to use to write a Web Service and client.
Requirements
The following software must be installed
J2EE SDK (a.k.a. Sun Application Server v.8)
- Download the "All-in-one" bundle from the
Java website
. Install the package by following the on-screen instruction.
After installation, add J2EE_HOME/bin to your PATH environment to gain instant access to the J2EE tools. Please ensure your CLASSPATH environment is not set. To
check your system is setup correctly, run
[me@mybox ~]$ wscompile -version
JAX-RPC Standard Implementation (1.1.1, build R5)
Apache ANT 1.6 or above
- Download the Ant tool from
Apache
. Please ensure the ANT_HOME points to the right Ant directory, and ANT_HOME/bin is at the
beginning of your PATH to make sure you are not using other one. To check (version must be equal or greater than 1.6+),
[wwhl@mybox ~]$ ant -version
Apache Ant version 1.6.1 compiled on February 12 2004
Preparation
In order to help you packaging up your service, an Ant script has been prepared for you. The Ant script utilises the ICENI build system and the ICENI wsdl-to-java Ant
plugin, which is used in the Markets Project and WS-JDML. It should take away most of the burden of building and packaging your code.
Download the tutorial materials
here
tar zxvf tutorial.tar.gz
to TUTORIAL_HOME
From now on, all file references are relative to TUTORIAL_HOME unless indicated.
Various documents that you will might find useful
J2EE API Javadocs
J2SE API Javadocs
If you don't want to install J2EE Developer Kit, then use the one in /homes/wwhl/j2ee/appserver
Tutorial Task - Bulletin Board Service
In this tutorial, we will build a bulletin board service where any client can post, retrieve and search for messages. The tutorial will demonstrate
Top-down Approach - Write a WSDL interface and generate the Java artefacts
Implement a JAX-RPC service
Use the
javax.xml.rpc.server.ServletEndpointContext
for light-weight state management
Write a service client as a
JUnit TestCase
with the JAX-RPC client-side API
Task 1 - Warming up
Assuming you have downloaded the tutorial package and all the pre-requisites have been satisfied, you are ready to perform your first build and deployment
[me@mybox ~]$ cd ${TUTORIAL_HOME}
[me@mybox tutorial]$ ant
The build process should have now produced a distributable at ${TUTORIAL_HOME}/build/dist/tutorial-1.0/tutorial/ (just like any other ICENI module). The
wars
directory
contains a
Web Application aRchive
(essentially a jar file) containing all the deployable classes, libraries and deployment descriptors, etc.. Take a look at the content of the
.war.
[me@mybox wars]$ jar tvf bulletinboard.war
.
|-- META-INF
|
`-- MANIFEST.MF
|-- WEB-INF
|
|-- bulletinboard.mapping.xml
|
|-- lib
|
|
`-- tutorial.jar
|
|-- web.xml
|
|-- webservices.xml
|
`-- wsdl
|
|-- bulletinboard-interface.wsdl
|
`-- bulletinboard-service.wsdl
|-- images
|
`-- borders
|
|-- bottom.gif
|
|-- bottomleft.gif
|
|-- bottomright.gif
|
|-- left.gif
|
|-- right.gif
|
|-- top.gif
|
|-- topleft.gif
|
`-- topright.gif
|-- index.jsp
`-- style
`-- style.css
7 directories, 17 files
J2EE dictates the directory structure of a
war
file.
/WEB-INF/web.xml
: The main web application deployment descriptor
/WEB-INF/webservices.xml
: The web services deployment descriptor references named servlet in
web.xml
/WEB-INF/lib/
: Directory containing all the jar files (including your own classes) that your application needs.
/WEB-INF/wsdl/*.wsdl
: Directory containing all your WSDLs and XSDs. The location of these files are referenced in the
webservices.xml
file.
/WEB-INF/*mapping.xml
: JAX-RPC XSD-to-Java Mapping. This file is generated by the build process. It is referenced in the
webservices.xml
file.
/*
: Contains any .jsp, .html, etc.. that are served along with your web service.
Once you
war
file is built, you are ready to deploy it to a local/remote server. You can
hot-deploy
your application, meaning you don't have to reboot the server (very very
rarely...). If you application keeps the state in the session object or persisted to a JDBC database, your application is back to the same state as it was before the redeployment.
More on state later!
To deploy your
war
,
[me@mybox wars]$ asadmin deploy --host willow.doc.ic.ac.uk --port 55554 \
--user tutorial --password tutorial \
--name ${yourname} --contextroot ${yourname} bulletinboard.war
Unable to read system environment. No system environment will be used.
Command deploy executed successfully.
The --name and --context parameters are optional. They are there to force a different context path and application name to the default (= the name of the war) so that you are
not messing up with other's deployment.
To check whether your service is up-and-running, browse
http://willow.doc.ic.ac.uk:55555/${yourname}/
I'm so kind to have prepared this web client for you to test your service. You can type in an alternative URL to test your mate's service!
Just a few house-keeping hints,
To undeploy your service,
[me@mybox wars]$ asadmin undeploy --host willow.doc.ic.ac.uk --port 55554 \
--user tutorial --password tutorial ${yourname}
To inspect the log of the container,
[me@mybox wars]$ tail -f ${DOMAIN_DIR}/logs/server.log
${YOUR_DOMAIN} is the directory of the server domain. To access the server log on willow, you need to ssh to willow.doc.ic.ac.uk and the ${DOMAIN_DIR} is
~wwhl/j2ee/appserver/domains/willow.doc.ic.ac.uk/. If you are using your own server, the default location is in ${J2EE_HOME}/domains/${YOUR_DOMAIN}/.
To create your own server on your system,
[me@mybox wars]$ asadmin create-domain --adminport ${YOUR_ADMIN_PORT} --adminuser ${ADMIN_USER} --adminpassword ${ADMIN_PASSWORD} --instanceport ${H
To start/stop the domain,
[me@mybox wars]$ asadmin start-domain ${DOMAIN_NAME}
[me@mybox wars]$ asadmin stop-domain ${DOMAIN_NAME}
You can configure a started domain by browsing
http://${YOUR_HOST}:${YOUR_ADMIN_PORT/
OK! Enough warm up! Let's write some code!
Task 2 - Writing the WSDL interface
A skeleton WSDL can be found at etc/wsdl/bulletinboard-service.wsdl, which references etc/wsdl/bulletinboard-interface.wsdl. It contains the
post
and
get
operations. In this
task, you need to extend the interface with a new operation
search
, which takes a list of xsd:string as search keywords. The service should return a type:MessagesType
containing all the messages whose content contains any of the supplied keywords. It is recommended to use the following XSD type as the parameter for the
search
operation
<complexType name="SearchCriteriaType">
<sequence>
<element name="keyword" type="xsd:string" minOccurs="1" maxOccurs="unbounded"/>
</sequence>
</complexType>
Once you are happy with the WSDL, run
ant
again to see whether your WSDL is valid and the generated stubs would be rebuilt.
It's time to familiarise yourself with the build files.
build.xml
: plain old build script used in any ICENI module
build.prebuild.xml
: This script is run before the
compile
target is called in
build.xml
. The crux of the script contains the following action, which takes
the bulletin-board-service.wsdl file and creates all the Java client and interface artefacts for you. The nested
namespaceMapping
provides you with finer control to the Java
packages used by the generated classes. The other attributes are fairly self-explanatory. At the end of the prebuild process, you should find a set of new classes generated in
the
build/javagen-nc/
directory (nc stands for 'not compiled', they are there for your reference)
<wsdl-to-java vendor="sun" wsdl="${basedir}/etc/wsdl/bulletinboard-service.wsdl"
generate="interface,client"
outputdir="${basedir}/build/classes"
javaoutputdir="${basedir}/build/javagen-nc"
package="org.icenigrid.tutorial.bulletinboard"
mappingfile="${basedir}/build/bulletinboard.mapping.xml"
unless="ws.uptodate">
<namespaceMapping namespace="urn:lesc:tutorial:type"
package="org.icenigrid.tutorial.bulletinboard.type"/>
</wsdl-to-java>
build.postbuild.xml
: The script is called after the
build
target is called in
build.xml
. This script is responsible for generating the
war
file by using ANT's
war
action.
<war destfile="${build.path}/wars/bulletinboard.war"
webxml="${basedir}/etc/descriptor/web.xml"
>
<!-- the WEB-INF directory -->
<webinf file="${basedir}/etc/descriptor/webservices.xml"/>
<webinf file="${basedir}/build/bulletinboard.mapping.xml"/>
<!-- the WEB-INF/wsdl directory -->
<zipfileset dir="${basedir}/etc/wsdl" prefix="WEB-INF/wsdl"/>
<!-- the WEB-INF/lib directory -->
<lib dir="${build.path}/lib">
<include name="tutorial.jar"/>
</lib>
<!-- the root -->
<fileset dir="${basedir}/src/jsp"/>
</war>
Hopefully, by the end of this task, you will know how to edit the WSDL document and the build scripts to add your own service.
Task 3 - Implementing the
BulletinBoard
?
service
Implementing a Web Service in JAX-RPC is just like implementing an interface in Java. In the previous task, you have generated a set of interfaces and support classes from
the WSDL document. An implementation class is simply a class implementing the exposed interface, in this case
org.icenigrid.tutorial.bulletinboard.service.BulletinBoardPortType
A skeleton implementation is provided in src/java/org/icenigrid/tutorial/bulletinboard/service/DefaultBulletinBoardPortTypeImpl.java, it is recommended that you write your
own in a different class. Remember that if you have implemented a different class, you need to update
etc/descriptor/web.xml
to reflect the change in class name.
...
<servlet>
<servlet-name>BulletinBoardServletEndpoint</servlet-name>
<servlet-class>org.icenigrid.tutorial.bulletinboard.service.DefaultBulletinBoardPortTypeImpl</servlet-class>
</servlet>
...
There are a few gotchas in writing JAX-RPC web service
You should not use any member variables to store the state of your service.
Instantiation of your class is controlled by the container. You don't know how/when your instantiation is created.
Your service might be clustered. Let the container manage the state persistence through EJB or session replication.
If you want to be notified at certain critical point during the lifetime of your service class, implements the additional interface
javax.xml.rpc.server.ServiceLifecycle
.
The
init(Object)
method allows you to obtain a context object from which you can talk to the container. You need to cast it to
javax.xml.rpc.server.ServletEndpointContext
. This is useful for storing temporary state, however, you are still advised to use other means for storing states for
maximum fail-over and scalability.
Task 4 - Writing a Web Service Client in a JUnit
TestCase
?
JUnit provides a valuable tool for testing Java application. It's easy to set up and integrate well with the build process. All our existing build scripts contain the
test
ant target,
which runs all the junit.framework.TestCase defined in your source.
[me@mybox wars]$ ant test [-Dadditional.param=value ....]
In the case of testing a web service, we simply pass the service endpoint URL as an Ant parameter (i.e. -
Dservice.endpoint.url=http://willow.doc.ic.ac.uk:55555/${YOUR_NAME}/service).
A test case is defined as a class that extends junit.framework.TestCase, e.g.
public class MyTestCase extends junit.framework.TestCase {
public MyTestCase(String args){
super(args);
}
...
...
}
Each method in the test case class with the following signature (void, name starts with "test") represents a test in the test suite.
public void testXYZ() {
... test code ...
}
In order to assert
what you expect
from a piece of code, such as the return value of a method call, etc.., you use the assertXYZ() methods defined in the
TestCase
?
class to do
just that. For example, to test whether Java's "+" operation actually works as what you expect, you do
public void testJavaAddition() {
int a = 1 + 2;
assertEquals("sum", 3, a);
}
Enough on JUnit, now let's turn to Web Service Client,
In JAX-RPC, the client-side API is available in the package
javax.xml.rpc
. The general way of obtaining a service stub is as follow
import javax.xml.rpc.ServiceFactory;
import javax.xml.rpc.Stub;
import org.icenigrid.tutorial.bulletinboard.*;
..
// obtain a impl. specific service factory. This allows different vendor to provide different
// JAX-RPC runtime implementation
ServiceFactory xFactory = ServiceFactory.newInstance();
// obtain the service stub
BulletinBoardService xService = (BulletinBoardService)xFactory.loadService(BulletinBoardService.class);
// obtain the port stub
BulletinBoardPortType xPort = xService.getBulletinBoardSOAPPort();
// setup stub properties
((Stub)xPort)._setProperty(Stub.ENDPOINT_ADDRESS_PROPERTY, "http://host:port/myservice/endpoint");
// call service method
xPort.post(....);
The JAX-RPC client API has hidden the details of SOAP and HTTP from you, therefore your code simply looks like it's calling some local object.
Now, your task is to write a testcase to test your
find
method.
-- Main.wwhl - 15 Aug 2004
J2EEWebServiceTutorial.pdf
: Tutorial Presentation
tutorial.tar.gz
: Tutorial Package
Attachment
:
Action: Size:
Date:
Who:
Comment:
J2EEWebServiceTutorial.pdf action
1049529 19 Aug 2004 - 10:25 Main.wwhl Tutorial Presentation
tutorial.tar.gz
action
5256807 19 Aug 2004 - 11:05 Main.wwhl Tutorial Package
tutorial-completed.tar.gz
action
5565050 24 Aug 2004 - 16:35 Main.wwhl
-----
Revision r1.4 - 24 Aug 2004 - 16:35 GMT - Main.wwhl
Copyright © 1999-2003 by the contributing authors. All material on this collaboration platform is the property of the contributing authors.
Ideas, requests, problems regarding LeSCWiki?
Send
feedback.
  • Univers Univers
  • Ebooks Ebooks
  • Livres audio Livres audio
  • Presse Presse
  • Podcasts Podcasts
  • BD BD
  • Documents Documents