1

I'm developing a REST API in order to transfer data from a client application to a web application.

So far it all worked well: I created my entity objects in the client application and then serialized them with Jersey into XML/JSON and called PUT, on the other end a Resource listened for PUT and magically serialized them into Objects ready to be persisted with JPA.

Below is a sample of an entity Album with annotations and the associated Resource.

@XmlRootElement
@Entity
public class Album
{
    @Id
    private String id;
    private String name;

    @ManyToMany(cascade = CascadeType.ALL)
    private Collection<Photos> photos;

    // getters/setters
} 


@ApplicationPath("webresources")
@Path("/album")
@Stateless
public class AlbumResource extends Application
{
    @PUT
    @Path("/add")
    @Consumes(
    {
        MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML
    })
    public Response addAlbum(Album album)
    {
        try
        {
            getAlbumEJB().create(album);
        }
        catch (Exception ex)
        {
            Logger.getLogger(AlbumResource.class.getName()).log(Level.SEVERE, null, ex);
        }
        if (!exception)
        {
            return Response.status(201).entity(album).build();
        }
        else
        {
            return Response.status(403).entity(album).build();
        }
    }
}

The above worked well even though according to some sites this is a classic anti-pattern of "Conflating models and resources" (see for instance http://jacobian.org/writing/rest-worst-practices/). Their reasoning is that the above example would collapse, indeed to update an Album name I would need to re-send a PUT with a whole photos collection, in a more articulated example I would end sending tons of useless data just to honour relations between objects.

They however don't point out a regular solution so I came up with this rather convoluted solution to keep mapping models and resources together and thus exploit automatic serialization:

I would basically send from the client a new entity "RESTAlbum" where instead of a collection of Photos as the "Album" entity it would contain a collection of links to photos:

<Album>
    <id>73</id>
    <name>Great Album</name>
    <photosCollection>
    <photo>
      <href>htttp://example.com/photo/211</href>
    </photo>
    <photo>
      <href>htttp://example.com/photo/232</href>
    </photo>
    </photosCollection>
</Album>

on the server side end I would serialize RESTAlbum and would fetch each photo entity based on its URL and construct manually an Album entity which I would be able to serialize with JPA.

Is the above the only way to go?

It seems like quite a lot of work to create all this custom classes just to serialize relations and strangely all the web is full of REST purists but noone talking about issues like this.

4

0 回答 0