Quantcast
Channel: Planet Apache
Viewing all articles
Browse latest Browse all 9364

Glen Mazza: Converting between RESTEasy's ClientRequest and CXF's WebClient

$
0
0

As there is no client API defined in JAX-RS 1.1, both RESTEasy and CXF provide a product-specific API to simplify REST calls. For RESTEasy, the class is ClientRequest for requests and the JAX-RS Response subclass ClientResponse for responses; CXF has WebClient and does not presently subclass Resource. Not covered here, but both also provide proprietary client proxies (CXF) (RESTEasy), which reuse a root resource's Java interface to construct REST client calls. If client-side REST implementation independence is desired, the more verbose java.net.HttpURLConnection and Apache HttpClient are options.

I'm showing below some of the syntactical differences between ClientRequest and WebClient, helpful for converting a client from one JAX-RS implementation to the other. These differences are rather minor as I learned when converting the RESTful Java book examples 9-1 and 9-2 from RESTEasy to CXF. The CustomerResourceTest class in Example 9-1, for example, just needs these changes:

package com.restfully.shop.test;

import com.restfully.shop.domain.Customers;
// import org.jboss.resteasy.client.ClientRequest;  // RESTEasy
import org.apache.cxf.jaxrs.client.WebClient;  // CXF
import org.junit.Test;

/**
 * @author Bill Burke
 * @version $Revision: 1 $
 */
public class CustomerResourceTest
{
   @Test
   public void testQueryCustomers() throws Exception
   {
      String url = "http://localhost:9095/customers";
      while (url != null)
      {
//       ClientRequest request = new ClientRequest(url);  // RESTEasy
         WebClient wc = WebClient.create(url);  // CXF
//       String output = request.getTarget(String.class);  // RESTEasy
         String output = wc.get(String.class);  // CXF

         System.out.println("** XML from " + url);
         System.out.println(output);

//       Customers customers = request.getTarget(Customers.class);  // RESTEasy
         Customers customers = wc.get(Customers.class);  // CXF
         url = customers.getNext();
      }
   }
}

The OrderResourceText class in Example 9-2 is lengthier and shows a few more differences between RESTEasy and CXF:

  • RESTEasy's Response subclass provides a getHeaders() convenience method that returns a Map of Strings instead of Objects, while CXF JAX-RS relies on the standard Response getMetadata() that requires subsequent casting of the Objects to Strings:

    RESTEasy:
    List<String> linkHeaders = (List<String>) response.getHeaders().get("Link");
    CXF JAX-RS:
    List<Object> linkHeaders = response.getMetadata().get("Link");
  • Setting the body for a POST call and making the calls consists of two steps with RESTEasy, one with CXF JAX-RS. CXF also does not need the body type ("application/xml") as it apparently relies on the JAXB XmlRootElement annotation on the Customer object:

    RESTEasy:
    Customer customer = new Customer();
    ...populate Customer...
    request = new ClientRequest(customers.getHref());
    request.body("application/xml", customer);
    response = request.post();
    Assert.assertEquals(201, response.getStatus());
    
    CXF JAX-RS:
    Customer customer = new Customer();
    ...populate Customer...
    wc = WebClient.create(customers.getHref());
    response = wc.post(customer);
    Assert.assertEquals(201, response.getStatus());
    
  • For GETs, RESTEasy splits out the call from the retrieval of the result, while they are combined in the same step with CXF JAX-RS:

    RESTEasy:
    System.out.println("** New list of orders");
    request = new ClientRequest(orders.getHref());
    response = request.get();
    System.out.println(response.getEntity(String.class));
    
    CXF JAX-RS:
    System.out.println("** New list of orders");
    wc = WebClient.create(orders.getHref());
    System.out.println(wc.get(String.class));
    

Viewing all articles
Browse latest Browse all 9364

Trending Articles