user1552879
user1552879

Reputation: 99

Customize Json Output with Jersey and Jaxb

I am trying to create a simple web service which outputs using json, but am not getting the desired Json output.

POJO: package com.rest.resource;

import java.io.Serializable;
import javax.xml.bind.annotation.XmlElement;
import javax.xml.bind.annotation.XmlRootElement;

    @XmlRootElement
    @XmlAccessorType(XmlAccessType.FIELD)
    public class Track implements Serializable
       {

       @XmlElement
       String   singer   = "ABC";
       @XmlElement
       String   title    = "XYZ";
       }

Service:

import javax.ws.rs.Consumes;
import javax.ws.rs.GET;
import javax.ws.rs.POST;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import javax.xml.bind.JAXBException;
import com.rest.resource.Track;

@Path("/json/metallica")
public class JSONService
   {

   @POST
   @Path("/post")
   @Consumes(MediaType.APPLICATION_JSON)
   @Produces(MediaType.APPLICATION_JSON)
   public Track createTrackInJSON(final Track track)
      {
       return track;
      }

   @GET
   @Path("/get")
   @Produces(MediaType.APPLICATION_JSON)
   public Response getTrackInJSON() throws JAXBException
      {
      final Track track = new Track();
      return Response.status(201).entity(track).build();
      }

   }

On /get I get

{"singer":"ABC","title":"XYZ"}

but I want "track": {"singer":"ABC","title":"XYZ"} I am unable yo print the root element.

I tried using a CustomJAXBContextResolver class but did not work for me? Can anyone give an example of the same?

Upvotes: 3

Views: 1098

Answers (2)

Durandal
Durandal

Reputation: 5663

If you want to use the ContextResolver, you'd need to use the JSONConfiguration and switch the JSON Notation. You could do that by adding a class like this:

@Provider
public class MyJAXBContextProvider implements ContextResolver<JAXBContext> {

    private JSONJAXBContext trackCtx;

    public MyJAXBContextProvider() throws JAXBException {
        trackCtx = new JSONJAXBContext(JSONConfiguration.mappedJettison().build(), Track.class);
    }

    public JAXBContext getContext(Class<?> type) {
        if(type == Track.class) {
            return trackCtx;
        }

        return null;
    }

}

Adding that class produced this for me:

{"track":{"singer":"ABC","title":"XYZ"}}

For more info check out the Jersey Docs

Upvotes: 3

Camilo
Camilo

Reputation: 1909

You'd have to wrap Track with another object:

public class TrackWrapper {
  Track track;
  TrackWrapper(Track track) {
    this.track=track;
  }
}

and return an instance of TrackWrapper,

@GET
@Path("/get")
@Produces(MediaType.APPLICATION_JSON)
public Response getTrackInJSON() throws JAXBException
  {
  final TrackWrapper trackWrapper = new TrackWrapper(new Track());
  return Response.status(201).entity(trackWrapper).build();
  }

}

and just in case, if you're gonna use JSON only you don't need the JAXB annotations.

Upvotes: 1

Related Questions