Hi,
I'm designing & implementing my first REST-style API. It's for an
existing application. I'm using Restlet 1.1-M1 and have found it very
cleanly designed and easy to use.
I've run into a problem where I can't seem to implement one of the
resources in the way that makes most sense to me because Restlet's
Resource considers a PUT without an entity to be automatically invalid
(i.e., it responds with 400 Bad Request before calling
storeRepresentation). I hope if I can explain what I'm trying to do,
someone can suggest a better way, or at least explain why what I'm
trying is wrong.
The resource in question represents a link between instances of two
other resources. Relationally, the link is many-to-many and is not
logically owned by one end or the other of the relationship. The link
logically contains two collections of other resources, but neither of
them is known at the time the link itself is created. (In fact, the
user group which can create the link is different from the ones which
can update the collections.) I'm trying to implement the API like this:
/resource1/{r1_identifier}
- GET: XML representation of resource1
- PUT: XML rep to create or update
/resource2/{r2_identifier}
- GET: XML representation of resource2
- PUT: XML rep to create or update
/resource1/{r1_identifier}/resource2/{r2_identifier} <-- the link
resource
- GET: return 200 if the link exists or 404 if it doesn't
- PUT: create link if both r1 and r2 exist
- DELETE: delete link
/resource1/{r1_identifier}/resource2/{r2_identifier}/collection1
- GET: XML rep of collection
- POST: add to collection
/resource1/{r1_identifier}/resource2/{r2_identifier}/collection2
- GET: XML rep of collection
- POST: add to collection
The key thing here, I think, is that write access to the /resource1/
{r1_identifier}/resource2/{r2_identifier} is limited to one group of
users. Read and write access to the collections belongs to another
group, so they have to be separate resources -- they can't be treated
as part of the link resource.
Is there a better way to model the resources in this case? Or is it
reasonable to have PUT without an entity (i.e., restlet needs to be
changed)? I know that, e.g., Amazon S3 supports PUT without an entity
to create a bucket with default settings. The HTTP spec seems
ambiguous on this point -- it says PUT should accept the entity as the
new representation of the resource, but it never says that the entity
has to be non-empty (RFC2616 section 9.6).
Thanks for any suggestions,
Rhett