| <?xml version="1.0" encoding=""?> |
| <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en"> |
| <head> |
| <meta http-equiv="content-type" content="" /> |
| <title>Introducing Axis2</title> |
| <link href="../css/axis-docs.css" rel="stylesheet" type="text/css" |
| media="all" /> |
| </head> |
| |
| <body> |
| <a name="buildservices"></a> |
| |
| <h1>Apache Axis2 User's Guide -Building Services</h1> |
| |
| <p>Now that you know how to use Axis2 to generate clients from WSDL, this |
| section digs a little deeper showing you how to create services, and also how |
| to create services and clients "from scratch", so to speak.</p> |
| <ul> |
| <li><a href="userguide.html#intro">Introducing Axis2</a><br /> |
| |
| <ul> |
| <li><a href="userguide.html#whatis">What is Axis2?</a></li> |
| <li><a href="userguide.html#underhood">What's Under the Hood?</a></li> |
| <li><a href="userguide.html#handlessoap">How Axis2 Handles SOAP |
| Messages</a></li> |
| <li><a href="userguide.html#distributions">Axis2 Distributions</a></li> |
| <li><a href="userguide.html#sbd">The Axis2 Standard Binary |
| Distribution</a></li> |
| <li><a href="userguide.html#hierarchy">Axis2.war Directory |
| Hierarchy</a></li> |
| <li><a href="userguide.html#docs">Axis2 Documents Distribution</a></li> |
| <li><a href="userguide.html#clients">Axis2 and Clients</a></li> |
| </ul> |
| </li> |
| <li><a href="userguide-installingtesting.html#installingtesting">Installing |
| and Testing Client Code</a></li> |
| <li><a href="userguide-introtoservices.html#introservices">Introduction to |
| Services</a><br /> |
| |
| <ul> |
| <li><a href="userguide-introtoservices.html#messageexchange">Message |
| Exchange Patterns</a></li> |
| </ul> |
| </li> |
| <li><a href="userguide-creatingclients.html#createclients">Creating |
| Clients</a><br /> |
| |
| <ul> |
| <li><a href="userguide-creatingclients.html#choosingclient">Choosing a |
| Client Generation Method</a></li> |
| <li><a href="userguide-creatingclients.html#generating">Generating |
| Clients</a></li> |
| <li><a href="userguide-creatingclients.html#adb">Axis Data Binding |
| (ADB)</a></li> |
| </ul> |
| </li> |
| <li><a |
| href="userguide-buildingservices.html#buildservices"><strong>Building |
| Services</strong></a><br /> |
| |
| <ul> |
| <li><a |
| href="userguide-buildingservices.html#getcomfortable"><strong>Getting |
| Comfortable with Available Options</strong></a></li> |
| <li><a |
| href="userguide-buildingservices.html#createscratch"><strong>Creating |
| a Service from Scratch</strong></a></li> |
| <li><a |
| href="userguide-buildingservices.html#deploypojo"><strong>Deploying |
| Plain Old Java Objects</strong></a></li> |
| <li><a |
| href="userguide-buildingservices.html#deployrun"><strong>Deploying |
| and Running an Axis2 Service Created from WSDL</strong></a></li> |
| </ul> |
| </li> |
| <li><a href="userguide-samples.html">Samples</a></li> |
| <li><a href="userguide-forfurtherstudy.html">For Further Study</a></li> |
| </ul> |
| |
| <p><a name="getcomfortable"></a></p> |
| |
| <h2>Getting Comfortable with the Available Options</h2> |
| |
| <p>Axis2 provides a number of ways to create a service, such as:</p> |
| <ul> |
| <li>Create a service and build it from scratch. In this case, you build |
| your service class to specifically access AXIOM OMElement objects, then |
| create the services.xml file and package it for deployment.</li> |
| <li>Deploy Plain Old Java Objects (POJOs) as a service.</li> |
| <li>Generate the service from WSDL. Just as you can generate clients with |
| WSDL, you can also generate the skeleton of a service.</li> |
| </ul> |
| |
| <p>Let's look at these three options.</p> |
| <a name="createscratch"></a> |
| |
| <h2>Creating a Service from Scratch</h2> |
| |
| <p>Creating a service from scratch is not the most convenient way to do it, |
| but it does give you the most control. The process involves several steps.</p> |
| |
| <p><b>The short story:</b></p> |
| <ol> |
| <li>Create the service class with each operation that is represented by a |
| method that takes an org.apache.axiom.om.OMElement object as its |
| argument. (An OMElement is how the AXIs2 Object Model (AXIOM) represents |
| an XML element.)</li> |
| <li>Create the service descriptor, services.xml, which defines the class to |
| be used by the service and the appropriate message receivers.</li> |
| <li>Create the .aar file, with the classes in their proper locations based |
| on the package and the services.xml file in the META-INF directory.</li> |
| <li>Deploy the .aar file by using the <a href="webadminguide.html">Web |
| Administration application</a> or by copying it to the Axis2 services |
| directory.</li> |
| </ol> |
| |
| <p><b>The long story:</b></p> |
| |
| <p>Start by creating the service class, a plain Java class that uses classes |
| from the Axis2 libraries (see Code Listing 8).</p> |
| |
| <h3>Code Listing 8-Creating the Service Class</h3> |
| <pre>package org.apache.axis2.axis2userguide; |
| |
| import javax.xml.stream.XMLStreamException; |
| import org.apache.axiom.om.OMAbstractFactory; |
| import org.apache.axiom.om.OMElement; |
| import org.apache.axiom.om.OMFactory; |
| import org.apache.axiom.om.OMNamespace; |
| |
| public class SampleService { |
| |
| public OMElement sayHello(OMElement element) |
| throws XMLStreamException { |
| element.build(); |
| element.detach(); |
| |
| String rootName = element.getLocalName(); |
| System.out.println("Reading "+rootName+" element"); |
| |
| OMElement childElement = element.getFirstElement(); |
| String personToGreet = childElement.getText(); |
| |
| OMFactory fac = OMAbstractFactory.getOMFactory(); |
| OMNamespace omNs = fac.createOMNamespace( |
| "http://example1.org/example1", "example1"); |
| OMElement method = fac.createOMElement("sayHelloResponse", |
| omNs); |
| OMElement value = fac.createOMElement("greeting", omNs); |
| value.addChild(fac.createOMText(value, "Hello, |
| "+personToGreet)); |
| method.addChild(value); |
| |
| return method; |
| } |
| |
| private void ping(){ |
| } |
| |
| }</pre> |
| |
| <p>Make sure to include Axis2 libraries in your class path when compiling the |
| source.</p> |
| |
| <p>Axis2 uses AXIOM, or the AXIs Object Model, a DOM (Document Object Model) |
| -like structure that is based on the StAX API ( Streaming API for XML). |
| Methods that act as services must take an OMElement as their argument, which |
| represents the payload of the incoming SOAP message. (An OMElement is just |
| AXIOM's way of representing an XML element, like a DOM Element object.) In |
| this case, you're extracting the contents of the first child of the payload |
| element, adding text to it, and using it as content for the return OMElement. |
| Unless this is an "in only" service, these methods must return an OMElement, |
| because that becomes the payload of the return SOAP message.</p> |
| |
| <p>To turn this class into a service, create the service description file, |
| services.xml, as in Code Listing 9.</p> |
| |
| <h3>Code Listing 9 - Create the Service Description</h3> |
| <pre><service name="UserGuideSampleService"> |
| <description> |
| This is a sample service created in the Axis2 User's Guide |
| </description> |
| |
| <parameter name="ServiceClass" |
| locked="false">org.apache.axis2.axis2userguide.SampleService |
| </parameter> |
| |
| <operation name="sayHello"> |
| <messageReceiver |
| class="org.apache.axis2.receivers.RawXMLINOutMessageReceiver"/> |
| </operation> |
| <operation name="ping"> |
| <messageReceiver |
| class="org.apache.axis2.receivers.RawXMLINOnlyMessageReceiver"/> |
| </operation> |
| </service></pre> |
| |
| <p>This document defines the service, called by the <a |
| href="webadminguide.html">Web Administration Application</a>, and the class |
| used to serve requests. For each operation, it defines the appropriate |
| message receiver class.</p> |
| |
| <p>Create a new directory, META-INF, in the main directory for the class. (In |
| this case, that's the same directory that contains the org directory) and |
| place the services.xml file in it.</p> |
| |
| <p>Create the .aar file by typing: jar cvf SampleService.aar ./*</p> |
| |
| <p>Deploy the SampleService.aar file by using the <a |
| href="webadminguide.html">Web Administration application</a> or by copying it |
| to the Axis2 services directory.</p> |
| |
| <p>Now you can create a client class that accesses the service directly (see |
| Code Listing 10).</p> |
| |
| <h3>Code Listing 10 - Create a Client Class that Accesses the Service |
| Directly</h3> |
| <pre>package org.apache.axis2.axis2userguide; |
| |
| import javax.xml.stream.XMLStreamException; |
| import org.apache.axiom.om.OMAbstractFactory; |
| import org.apache.axiom.om.OMElement; |
| import org.apache.axiom.om.OMFactory; |
| import org.apache.axiom.om.OMNamespace; |
| import org.apache.axis2.addressing.EndpointReference; |
| import org.apache.axis2.client.Options; |
| import org.apache.axis2.Constants; |
| import org.apache.axis2.client.ServiceClient; |
| |
| public class SampleClient { |
| |
| private static EndpointReference targetEPR = |
| new EndpointReference( |
| "http://localhost:8080/axis2/services/UserGuideSampleService"); |
| |
| public static OMElement greetUserPayload(String personToGreet) { |
| OMFactory fac = OMAbstractFactory.getOMFactory(); |
| OMNamespace omNs = fac.createOMNamespace( |
| "http://example1.org/example1", "example1"); |
| OMElement method = fac.createOMElement("sayHello", omNs); |
| OMElement value = fac.createOMElement("personToGreet", |
| omNs); |
| value.addChild(fac.createOMText(value, personToGreet)); |
| method.addChild(value); |
| return method; |
| } |
| |
| public static void main(String[] args) { |
| try { |
| OMElement payload = |
| SampleClient.greetUserPayload("John"); |
| Options options = new Options(); |
| options.setTo(targetEPR); |
| |
| options.setTransportInProtocol(Constants.TRANSPORT_HTTP); |
| |
| ServiceClient sender = new ServiceClient(); |
| sender.setOptions(options); |
| OMElement result = sender.sendReceive(payload); |
| |
| String response = result.getFirstElement().getText(); |
| System.out.println(response); |
| |
| } catch (Exception e) { //(XMLStreamException e) { |
| System.out.println(e.toString()); |
| } |
| } |
| |
| }</pre> |
| |
| <p>This class uses the same technique of sending and receiving OMElements, |
| but it's also important to note the use of the Options class. This class |
| enables you to determine properties such as the transport used for the return |
| message (the transport used for the outgoing message can be inferred from the |
| URL of the destination) and the SOAP version to use. In addition to providing |
| setter and getter methods of specific properties that affect how the client |
| interacts with the service, the Options class enables you to create |
| inheritance relationships between Options objects. So if a property is not |
| found in the current Options object used, the client can check the parent |
| Options object of the current Options object.</p> |
| |
| <p>Compile and run the above SampleClient.java. Make sure to have all axis2 |
| libraries in your class path. If all has gone well, 'Hello, John' will be |
| shown as the output in the console.</p> |
| <a name="deploypojo"></a> |
| |
| <h2>Deploying Plain Old Java Objects (POJOs)</h2> |
| |
| <p>One very easy way to create a Web service is simply to deploy the Java |
| objects that represent the service. Start with the class, shown in Code |
| Listing 11.</p> |
| |
| <h3><b>Code Listing 11 - Creating the Class SampleService</b></h3> |
| <pre>package org.apache.axis2.axis2userguide; |
| |
| public class SampleService { |
| |
| public void doInOnly(){ |
| return; |
| } |
| |
| public String noParameters(){ |
| return "Hello"; |
| } |
| |
| public String twoWayOneParameterEcho(String toEcho){ |
| return toEcho; |
| } |
| |
| public boolean multipleParametersAdd(float price, int itemId, |
| String description, String itemName){ |
| //Code to handle the logic |
| return true; |
| } |
| |
| }</pre> |
| |
| <p>Next, you'll need to tell Axis2 what class corresponds with what Web |
| service calls. Do this by creating a file called services.xml and adding the |
| following shown in Code Listing 12.</p> |
| |
| <h3><b>Code Listing 12 - Creating services.xml</b></h3> |
| <pre><service name="SampleService" scope="application"> |
| <description> |
| Sample Service |
| </description> |
| <messageReceivers> |
| <messageReceiver |
| mep="http://www.w3.org/2004/08/wsdl/in-only" |
| class="org.apache.axis2.rpc.receivers.RPCInOnlyMessageReceiver"/> |
| <messageReceiver |
| mep="http://www.w3.org/2004/08/wsdl/in-out" |
| class="org.apache.axis2.rpc.receivers.RPCMessageReceiver"/> |
| </messageReceivers> |
| <parameter name="ServiceClass"> |
| org.apache.axis2.axis2userguide.SampleService |
| </parameter> |
| </service></pre> |
| |
| <p>This file makes the InOnly and InOut MEPs available to the service and |
| tells Axis2 which class to call; operations must match method names. In other |
| words, Axis2 automatically sends a call to the multipleParametersAdd |
| operation to the |
| org.apache.axis2.axis2userguide.SampleService.multipleParametersAdd() |
| method.</p> |
| |
| <p>Now it's time to create the distribution. Arrange your files in the |
| following directory structure (see Code Listing 13).</p> |
| |
| <h3><b>Code Listing 13- Create the Directory Structure for the |
| Distribution</b></h3> |
| <pre> - SampleService |
| - META-INF |
| - services.xml |
| - org |
| - apache |
| - axis2 |
| - axis2userguide |
| - SampleService.class</pre> |
| |
| <p>Finally, deploy the service by copying the SampleService directory to the |
| webapps/axis2/WEB-INF/services directory on the servlet engine. You can check |
| to make sure that it's been properly deployed by checking <a |
| href="http://<host>:<port>/axis2/services/listServices">http://<host>:<port>/axis2/services/listServices</a>.</p> |
| <a name="deployrun"></a> |
| |
| <h2>Deploying and Running an Axis2 Service Created from WSDL</h2> |
| |
| <p>If you have a WSDL file, you can easily create and deploy a service based |
| on that description. For example, to create a service based on the same WSDL |
| file used in the <a href="userguide-creatingclients.html">clients section</a> |
| of this document, you will follow the steps below.</p> |
| |
| <p><b>The short story:</b></p> |
| <ol> |
| <li><a |
| href="http://ws.apache.org/axis2/download/@axis2_version_dir@/download.cgi#std-bin">Download</a> |
| the Axis2 standard distribution, if you have not done so already.</li> |
| <li>Generate the skeleton using the WSDL2Java utility, as in: <br /> |
| |
| <pre>java org.apache.axis2.wsdl.WSDL2Java -uri file:///C:/apps/axis2/samples/zSample/Axis2UserGuide.wsdl -p org.apache.axis2.axis2userguide -d adb -s -wv 1.1 -ss -sd -ssi</pre> |
| </li> |
| <li>Open the *Skeleton.java file and add the functionality of your service |
| to the generated methods.</li> |
| <li>Build a service using Ant by typing ant jar.server</li> |
| <li>Deploy the service by copying the build/lib/*.aar file to |
| <J2EE_HOME>/webapps/axis2/WEB-INF/services</li> |
| <li>Check http://<server>:<port>/axis2/services/listServices to |
| make sure the service has been properly deployed.</li> |
| </ol> |
| |
| <p><b>The long story:</b></p> |
| |
| <p>As with generating clients, you will need the <a |
| href="http://ws.apache.org/axis2/download/@axis2_version_dir@/download.cgi#std-bin">Axis2 |
| Standard Distribution</a>, because the <a |
| href="http://ws.apache.org/axis2/download/@axis2_version_dir@/download.cgi#war">Axis2 |
| WAR Distribution</a> does not include the WSDL2Java utility. Once you've got |
| it downloaded and unpacked, make sure that you set the AXIS2_HOME variable to |
| point to the location in which you've unpacked it.</p> |
| |
| <p>Now you are ready to generate the actual service. To keep things neat, |
| create a new directory and change to it. The WSDL file is the same one |
| referenced in <a href="userguide-creatingclients#generating.xhtml">Generating |
| Clients</a> and includes four operations: NoParameters, |
| TwoWayOneParameterEcho, MultipleParametersAddItem, and DoInOnly. To generate |
| the service, use the WSDL2Java utility, as in Code Listing 14.</p> |
| |
| <h3>Code Listing 14 - Using the WSDL2Java Utility to Generate the Service</h3> |
| |
| <p><strong>Code Listing 14.1:</strong></p> |
| <pre>java org.apache.axis2.wsdl.WSDL2Java -uri |
| file:///C:/apps/axis2/samples/zSample/Axis2UserGuide.wsdl -p |
| org.apache.axis2.axis2userguide -d adb -s -wv @axis2_version@ -ss -sd</pre> |
| |
| <p>Note: Make sure all the .jar files in the Axis2 lib directory is set to |
| the CLASSPATH before you run the above code.</p> |
| |
| <p>This statement tells the utility you want to create a service out of the |
| operations in the file <a |
| href="userguide-codelisting5.html">Axis2UserGuide.wsdl</a>, and that the Java |
| classes generated should be in the org.apache.axis2.axis2userguide package |
| (-p). (You can view the appropriate directories created.) It also indicates |
| that you want to use the Axis2 DataBinding Framework, or ADB (-d), to |
| generate only synchronous or blocking code (-s), and to generate server-side |
| code (-ss) as opposed to a client, including the services.xml service |
| descriptor file (-sd). It also specifies version @axis2_version@ for the WSDL |
| file (-wv)<strong>.</strong></p> |
| |
| <p><strong>Code Listing 14.2:</strong></p> |
| |
| <p>You can also use the following script files to achieve the same. In this |
| case you do not have the set the CLASSPATH manually.</p> |
| |
| <p>For Linux:</p> |
| <pre>$AXIS2_HOME/bin/wsdl2java.sh -uri file:///C:/apps/axis2/samples/zSample/Axis2UserGuide.wsdl |
| -p org.apache.axis2.axis2userguide -o target_directory_name -d adb -s -wv @axis2_version@ -ss -sd</pre> |
| |
| <p>For MS Windows:</p> |
| <pre>%AXIS2_HOME%\bin\wsdl2java.bat -uri file:\\\C:\apps\axis2\samples\zSample\Axis2UserGuide.wsdl |
| -p org.apache.axis2.axis2userguide -o target_directory_name -d adb -s -wv @axis2_version@ -ss -sd</pre> |
| |
| <p>In both instances, at this point, you should see four new items in your |
| chosen directory: the build.xml file, which includes instructions for Ant, |
| the src directory, which includes all the generated classes and stubs, the |
| resources directory, which includes a regenerated version of the WSDL, and |
| the services.xml file, which ultimately controls the service's behavior.</p> |
| |
| <p>You can compile the service at this point, but it doesn't actually do |
| anything yet. You can solve that problem by opening the |
| src\org\apache\axis2\axis2userguide\Axis2UserGuideServiceSkeleton.java file |
| and either editing the code in bold -- make sure you manage parameter numbers |
| -- or replacing all the code with the following in Code Listing 15.</p> |
| |
| <h3>Code Listing 15 - Compiling the Service</h3> |
| |
| <p><pre>/** |
| * Axis2UserGuideServiceSkeleton.java |
| * |
| * This file was auto-generated from WSDL |
| * by the Apache Axis2 version: SNAPSHOT Oct 15, 2006 (11:23:18 |
| GMT+00:00) |
| */ |
| package org.apache.axis2.axis2userguide; |
| /** |
| * Axis2UserGuideServiceSkeleton java skeleton for the axisService |
| */ |
| public class Axis2UserGuideServiceSkeleton { |
| |
| |
| /** |
| * Auto generated method signature |
| |
| * @param param7 |
| |
| */ |
| public org.apache.axis2.axis2userguide.NoParametersResponse |
| NoParameters |
| (org.apache.axis2.axis2userguide.NoParametersRequest param7) |
| |
| { |
| <b>System.out.println(param7); |
| |
| NoParametersResponse res = |
| new NoParametersResponse(); |
| |
| return res;</b> |
| } |
| |
| |
| /** |
| * Auto generated method signature |
| |
| * @param param9 |
| |
| */ |
| public |
| org.apache.axis2.axis2userguide.TwoWayOneParameterEchoResponse |
| TwoWayOneParameterEcho |
| ( |
| org.apache.axis2.axis2userguide.TwoWayOneParameterEchoRequest |
| param9 |
| ) |
| |
| { |
| <b>System.out.println(param9.getEchoString()); |
| |
| TwoWayOneParameterEchoResponse res = |
| new TwoWayOneParameterEchoResponse(); |
| |
| res.setEchoString(param9.getEchoString()); |
| |
| return res;</b> |
| } |
| |
| |
| /** |
| * Auto generated method signature |
| |
| * @param param11 |
| |
| */ |
| public void DoInOnly |
| ( |
| org.apache.axis2.axis2userguide.DoInOnlyRequest param11 |
| ) |
| |
| { |
| <b>System.out.println(param11.getMessageString());</b> |
| } |
| |
| |
| /** |
| * Auto generated method signature |
| |
| * @param param12 |
| |
| */ |
| public |
| org.apache.axis2.axis2userguide.MultipleParametersAddItemResponse |
| MultipleParametersAddItem |
| ( |
| |
| org.apache.axis2.axis2userguide.MultipleParametersAddItemRequest |
| param12 |
| ) |
| |
| { |
| <b>System.out.println(param12.getPrice()); |
| System.out.println(param12.getItemId()); |
| System.out.println(param12.getDescription()); |
| System.out.println(param12.getItemName()); |
| |
| MultipleParametersAddItemResponse res = |
| new MultipleParametersAddItemResponse(); |
| |
| res.setSuccessfulAdd(true); |
| res.setItemId(param12.getItemId()); |
| |
| return res;</b> |
| } |
| |
| }</pre> |
| </p> |
| |
| <p>As with generating clients, all these classes, such as |
| MultipleParametersAddItemRequest and TwoWayOneParameterEchoResponse, are |
| generated by the utility, and can be found in the same directory as the |
| skeleton file. They include methods such as setSuccessfulAdd(), which sets |
| the value of the content of an element in the response, and getItemName(), |
| which retrieves the content of elements in the request.</p> |
| |
| <p>Save the file and compile it by typing: ant jar.server</p> |
| |
| <p>If all goes well, you should see the BUILD SUCCESSFUL message in your |
| window, and the Axis2UserGuideService.aar file in the newly created build/lib |
| directory.</p> |
| |
| <p><img alt="The BUILD SUCCESSFUL message in your window" |
| src="images/fig05.jpg" /></p> |
| |
| <p>Now you need to deploy the service to the server. To do that, copy the |
| Axis2UserGuideService.aar file to the WEB-INF/services directory of the |
| application server. (You also have the option to use the administration |
| tools. See the <a href="webadminguide.html">Web Administrator's Guide</a> for |
| more information.)</p> |
| |
| <p>To verify that the service has been properly deployed, check the list of |
| services at <a |
| href="http://<host>:<port>/axis2/services/listServices">http://<host>:<port>/axis2/services/listServices</a>.</p> |
| |
| <p><img alt="Checking the list of services" src="images/fig06.jpg" /></p> |
| |
| <p>Now you should be able to access the service using any of the clients |
| built in the <a href="userguide-creatingclients.html#generating">Generating |
| Clients</a> document.</p> |
| |
| <p><strong>See Next Section</strong>- <a |
| href="userguide-samples.html">Samples</a></p> |
| </body> |
| </html> |