Web Services

I am going to point you in the direction of my JBoss web services introduction so that you can have an idea on what web services are, so take a peek then come back here to how this relates to EJB 3.

Web services are now the industry standard for application-to-application (A2A) and business-to-business (B2B) integration, it will provide interoperability between networked applications out of the box. Service-Oriented Architecture (SOA) is a new way of building loosely coupled applications, you focus on building services, for an example you could have a service that validates a credit card. When implementing SOA, Web Services Description Language (WSDL) describes the messages, types, and operations of the web service and its contract to which the web services guarantees it will conform.

An example would be to register your service in the UDDI (Universal Description, Discovery and Integration) registry, the client would then perform a lookup which finds the WSDL describing how to call the service from the registry, generates the endpoint interface and proxy classes and then invokes the web service (see below diagram)



Clients can even search for multiple similar services and determine which one to use on the fly at runtime, depending on known data, user preferences, user locale, or any number of other circumstances unique to the client application at that moment in time.

Identifying Web Service Components

At its core a web service is published by a service producer and accessed by a service consumer, this mostly always ends up with a XML document being sent over an HTTP transport. As a general rule the data protocol shared between service consumer and producer is based on some flavor of XML, but the transport can be any network protocol (HTTP, JMS, FTP). There are a number of ways to implement a service

Because SOAP is widely used the most I will describe how to implement this, first a SOAP stack will consist of the following

Service messaging Messages are sent between client and service in XML, the universal format for metadata. For SOAP you use the standard message structure as defined.
Service description

Each service has a XML detailing

  • What parameters it expects
  • Optional parameters
  • Data types of the parameters
  • Return types
  • etc

A web service client "consumes" the WSDL file in order to communicate with a web service

Service discovery A service will registry with the UDDI registry by providing the WSDL required to access the service, clients then can access this registry looking for services that meet their requirements
Service transport This is the network mechanism that transports the messages between the client and the service, HTTP is the most commonly used transport but you can also use JMS, FTP, etc.

SOAP Message

The Simple Object Access Protocol (SOAP) is a distributed protocol similar to COBRA and Java RMI. It allows applications to talk to each other over a network by exchanging messages. A SOAP message is an XML document that contains several elements (Envelope, Header and Body).

SOAP XML document <SOAP-ENV:Envelope
  xmlns:SOAP-ENV="http://schemas.org/soap/envelope/"
  SOAP-ENV:encodingStyle="http://schema.xmlsoap.org/soap/encoding/">
  <SOAP-ENV:Header/>
  <SOAP-ENV:Body>
    <addBid xmlns="http://actionbazaar.com/Bidding">
      <user-id>viper</user-id>
      <item-id>100</user-id>
      <bid-price>2000.00</bid-price>
    </addBid>
  </SOAP-ENV:Body>
</SOAP-ENV:Envelope>

The message starts off with an Envelope which typically declares a namespace and may include encoding. Immediately inside the Envelope is the Header which is optional, this may contain meta-information about he message such as security, network routing and other data required to get the message to its destination. The last piece of the SOAP message is the Body which in the case of our example defines the addBid method and its associated parameters.

WSDL

The Web Services Description Language (WSDL) is central to a web service because it describes the service to possible customers, it specifies the message type, port, supported operations, data types, and all other details about how the web service works, where it can be found and what a client should expect in return. I am going to leave you to look at an example from the web there are many out there.

There is no one-to-one mapping between XML data types and Java, if the service is not Java then it has to provide data type binding support, but in Java the binding is accomplished through the Java Architecture for XML Binding (JAXB) 2.0 specification. JAXB allows web services to use the complete XML schema, which results in improved interoperability and ease of use.

UDDI is a platform-independant, XML-based registry that enables clients to find available services, a client can then search through the registry looking for a particular type of service, vendor name or similar information. Once found the client can then request the WSDL for the service, the client will then consume the WSDL, bind to the service and invoke the service using the published service description.

There are two primary types of web services styles, see JBoss configuring web services for more details

There are also two different approaches to developing web services

JAX-WS

The Java API for XML-Based Web Services (JAX-WS) 2.0 is the core specification that defines the web services standard for Java EE 5. The specification builds on to support web services such as in the table below

Specification
Purpose
Java API for XML Web Services 2.0 Platform specification
Java API for XML Binding 2.0 Binding for WSDL to Java
WS Basic Profile 1.1 Interoperability with .NET
Web Services Metadata 2.0 Metadata appoarch to define web service
Java API for XML RPC 1.1 Backward compatibility with J2EE 1.4 web services

JAX-WS allows both regular Java classes and stateless EJBs to be exposed as web services, there are a few reasons why you should choose EJB over regular Java classes, as you can see in the table below you get declartive transaction and security using EJB 3, you can also use interceptors and the timer service without depending on extra layering. EJB 3 can easily expose your business application using additional protocols (such as RMI), by adding a remote interface, exposing the bean is done by simply adding the annotation @WebService.

Feature
Java Web Service
EJB 3 Web Service
POJO
Yes
Yes
Dependancy injection of resources, persistence units, etc
Yes
Yes
Lifecycle methods
Yes
Yes
Declarative transaction
No
Yes
Declarative security
No
Yes
Requires annotations processing in an external Annotation Processing Tool (APT)
Yes
Most EJB containers do not require this
Can be run in a web container like Tomcat
Yes
No


If you use the @WebService annotation in the interface then all methods in the bean are exposed in the web service, you may be tempted to use both the @WebService and @Remote annotation, although it will work it is not part of the specification and thus may not be portable between vendors.

@WebService interface

@Target({TYPE})
public @interface WebService {
  String name() default "";
  String targetNamespace() default "";
  String serviceName() default "";
  String wsdlLocation() default "";
  String endpointInterface() default "";
  String portName() default "";
}

Note:
name - the name of the wsdl:portType (default is to use the bean class or interface name)
targetNamespace - XML namespace of the WSDL
serviceName - service name of the web service wsdl:service
wsdlLocation - used when using the meet-in-the-middle approach
endpointInterface - qualified name of the service endpoint interface
portName - wsdl:portName

@WebService

# The interface

@WebService
public interface PlaceBidWS {

  public Long addBid(String bidderId, Long itemId, Double bidPrice);
}

# The bean

@Stateless
public class PlaceBidBean implements PlaceBidWS, PlaceBid {

  ...
}

You can exclude methods from being exposed as a web service using the @WebMethod annotation, the below example excludes the method persistBid from being exposed.

@WebMethod @WebService(endPointInterface="PlaceBidSEI")
@Stateless
public class PlaceBidBean {
 
  public Long addBid ( ... ) { ... }

  @WebMethod(exclude="true")
  public Long persistBid( ... ) { ... }
}

There are a number of other annotation that can be used, I will leave you to the web for examples

Acessing Web Services

A Java client application can access a web service by injecting the web service using the @WebServiceRef annotation

@WebServiceRef (Java application client)

import java.xml.ws.WebServiceRef;
import actionbazaarplacebidservice.PlaceBidService;

@WebServiceRef(wsdlLocation="http://localhost:8080/PlaceBidService/PlaceBidBean?WSDL")
private static PlaceBidService placeBidService;

public static void main(String [] args) {

  try {
    actionbazaarplacebidservice.PlaceBidBean placeBid = placeBidService.getPlaceBidBeanPort();

    System.out.println("Bid Successful, BidId Received is: " + placeBid.addBid("vallep", Long.valueOf(9001), 2000.50));

  } catch (Exception (ex) {
      ex.printStackTrace();
  }
}

@WebServiceRef (EJB ) @Stateless
public class TrackOrderBean implements TrackOrder {

  @WebServiceRef(TrackDeliveryService.class)
  private TrackDeliverySEI deliveryService;

  public String checkOrderDeliveryStatus(String shipId) {

    ...
    String deliveryStatus = deliveryService.checkDeliveryStatus(shipId);
    ...
  }
}

The @WebServiceRef has a number of elements that can be used

Element Description
name The JNDI name for the web service, it gets bound to java:comp/env/<name> in the ENC
wsdlLocation The WSDL location for the ervice. If not specified, then it is derived from the referenced service class
type The Java type of the resource
value The service class; always a type extending java.xml.ws.Service
mappedName Vendor-specific global JNDI name for the service

Here are some best practices tips