RESTful Web services with Apache Wink, Part 2: Advanced topics in Apache Wink REST development

Annotations, integrations, and more

This article, the second in a three-part series, explores advanced topics in Apache Wink 1.0 development, a new Java™ framework for implementing and consuming REST-based Web services.

Share:

Vishnu Vettrivel , Principal Consultant, PunditLabs

Photo of Vishnu VettrivelVishnu Vettrivel is the Principal Consultant at PunditLabs, which specializes in enterprise consulting and technology, and he has over a decade of experience in architecting, designing, designing, and developing mission-critical enterprise applications. Having worked extensively for Fortune 50 clients, he has helped craft strategic technical plans for many emerging technologies. You can reach him at vishnu@punditlabs.com.



09 March 2010

Also available in Chinese Japanese

This article explores advanced topics related to Apache Wink version 1.0 development, including the use of additional annotations, integration of Wink services with the popular Spring Framework, and implementation of a custom RESTful client using the Apache Wink Client framework.

Frequently used acronyms

  • API: Application programming interface
  • CSV: Comma-separated values
  • HTTP: Hypertext Transfer Protocol
  • JSON: JavaScript Object Notation
  • MIME: Multipurpose Internet Mail Extensions
  • RSS: Really Simple Syndication
  • URI: Uniform resource identifier
  • XML: Extensible Markup Language

Annotate this!

In JAX-RS, annotations are one of the main mechanisms used to inject the incoming HTTP request information into Java™ methods. As a JAX-RS-compliant framework, Apache Wink implements the annotations that are required according to the specification, but it also provides various other annotations that are not mandatory, such as the @Asset annotation and the @Scope annotation.

The @Asset annotation

An @asset annotation is used as a marker to identify a Java class as an asset. An asset is a special form of entity object that a resource method returns. The Apache Wink run time can also inject an asset into a resource method as a parameter. The asset is a data model container object that provides transformation methods for various content types. Assets are used to pass information between a resource and a provider and help reduce the number of registered providers in the Apache Wink system. This is important, as provider bloat can lead to system performance degradation in the Wink system.

Listing 1 demonstrates the use of the @asset annotation. The Transaction bean is a Java Architecture for XML Binding (JAXB) class.TransactionAsset class. The TransactionAsset class wraps an instance of a Transaction bean as shown here.

Listing 1. TransactionAsset class
@Asset
public class TransactionAsset {
	public Transaction transaction;   						
	public TransactionAsset(Transaction transaction) {
		this.transaction = transaction;
    }
 	@Produces("application/xml")
    public Transaction getTransaction() {
        return this.transaction;
    }
	@Consumes("application/xml")
	public void setTransaction(Transaction transaction) {
		this.transaction = transaction;
    }
}

This asset class is returned by a resource method as a response or can be passed in as a parameter. The Apache Wink run time uses the asset class to construct the actual response entity by calling the corresponding method of the asset class.

The @Scope annotation

According to the JAX-RS specification, by default, provider and resource classes are instantiated once for each JAX-RS application. This instantiation involves the default constructor for the class being called, with the injection of dependencies happening afterwards.

The corresponding methods on the provider and resource objects can be called multiple times during the life of the object before being made available for garbage collection. Apache Wink offers other life cycles for providers and resources through the @Scope annotation. Listing 2 shows how to define a resource with a prototype (per-request) life cycle.

Listing 2. @Scope example
@Scope(ScopeType.PROTOTYPE)
@Path("helloworld")
public class HelloWorldResource {
    ...
}

In a prototype life cycle, the Apache Wink run time instantiates a new object for every incoming request. Even though this behavior might not be ideal from a memory/performance perspective, it frees you from having to worry about threading and concurrency issues in resource and provider classes.

The @Parent annotation

Part 1 of this series discussed the @Path annotation in detail and pointed out that it is used in JAX-RS to define a URI matching pattern for incoming requests. It is usually placed in a Java class or method.

The @Parent annotation is closely "related" to the @Path annotation, providing the base URI for the one specified in a resource. If the Apache Wink run time encounters the @Parent annotation in a resource, it tries to calculate the final resource URI template by first calculating the value of the @Parent annotation that holds the URI of the parent resource class, after which it tries to concatenate the resource path URI to that of the parent resource. Listing 3 provides an example of the @Parent annotation.

Listing 3. @Parent example
@Path("parentservice")
public class ParentResource {
    ...
}

@Parent(ParentResource.class)
@Path("childservice")
public class ChildResource {
    ...
}

In this example, there are two resources: ParentResource and ChildResource. ParentResource defines the @Path annotation to be the parentservice URI. ChildResource defines the @Path annotation to be the childservice URI. ChildResource also defines ParentResource to be its parent by using the @Parent annotation. In this example, the Apache Wink run time resolves the final URI path for ChildResource to be parentservice/childservice.


Administration views

To help developers gain a better understanding of their RESTful Web services, Apache Wink provides two types of administration views: The Application Resource XML view and the Resource Registry XML view. By default, both of these views are disabled, and you must register the org.apache.wink.server.internal.servlet.AdminServlet class in the application web.xml file to activate them.

The Application Resources XML view exposes the REST resources along with their URI templates, HTTP methods, and the MIME types that each method supports, similar to the manner in which the application has been made available to users. This view is useful for generating automated service documentation for the deployed services.

The Resource Registry XML view is more detailed than the Application Resources XML view and displays the actual implementation details of the services exposed, including the class names that implement resources and their priorities in the registry. This view is useful for debugging purposes but should not be enabled in production, as it might compromise security by revealing implementation details.


WebDAV support

Web-based Distributed Authoring and Versioning (WebDAV) is a set of extensions to the core HTTP protocol that enables users to edit and manage files on Web servers like Apache Web Server. Some of the main features of the WebDAV protocol include:

  • Locking files
  • File properties or metadata
  • File name space management

Apache Wink supports the WebDAV protocol through an extension module. The Apache Wink extension module contains the WebDAV XML model and a WebDAV response builder to help with creation and processing of WebDAV responses.


Spring into action

Spring is a popular open source Java framework and was originally meant to be a lightweight alternative to existing Java standards like Enterprise JavaBean (EJB) technology. Similar to the EJB standard, the Spring Framework also provides capabilities for transactions, persistence, security, and—more importantly—dependency injection, a concept from which JAX-RS also borrows. For more details about the Spring Framework, refer to Resources.

Apache Wink provides easy Spring integration through an additional module that comes with the core framework. The Apache Wink Spring integration module provides the following main features:

  • Registering resources and providers as classes or Spring beans from within the Spring context
  • Defining resources/provider life cycle and overriding the default singleton scope
  • Using Spring features like Inversion of Control (IoC) and postprocessors
  • Customizing Apache Wink through easy customization hooks from within the Spring context

Spring context loading

In the Spring Framework, the Spring context is similar to the Apache Wink application and has to be loaded before any of the other Spring beans can be defined and loaded. Once the Spring context has been loaded, it is easy to register resources and providers as Spring beans.

To load the Spring context, you must first define and add the context load listener to the web.xml file of the Web application. Also, the contextConfigLocation context-param should indicate the location of the Apache Wink core context file and the application-specific context file. Listing 4 provides an example of the web.xml file that defines and loads the Spring context.

Listing 4. Spring context loading web.xml
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:META-INF/server/winkCoreContext-server.xml
	classpath:mySpringcontext.xml
</param-value>
</context-param>
<listener>
<listener-class>
	org.springframework.web.context.ContextLoaderListener
  	</listener-class>
</listener>

Resource and provider registration

When the Spring context has been loaded, you can register resources and providers using the org.apache.wink.spring.Registrar class that Apache Wink provides. The Registrar class is an extension of the familiar WinkApplication class and has to be defined as a spring bean, first.

It is possible to define the following properties using the Registrar class:

  • Instances. Resource and provider instances are typically defined as Spring beans that automatically gain IoC and other Spring functionality.
  • Classes. The class names of the resources and providers defined; this property is the same as that of the getClasses method in the Wink Application class.
  • Priority. This property defines the priority of the WinkApplication.

Listing 5 is an example of the Spring bean configuration file that defines Apache Wink resources and providers as Spring beans.

Listing 5. Spring configuration file mySpringcontext.xml
<bean class="org.apache.wink.spring.Registrar">
  <property name="classes">
    <set value-type="java.lang.Class">
      <value>org.openengine.example.TransactionResource</value>
    </set>
  </property>
  <property name="instances">
    <set>
      <ref bean="resources.TransactionResource"/>
      <ref bean="providers.myprovider"/>
    </set>
  </property>
</bean>

Wink as a client

Apart from being a JAX-RS-compliant server framework, Apache Wink comes with a sophisticated client framework. The Apache Wink client framework provides a simple Java API to make the task of implementing clients to consume HTTP-based RESTful Web services easy and straightforward. The Apache Wink client framework also has a customizable handler mechanism to manipulate HTTP requests and responses. Apache Wink clients are built on JAX-RS principles and encompass REST-based concepts and standards. By mapping REST-driven ideas to Java classes, they not only help to develop clients for Apache Wink-based services but any HTTP-driven RESTful Web service. This makes them really useful as a stand-alone REST-based Java client framework.

Listed below are some of the main features of the Apache Wink client framework:

  • Serializes and de-serializes resources using configurable JAX-RS providers
  • Provides built-in support for various content types, including Atom, JSON, RSS, APP, CSV, and Multipart, along with corresponding object models in Java
  • Provides support for Secure Sockets Layer (SSL) and HTTP proxies
  • Similar to the server-side framework, the client framework has a configurable handler chain for manipulating HTTP requests and responses
  • Uses the java.net.HttpUrlConnection class for its core HTTP transport by default
  • Allows for easy customization of the core HTTP transport mechanism

The diagram in Figure 1 illustrates the architecture of the Apache Wink client framework.

Figure 1. Apache Wink client architecture
Four boxes on the left are labeled 'Resources.' These are all pointing to a box labeled 'Handler.' The line connecting them is labled 'Invoke method.' Above these boxes is a box labeled 'RestClient.' Below are two boxes labled 'Provider registry' and 'Configuration,' respectively.

As you can see, the Apache Wink client framework is mainly composed of the RestClient class, which acts as the central point of entry holding the various configuration and provider registries. In order to start working with the client framework, it is necessary to instantiate a new instance of the RestClient object. Then, you create an instance of the Resource class from it using the URI of the service you want to connect to. The Resource class is the Java equivalent of the RESTful Web resource associated with the specific URI and is used to perform HTTP-based operations on it. All HTTP method invocations are filtered through a customizable handler chain that enables easy manipulation of HTTP requests and responses.

GET request

Listing 6 demonstrates the use of an HTTP GET request using the Apache Wink client.

Listing 6. GET request example
// create the rest client instance
RestClient client = new RestClient();

// create the resource instance to interact with
Resource resource = client.resource("http://localhost:8080/HelloWorld");

// perform a GET on the resource. The resource will be returned as plain text
String response = resource.accept("text/plain").get(String.class);

As mentioned already, the RestClient object is the entry point for the Apache Wink client framework. To build a RESTful Web service client, you must instantiate a new instance of the RestClient object, after which a new Resource object is created with the URI of the service you want to invoke by calling the RestClient#resource() method. To issue an HTTP GET request, you invoke the Resource#get() method. This method returns the HTTP response. Then, by invoking the appropriate provider, the client is able to de-serialize the response.

POST request

Listing 7 demonstrates use of an HTTP POST request using the Apache Wink client.

Listing 7. POST request example
// create the rest client instance
RestClient client = new RestClient();

// create the resource instance to interact with
Resource resource = client.resource("http://localhost:8080 ");

// issue the request
String response = resource.contentType("text/plain").
			accept("text/plain").
				post(String.class, "foo");

As you can see, issuing the POST request is similar to issuing a GET request. Just like the GET request example, you create a new instance of a Resource through the RestClient. The only difference is that the POST string itself is passed in as a method parameter to the resource.post method after specifying the request and response media types and the response entity type. Once again, the response is returned as a string.

Atom client request

As mentioned above, the Apache Wink client framework also provides functionality to issue requests in multiple content types. Listing 8 provides an example that demonstrates issuing an HTTP POST request that sends and receives Atom entries.

Listing 8. Atom request example
// create the rest client instance
RestClient client = new RestClient();

// create the resource instance to interact with
Resource resource = client.resource("http://services.co");
AtomEntry request = getAtomEntry();

// issue the request
AtomEntry response = resource.contentType("application/atom+xml").
			accept("application/atom+xml").
				post(AtomEntry.class, request);

Because the Apache Wink client provides the object model for Atom that enables sending and receiving Atom feeds and entries, it is simple to issue Atom requests and parse responses using AtomEntry objects.


Conclusion

This article outlined some advanced topics related to the Apache Wink 1.0 framework, including annotations, administration views, and WebDAV support. You also saw how Apache Wink supports Spring integration through a built-in extension module and got an in-depth look at the Apache Wink client framework and its underlying architecture. Stay tuned for Part 3 of this series for a comparative study of Apache Wink and other JAX-RS-compliant frameworks, as well as a discussion of their relative strengths and weaknesses. If you would like to learn more about REST, JAX-RS, or the Apache Wink 1.0 framework, refer to Resources.

Resources

Learn

Get products and technologies

Discuss

Comments

developerWorks: Sign in

Required fields are indicated with an asterisk (*).


Need an IBM ID?
Forgot your IBM ID?


Forgot your password?
Change your password

By clicking Submit, you agree to the developerWorks terms of use.

 


The first time you sign into developerWorks, a profile is created for you. Information in your profile (your name, country/region, and company name) is displayed to the public and will accompany any content you post, unless you opt to hide your company name. You may update your IBM account at any time.

All information submitted is secure.

Choose your display name



The first time you sign in to developerWorks, a profile is created for you, so you need to choose a display name. Your display name accompanies the content you post on developerWorks.

Please choose a display name between 3-31 characters. Your display name must be unique in the developerWorks community and should not be your email address for privacy reasons.

Required fields are indicated with an asterisk (*).

(Must be between 3 – 31 characters.)

By clicking Submit, you agree to the developerWorks terms of use.

 


All information submitted is secure.

Dig deeper into Web development on developerWorks


static.content.url=http://www.ibm.com/developerworks/js/artrating/
SITE_ID=1
Zone=Web development
ArticleID=472565
ArticleTitle=RESTful Web services with Apache Wink, Part 2: Advanced topics in Apache Wink REST development
publish-date=03092010