February 18, 2010

Using Jersey to (un)marshall Java objects

When developing a REST API in Java, it is straightforward when you do that using Jersey. At least when implementing the server side. For instance, we can have the following methods to manage a Foo object:

@GET
@Path("{fooId}")
@Produces("application/xml")
public Foo getFoo(@PathParam("fooId") int fooId) {
return FooBean.getInstance().findFoo(fooId);
}

@GET
@Path("/list")
@Produces("application/xml")
public List<Foo> getFoos() {
return FooBean.getInstance().findAllFoos();
}

@PUT
@Produces("application/xml")
public Foo putFoo(@FormParam("name") String name, @FormParam("bar") String bar) {
Foo foo = new Foo();
foo.setName(name);
foo.setBar(bar);
return FooBean.getInstance().createFoo(foo);
}

@POST
@Path("/{fooId}")
@Produces("application/xml")
public Foo updateFoo(@PathParam("fooId") int fooId, @FormParam("name") String name, @FormParam("bar") String bar) {
Foo foo = FooBean.getInstance().findFoo(fooId);
if (foo != null) {
foo.setName(name);
foo.setBar(bar);
return FooBean.getInstance().updateFoo(foo);
}

return null;
}

@DELETE
@Path("/{fooId}")
public void deleteFoo(@PathParam("fooId") int fooId) {
FooBean.getInstance().deleteFoo(fooId);
}


The Foo class must be annotated with @XmlRootElement, otherwise Jersey won't know how to marshall the object into XML or JSON.

@XmlRootElement
public class Foo implements Serializable {
private int id;
private String name;
private String bar;
...
}


Recently I discovered that you can also use Jersey when developing client applications that make use of a REST API. The Jersey Client API, as it is called, can be used to easily produce and consume REST requests and responses. The code below shows a quick overview of how to call the methods listed above.

Client client = Client.create();

WebResource wr = client.resource("http://localhost:8080/jm/rest/foo");

// getting a single Foo object
Foo foo = wrGetFoo.path("/1").get(Foo.class);

// getting a list of Foo objects
List<Foo> foos = wr.path("/list").get(new GenericType<List<Foo>>() {});

// creating a Foo object
MultivaluedMap params = new MultivaluedMapImpl();
params.add("name", "Foo2");
params.add("bar", "bar2");
Foo foo2 = wr.put(Foo.class, params);

// updating a Foo object
params.clear();
params.add("name", "Foo2");
params.add("bar", "bar2updated");
foo2 = wr.path("/" + foo2.getId()).post(Foo.class, params);

// deleting a Foo object
wr.path("/" + foo2.getId()).delete();


As you can see, the methods on the WebResource class map perfectly with the HTTP methods generally used in a REST API: GET, POST, PUT and DELETE. You can download the sample project, jerseymarshall.zip, which contains two NetBeans projects: a web project for the server side and a plain java project for the client side.

3 comments:

Anonymous said...

Great post! This is something I was looking for for a long time. Keep up the good work!

NBA jerseys said...

This is exactly what I've been searching for. Thanks!

Smith said...

Hi, Great.. Tutorial is just awesome..It is really helpful for a newbie like me.. I am a regular follower of your blog. Really very informative post you shared here. Kindly keep blogging. If anyone wants to become a Java developer learn from Java EE Online Training from India. or learn thru Java EE Online Training from India . Nowadays Java has tons of job opportunities on various vertical industry.