# Howto: Getting Started with WebServices and JOnAS 3.X

- WebServices and J2EE
- Early Integration of Axis in JOnAS 3.X series
- How to use WebServices
  - Endpoint Creation
  - Exposing Stateless Session Bean
  - Exposing Simple class (JAX-RPC Class)
  - Client Creation
  - WSDL Knowledge
  - no WSDL Knowledge
  - Using Axis WSDD Configuration file
  - Service
  - Parameter
  - Optional
  - Mappings
  - Deployment
  - Deploy Created Web Service

## WebServices and J2EE

WebServices are fully integrated in J2EE 1.4 compliant Application Servers.
Web services technologies can be seen as another communication protocol used to interoperate heterogeneous systems. Web services are based on the SOAP protocol. The SOAP messages can be transported with various transport mode (JMS, HTTP, mail, ...) but the focus of this document is the HTTP transport (because Web Services for J2EE v1.1 use only SOAP/HTTP).

## Early Integration of Axis in JOnAS 3.X series

JOnAS hosts Apache Axis starting with version 3.0. This means that the user no longer must add Axis jars in its webapp.
To use an Axis class (AdminClient, WSDL2Java, ...) from the command line, simply use the jclient script in place of the common java executable (jclient will create the appropriate classpath).

## How to use WebServices

### Endpoint Creation

When it is desirable to expose some business methods as web services, a servlet container such as Tomcat or Jetty should be used to hold the Axis servlet where the SOAP messages of clients will ultimately end up.
To configure Axis, the developer must write a .wsdd file holding Axis-specific configuration parameters. This can be in one of two different forms: a simple wsdd containing only information about the web services the developer wants to expose (see an example here), or a complete wsdd containing exposed web services information AND Axis base configuration (see an example here).
The first form is preferred for development purposes, because the developer can easily change configuration values and submit them again to the Axis servlet (the Axis servlet will merge the current WEB-INF/server-config.wsdd with this new configuration file). It is usually named deploy.wsdd (its location is user-defined).
The second form is appropriate when used in a production environment where configuration changes are minor (ultimately, both forms results in the same Axis wsdd file). It MUST be named server-config.wsdd and located in the WEB-INF directory of the servlet.

#### Exposing Stateless Session Bean

1. Create a simple WebApp containing minimal Axis information, such as a WEB-INF/web.xml declaring the Axis servlet and servlet mapping (sample here).
2. Create a wsdd file (use the form you prefer)

- add a service with a unique name (used to find the appropriate service to invoke from the URL String)
- set a provider for the service: `java:EJB`

3. Add mandatory parameters for EJB exposition:

- `beanJndiName`: name used in Axis lookup. (a java:comp/env name can be set here if ejb-ref or ejb-local-ref is added in the web-app descriptor)
- `homeInterfaceName`: EJB Home interface fully-qualified class name
- `remoteInterfaceName`: EJB Remote interface fully-qualified class name
- `localHomeInterfaceName`: Local EJB Home interface fully-qualified class name
- `localInterfaceName`: Local EJB interface fully-qualified class name
- `allowedMethods`: comma-separated list of method names accessible via the web service

The developer must set AT LEAST local OR remote interface names. If local AND remote interfaces are specified, Axis will use the REMOTE interface, even if the interfaces are different.
Refer to "Using Axis WSDD configuration files" for more information.

#### Exposing Simple class (JAX-RPC class)

JAX-RPC classes are normal classes with no particular inheritance requirements, exposed as a web service.
1. Add the Axis servlet declaration in the web-app descriptor (sample here) with a servlet mapping.
2. Create a wsdd file (use whichever form you prefer).

- add a service with a unique name (used to find the appropriate service to invoke from the URL String)
- set a provider for the service: `java:RPC`

3. Add mandatory parameters to expose JAX-RPC classes:

- `className`: the fully-qualified name of the class to be exposed as a web service.
- `allowedMethods`: comma-separated list of method names accessible via the web service.

### Client Creation

Creation of a web services client is heavily based on WSDL knowledge, even if it is not mandatory.

#### WSDL Knowledge

WSDL is the easiest way to create a web service client.
All that is necessary is to generate the files needed to access the web service, then compile them and add them into your component archive.
This can be done from the command line using the `org.apache.axis.wsdl.``WSDL2Java``` tool.
example:
`jclient org.apache.axis.wsdl.WSDL2Java --output <destination directory> --NStoPkg
<namespace>=<package> <wsdl url>`
The `--NStoPkg` option is used to place generated classes in a convenient package according to the namespace of the WSDL Definition and the namespace(s) of the XML Schema(s).
Axis provides an Ant Task for automated build:
`<taskdef name="axis-wsdl2java"
classname="org.apache.axis.tools.ant.wsdl.Wsdl2javaAntTask">
<!-- classpath holds jonas.jar, webservices_axis.jar, ... -->
<classpath refid="base.classpath"/>
</taskdef>
<axis-wsdl2java url="${ws.google.wsdl}/GoogleSearch.wsdl"
output="${src.dir}">
<mapping namespace="urn:GoogleSearch"
package="org.objectweb.wssample.gen.google"/>
</axis-wsdl2java>
` code :

`import path.to.your.generated.classes.*; [...] <ServiceInterface> service = new <Service>Locator(); <PortInterface> port = service.get<PortName>(); <ObjectType> result = port.<methodName>(<arguments>);`

#### No WSDL Knowledge

When the client does not have the WSDL of the service to access, the developer must use Service agnostic interfaces.
With Axis, you must instantiate an org.apache.axis.client.Service class (implementation of javax.xml.rpc.Service), create a javax.xml.rpc.Call instance from the Service, configure it manually, and invoke the Call.
Refer to the following example:
```
`

`import javax.xml.rpc.Call;
import javax.xml.rpc.Service;
import javax.xml.namespace.QName;
import javax.xml.rpc.encoding.TypeMappingRegistry;
import javax.xml.rpc.encoding.TypeMapping;
import org.apache.axis.encoding.ser.BeanSerializerFactory;
import org.apache.axis.encoding.ser.BeanDeserializerFactory;
[...]
// create a Service instance (other constructor usable, see the doc)
Service service = new org.apache.axis.client.Service();
` `// configure mappings if web service use Complex types
// first get the mapping registry instance
` `TypeMappingRegistry tmr = service.getTypeMappingRegistry();
// create a QName representing the fully qualified name of the
// XML type to serialize/deserialize (namespace+locapart pair)
QName xmlType =` `new QName("namespace-of-complex-type", "complex-type-name");
// get a TypeMapping (default for axis is SOAP encoding TypeMapping)
` `TypeMapping tm = tmr.getDefaultTypeMapping();
// register the XML type with a Java class by specifying
// Serializer/Deserializer factories to use.
tm.register(your.java.Type.class,
xmlType,
new` `BeanSerializerFactory(``your.java.Type.class, xmlType``),
new` `BeanDeserializerFactory(``your.java.Type.class, xmlType``)``);
// get a Call instance from the Service
// specify port to use and operation name to be invoked
// see the doc for other createCall methods usage
Call call = service.createCall(new QName("port-name", new QName("operation-name")));
// where is the web service ?
call.``setTargetEndpointAddress("url-address-of-the-endpoint");
` ```// now, we can invoke the web service with its parameters
` `String result = call.invoke(new Object[] {"Hello, World!"});
`

``

### Using Axis WSDD Configuration file

This section covers the basic functionality of wsdd configuration files.
For detailed information refer to the Axis User Guide and Reference Guide.

#### Service

`<service>` is the tag used to declare a web service.
Attributes:

- `name`: unique name of the service
- `provider`: bridge used by Axis to invoke different objects: EJB, normal classes, CORBA objects, ...
- `style`: defines global format of the SOAP Message
- `use`: SOAP encoded message or message enclosing classic XML Elements (depends on the style attributes)

Provider possible values: java:EJB (used to expose EJB Stateless Session Bean), java:RPC (used to expose Simple classes), java:MSG (used to ???)
Style possible values: document, rpc
With RPC, SOAP Messages must have an element named as the operation to be invoked as their first soap:body element.
With Document, SOAP Messages cannot have a first element with the operation name.
Use possible values: encoded, literal
With encoded, SOAP refs can be used in the SOAP Message.
With literal, no SOAP refs can be used in the SOAP Message.
Note: a SOAP ref is similar to a pointer in an XML SOAP Message: an Element is defined with an ID that can be referenced from somewhere else in the SOAP Message.
Refer to the following snippet of Axis javadoc for style and use combinations:

Description of the different styles
style=rpc, use=encoded
First element of the SOAP body is the operation. The operation contains elements describing the parameters, which are serialized as encoded (possibly multi-ref)

       <soap:body>
          <operation>
             <arg1>...</arg1>
             <arg2>...</arg2>
          </operation>

style=RPC, use=literal
First element of the SOAP body is the operation. The operation contains elements describing the parameters, which are serialized as encoded (no multi-ref)\

       <soap:body>
          <operation>
             <arg1>...</arg1>
             <arg2>...</arg2>
          </operation>

style=document, use=literal
Elements of the SOAP body are the names of the parameters (there is no wrapper operation...no multi-ref)

       <soap:body>
             <arg1>...</arg1>
             <arg2>...</arg2>

style=wrapped
Special case of DOCLIT where there is only one parameter and it has the same qname as the operation. In such cases, there is no actual type with the name...the elements are treated as parameters to the operation.

       <soap:body>
          <one-arg-same-name-as-operation>
             <elemofarg1>...</elemofarg1>
             <elemofarg2>...</elemofarg2>

style=document, use=encoded
There is no enclosing operation name element, but the parameters are encoded using SOAP encoding This mode is not (well?) supported by Axis.

#### Parameter

`<parameter>` is the tag used to configure a service. It is basically a name-value pair.
Attributes:

- `name`: parameter name (key)
- `value`: parameter value

Common parameter:

- `className`: fully-qualified class name of service class (only used for provider RPC & MSG)
- `beanJndiName`: name used in Axis lookup. (a java:comp/env name can be set here if ejb-ref or ejb-local-ref is added in the web-app descriptor)
- `localHomeInterfaceName`: Local EJB Home interface fully-qualified class name
- `localInterfaceName`: Local EJB interface fully-qualified class name
- `homeInterfaceName`: EJB Home interface fully-qualified class name
- `remoteInterfaceName`: Remote EJB interface fully-qualified class name
- `allowedMethods`: comma-separated list of method names accessible via the web service (for all providers)
- `scope`: scope of the web service (`Request`: create a new Object for each request, `Session`: keep the same Object for a given Session ID, `Application`: keep the same Object for the entire application run)

#### Optional

Other options can be specified to a service without parameter tags:

- `wsdlFile`: specify the static wsdl file to be served when a ?WSDL request comes to the endpoint
- `namespace`: specify the web service namespace (override default namespace created from URL location of the service). The developer can handle the namespace value with this tag.
By default a namespace will look like like the following: `http://ws.servlets.wssample.objectweb.org` (for a JAX-RPC class named `org.objectweb.wssample.servlets.ws`). The developer can write a more concise namespace as desired: for example, `urn:JaxRpcWsSample`.

- `operation`: used to describe the operation exposed (avoid Axis to use reflection to discover the service interface). Refer to the Axis doc for details.

#### Mappings

Mappings in WSDD can be set at different levels: mappings commons for all services are direct children of the deployment tag, and mappings specific for a given web service are children of the service tag.
The developer can specify the type of mappings in the WSDD configuration file: beanMapping and typeMapping. beanMapping is a write shortcut for typeMapping when mapping bean types.
Mapping is used to register a java type, with an XML QName and a serializer/deserializer pair.
examples:`
<typeMapping xmlns:ns="urn:my.namespace"
serializer="your.java.serializer.factory"
deserializer="``your.java.deserializer.factory``"
qname="``ns:my-xml-type-name``"
type="``java:your.java.classname``"
encodingStyle="encoding-namespace"/>
Notes :
type value must be a qname in java prefixed namespace (java:XXX.YYY)
by default encodingStyle is set to http://schemas.xmlsoap.org/soap/encoding/ (SOAP 1.1 Encoding)
` `When Arrays of Complex Types are serialized and/or deserailized the factories to be used are :
org.apache.axis.encoding.ser.ArraySerializerFactory
` `org.apache.axis.encoding.ser.ArrayDeserializerFactory`
`
<beanMapping xmlns:ns="urn:my.namespace"
languageSpecificType="java:your.java.classname"
qname="ns:my-xml-type-name"/>
Notes :
serializer and deserializer are automatically set to BeanSerializerFactory and BeanDeserializerFactory
encodingStyle is automatically set to null (cannot be overridden)`

#### Deployment

A deployment Element is the root Element of any Axis WSDD file. It holds commons namespace definitions.
A normal deployment Element looks like the following:
`<deployment xmlns="http://xml.apache.org/axis/wsdd/"
xmlns:java="http://xml.apache.org/axis/wsdd/providers/java">
<!-- ... services definitions here ... -->
</deployment>``
`

### `Deploy Created Web Service`

Deployment of the web service in JOnAS depends on the form of the wsdd file:
For full wsdd configuration files, simply add the wsdd file in the WEB-INF/ directory of the servlet with the name server-config.wsdd. Deployment will be performed automatically by Axis when the first client attempts to connect.
For simpler wsdd configuration files, deploy the web-app (or ear) into JOnAS (normal process). Then, use the Axis AdminClient tool:
``jclient org.apache.axis.client.AdminClient -lhttp://<hostname>:<port>/<web-app-context>/<servlet-mapping-to-Axis-Servlet> <your-deploy>.wsdd``