Hi Mike,
thanks for writing that lengthy email.
Am 20.02.2013 um 03:30 schrieb mike thompson:
For me, the #2 method (placing paging in the body) is advantageous
for clients as they can just marshal the document body and get at the paging information
via normal ways. The other advantage is that all the state (prev and next are alternate
states for page results) is contained within the body. No need for the client to look up
in the header to and figure out the format to parse the object in the header (and also
know the key name for the header object). This all creates unneccessary work for the
client when marshalling is pretty much automatic (like with JSON and Javascript).
You also need to know the name of the Link object in the body - besides, the header
"Link:" is standard, so there is no guessing.
If you marshall into e.g. Java objects you also need to have a specialized class that has
sub-elements for paging and the real payload.
Or you marshall into a generic map and try to find the paging objects by their name.
How parsable is this format?
Link: <
http://foo/?page=3>; rel='next'
Link: <
http://foo/?page=1>; rel='prev'
This concrete format is out, as I have stated in the update to my blog post, because
URLConnection.getHeaderField() can not deal with it.
That leaves
Link: <
http://foo/?page=3>; rel='next', <
http://foo/?page=1>;
rel='prev'
It looks like a combination of formats that definately requires
custom parsing on the client side. I realize it is RFC 5988, but you would think they
could pick a more
consistent(parser friendly) format. Any idea how prevalent this is? I did a search and
couldn't find much but maybe I'm not aware of the right resources. I see that it
was
I do not think it makes sense to invent an own format. RFC 5988 is an accepted format.
a 'Proposed Standard' in 2010
[
http://datatracker.ietf.org/doc/rfc5988/] but not much activity since then. This deserves
more research time than I can give it but does raise an eyebrow.
So you are saying, the internet can not rely on SMTP email transport, because RFC822 did
not change since 1982? :-)
The fact alone that RFC 5988 is published as a RFC makes it a standard, as this means that
it went through a series of ietf-drafts before being accepted
as RFC.
And for parsing I guess in almost all languages other than java, this can be expressed in
two lines :)
But then parsing { 'paging' : [ {
"url":"http://foo...","rel":"next"},{....}]} is
not obvious either.
One big argument against adding the paging info to the body for me is that for all clients
that are out there,
adding the paging info in the body will break them.
To stay backwards compatible we would already need to generate custom media types for
paging.
For those not familiar with HATEOAS, here is Bill Burke's definition for java
developers:
"I’ve explained HATEOAS with this analogy to Java developers. Imagine, a Java Swing
app passing value objects to a remote Hibernate service and merging the changes. Instead
of Java objects are your value objects, think of XML or JSON. Now add the idea of
embedding links into your XML or JSON that tell you where you can edit the service that
represents these value objects, or links to other services related to this data."
If you look at the RestEasy documentation, Bill very much supports the Link: headers
Leaving everything in the body also sets a better precedent for state other than paging
(HATEOAS) that should go into the doc body. HATEOAS is an essential part of
This argument is totally bogus, as e.g. the media type is not selected in the body, but
via header
REST and its use should be encouraged. REST representations are meant
to support alternate states and allow for easy discoverability by the client. The
And you request the representations via header field.
encapsulated states sent to the client make for less logic on the
client (meaning less brittle client applicatons). For instance, encapsulated states can be
sent to the client to provide state machines or validation rules and cached by the client,
cutting down the number of round trips to the server.
That is all correct what you say, but has no effect on the placement of the paging
headers.
Pragmatically, the way our REST APIs will be used is primary via
CL/I(javascript) so not having to reach into the header and parse pagnation data will make
much simpler/powerful integration scripts for our customers (IMO).
What makes you think this is true? We have an Android app, that works via REST-api -
adding the paging stuff to the body breaks that app
It will also break all the examples that we have that return collections. How does adding
the paging to the body make those existing clients
less brittle?
I do believe the header is a good place to store non-state data that
is not dependent on the on the body or relates to the body. Self describing meta-data
comes to
Paging links are not state representations of objects - switching a page does not modify
the objects.
We will probably want to add self, first and last to prev/next
regardless of the outcome of where to put this data. Also useful, would be record counts
and/or page
counts. Record counts via HEAD could provide client with insight as to whether or not
they should retrieve resources via a GET.
Right. I have already added the page count and may add the others too.
A client starts from the first page, and then through the link on
that page, goes to the second page. The fact that this page has one link to the first page
and another to the third page implies that the current state of the application (i.e. the
interactions) is that "the client is viewing the second page". That is what it
means by hypermedia as the engine of application state. It does not necessarily mean
serializing application state, such as "<page>2</page>" into
representations."
Yes totally. Which is what we largely do already.
Heiko