jsr339-experts@jax-rs-spec.java.net

[jsr339-experts] Re: [jax-rs-spec users] Re: Hypermedia Proposals

From: Marek Potociar <marek.potociar_at_oracle.com>
Date: Thu, 21 Jul 2011 15:12:12 +0200

Btw. just to make sure I'm not misunderstood - I am not against a programmatic API for links in general. IMHO, we should
look into ways how to provide such API without raising the concerns described in my previous email.

Marek

On 07/21/2011 03:08 PM, Marek Potociar wrote:
> Hi Guilherme,
>
> On 07/20/2011 05:43 PM, Guilherme Silveira wrote:
>> Hi Marek!
>>
>> I did not want to send one simple example with three lines so the smaller examples where you asked "why are they there"
>> are to contextualize step by step.
>>
>>> I am interested in how "serializer.link("self").to(this).find(id);" is supposed to work:
>>> - does the proxy (I just presume it's a proxy) returned by ".to(this)" actually invoke the "find" method on "this"?
>> No, it does a reverse lookup (method => URI), that's the idea of the proxy.
>
> I thought so. While I trully appreciate the elegance of the idea (really!), I have serious objections at the same time -
> see below.
>
>>
>>> If
>> yes, what about cases when the redundant method invocation is expensive?
>> (no, from the previous one).
>>
>>> If not, what if the proxy is accidentally used in place of the actual instance of <T>?
>> I can't see right now where it makes sense for a dev to have a local variable pointing to "this" and then mixing it up
>> with the proxy:
>> MyResource mr = this;
>> MyResource mr = serializer.link("self").to(this);
>> mr.find();
>>
>> The first line is really ackward. And if no dev writes it (hopefully nobody does), the other two lines have the same
>> effect of writing in one or two lines of code.
>
> My problem with the proposed approach is a more fundamental one: I'm afraid that suggested proxy implementation ignores
> the original contract declared by the resource method and violates the Liskov substitution principle. IOW, suppose the
> following method definition e.g.:
>
> public File thumbnailForClient(Long clientId, ClientController controller) {
> return controller.find(clientId).getThumbnail();
> }
>
> And ClientController variables initialized as:
>
> ClientController cc1 = new ClientController();
> ClientController cc2 = serializer.link("...").to(cc1);
>
> Then invoking thumbnailForClient(...) using cc1 and cc2 would yield different results for the same clientId, which I
> have trouble accepting, no matter how rarely possible such situation is. Also consider the following potential javadoc
> for the same method:
>
> /**
> * Retrieve all items with the same name.
> * This method never returns null. If no items are found, returns empty List.
> */
> public List<Item> getForName(String name);
>
> /**
> * Retrieve all items with the same name.
> * This method never returns null. If no items are found, a new Item with the name
> * is automatically created and returned as a single-item list.
> */
> public List<Item> getForName(String name);
>
> How would the proxy implementor ensure that the proxy can always return at least a valid value as declared in the
> proxied method documentation, which is part of the method API contract?
>
>>
>>> 4. Explicit variable mapping
>>> https://github.com/caelum/jaxrs2-caelum/commit/9ba9179e9f2dce71e0a36c8e7c7ab857579ce0bb#L11R44
>>> How would the implicit variable mapping look like in this case?
>> Sorry, this one is already implicit, not explicit.
>>
>>> 6. Header based link generation
>>> The pattern used here raises the same questions as the example 2. Also, I wonder what is the true purpose of Result and
>> where its instances come from.
>> Same answers for the pattern. Result is injected and is the explicit access for the view layer in mvc. Once its
>> injected, its ok.
>>
>>> I think we discussed this quite a long time ago
>> I posted the idea again because the hypermedia linking and configuration topic has been in discussion now, and before
>> that it I understood the discussion was only to prioritize the items. Please let me know if I am not supposed to post
>> something as I understood I should when I asked it a few emails again.
>>
>>> and I still believe that such low level details on the server-side
>> should not be part of the spec because of the constraints they impose upon the impl. providers. Also, I found it
>> somewhat challenging to understand functionality of the examples above, which I would attribute mainly to the
>> customizable conveniences aspect of the whole thing. As a matter of fact, I prefer to keep JAX-RS more strict to ensure
>> it's consistently readable without any surprises caused by some customization hidden in a small class in the project's
>> class hierarchy or worse, in some of the libraries used by the project.
>> The + and - for providing strict rules x allowing configuration are well known by all of us, so in the end it's just a
>> choice the spec leaders take.
>>
>>> I don't share such view - even with annotations a XML config file still plays an important role once the application is
>>> deployed to production and it needs to be configured externally.
>> I agree, configuration that changes between development and production are easily configured through XML (not
>> annotations). But I think its different for configuration that does not change between them, as in URI mappings.
>
> I can agree with that. I was objecting to the generalized statement that we "ran away from XML as a description language
> for configuration".
>
> Cheers,
> Marek
>
>>
>> Regards
>>
>> Guilherme Silveira
>> Caelum | Ensino e Inovação
>> http://www.caelum.com.br/
>>
>>
>> On Sat, Jul 16, 2011 at 12:23 PM, Marek Potociar <marek.potociar_at_oracle.com <mailto:marek.potociar_at_oracle.com>> wrote:
>>
>> Hi Guilherme
>>
>> On 07/13/2011 07:22 PM, Guilherme Silveira wrote:
>> > This is connected with the proposal you asked me to send in. Time to
>> > send it although the schedule has changed... here it is:
>> >
>> > 1. A simple request action. Will render the clients using conneg.
>> > https://github.com/caelum/jaxrs2-caelum/commit/9ba9179e9f2dce71e0a36c8e7c7ab857579ce0bb#L11R24
>> > 1.b. Same thing, optional Path so one can use multiple verbs (if it makes sense)
>> > https://github.com/caelum/jaxrs2-caelum/commit/9ba9179e9f2dce71e0a36c8e7c7ab857579ce0bb#L11R31
>>
>> Maybe I am missing the context - what is the above supposed to showcase?
>>
>> >
>> > 2. Serializing links in the controller: not mixing view concerns with
>> > the model, leaving it at the controller.
>> > Typesafe. Refactor friendly.
>> > https://github.com/caelum/jaxrs2-caelum/commit/9ba9179e9f2dce71e0a36c8e7c7ab857579ce0bb#L11R37
>> >
>>
>> I am interested in how "serializer.link("self").to(this).find(id);" is supposed to work:
>>
>> - does the proxy (I just presume it's a proxy) returned by ".to(this)" actually invoke the "find" method on "this"? If
>> yes, what about cases when the redundant method invocation is expensive? If not, what if the proxy is accidentally used
>> in place of the actual instance of <T>?
>>
>> > 3. Interceptor example
>> > If you return File, InputStream or similar ones, its a download. An
>> > example of how custom conventions can be created using interceptors.
>> > Conventions like this one can be created for one JAX-RS implementation
>> > and used in *any* of them without any change of code... different from
>> > string based features.
>> > https://github.com/caelum/jaxrs2-caelum/commit/9ba9179e9f2dce71e0a36c8e7c7ab857579ce0bb#L11R46
>> >
>>
>> Again, I am perhaps missing the context. Or maybe I don't see where/how the convention you refer to is established.
>>
>> > 4. Explicit variable mapping
>> > https://github.com/caelum/jaxrs2-caelum/commit/9ba9179e9f2dce71e0a36c8e7c7ab857579ce0bb#L11R44
>> > I prefer implicit one, but people might argue that reading debug
>> > information is nasty. So we can give the option, of course
>>
>> How would the implicit variable mapping look like in this case?
>>
>> >
>> > 5. Explicit entity unmarshalling
>> > https://github.com/caelum/jaxrs2-caelum/commit/9ba9179e9f2dce71e0a36c8e7c7ab857579ce0bb#L11R50
>> > With the use of an extra interceptor (as the previous one) one can
>> > handle generic cases such as 404, 401, etc
>>
>> I am sorry, but again, what is the context here? What is the purpose of the @Consumes annotation introduced in the
>> example?
>>
>> >
>> > 6. Header based link generation
>> > This one generates 303, a hyperlink to another part of the system.
>> > Again, type safe. Refactor friendly. Non annotation based. No need
>> > for an extra description language (that will offer the same limits of
>> > other annotation based expression languages):
>> > https://github.com/caelum/jaxrs2-caelum/commit/9ba9179e9f2dce71e0a36c8e7c7ab857579ce0bb#L11R55
>> >
>>
>> The pattern used here raises the same questions as the example 2. Also, I wonder what is the true purpose of Result and
>> where its instances come from.
>>
>> > 7. Programmatic route configuration
>> > If the user likes it. Mostly used by plugin providers to add the
>> > conventions they wish.
>> > https://github.com/caelum/jaxrs2-caelum/commit/9ba9179e9f2dce71e0a36c8e7c7ab857579ce0bb#L14R11
>> >
>> > 8. Default parameter names
>> > Explicit linking. Implementor can generalize it to use the debug
>> > information, the type name, an annotation or anything else. The JAX-RS
>> > spec can force one option (such as the annotation) and leave room for
>> > implementors to add support for, i.e. the debug information one. The
>> > first vendor to support it is also providing the same support to all
>> > other vendors, without too much effort.
>> > https://github.com/caelum/jaxrs2-caelum/commit/9ba9179e9f2dce71e0a36c8e7c7ab857579ce0bb#L14R20
>>
>> I think we discussed this quite a long time ago and I still believe that such low level details on the server-side
>> should not be part of the spec because of the constraints they impose upon the impl. providers. Also, I found it
>> somewhat challenging to understand functionality of the examples above, which I would attribute mainly to the
>> customizable conveniences aspect of the whole thing. As a matter of fact, I prefer to keep JAX-RS more strict to ensure
>> it's consistently readable without any surprises caused by some customization hidden in a small class in the project's
>> class hierarchy or worse, in some of the libraries used by the project.
>>
>> > Of course, the main reason that I see on running away from annotation
>> > based languages is that we already have Java. We ran away from XML as
>> > a description language for configuration only to arrive at Annotations
>> > as a description language for configuration... hmmm..
>>
>> I don't share such view - even with annotations a XML config file still plays an important role once the application is
>> deployed to production and it needs to be configured externally. Annotation-based configuration is primarily meant for
>> the development phase, so that developers do not have to switch back and forth between Java & XML files.
>>
>> Marek
>>
>> >
>> > So those are multiple examples of how linking can be done and - on the
>> > way - I've ended up creating the interfaces for the MVC part so we
>> > don't force users to break MVC or DDD concepts.
>> >
>> > Regards
>> >
>> > Guilherme Silveira
>> > Caelum | Ensino e Inovação
>> > http://www.caelum.com.br/
>> >
>> >
>> >
>> > On Wed, Jul 13, 2011 at 11:20 AM, Santiago Pericas-Geertsen
>> > <Santiago.PericasGeertsen_at_oracle.com <mailto:Santiago.PericasGeertsen_at_oracle.com>> wrote:
>> >> Markus, Guilherme,
>> >>
>> >>> Same point of view on Annotation based link generation: annotations
>> >>> are (way too) limited and usually imply in using yet another language
>> >>> for describing "cases".
>> >>
>> >> If we don't use something like EL, then I think a Java API sans annotations would be preferable. However, I'm
>> not convinced that such an alternative provides the same level of ease of use.
>> >>
>> >> Guilherme: Is there a RestFulie example in which a model is serialized using links that we can look at?
>> >>
>> >> -- Santiago
>> >>
>> >>> 2011/7/7 Markus KARG <markus_at_headcrashing.eu <mailto:markus_at_headcrashing.eu>>:
>> >>>> Thank you for coming up with this proposal, which seems as a good starting
>> >>>> point for the discussion but looks a bit complex to the average user. I want
>> >>>> to propose the following "defaults", which helps a lot people and is less
>> >>>> complex than supplying all that parameters:
>> >>>>
>> >>>>
>> >>>>
>> >>>> @Ref.resource -- It should be possible to omit this, and instead declare
>> >>>> *once* the sole resource used for resolving this reference. That means,
>> >>>> rather than always giving the resource here, I instead would prefer to mark
>> >>>> one resource as the "main resolver" for references of this type in *all*
>> >>>> @Refs. Reason: An apple is an apple and will not become a peach at some
>> >>>> particular link. So it makes no sense to enforce repeating of the apple
>> >>>> resolver. In our already shipping application we solved this using a
>> >>>> registry that maps resources on reference types, but obviously it is much
>> >>>> smarter to just mark a resource using an annotation as "the apple resolver".
>> >>>>
>> >>>>
>> >>>>
>> >>>> @Ref.style -- Typically in the web resources are virtually always relatively
>> >>>> addressed (ever wrote http:// into <img src>?), so the default should be
>> >>>> RELATIVE. Also I think it is not dependend of the particular link but should
>> >>>> be a global setting. That means, I want to omit this parameter and instead
>> >>>> tell the resource "whenever you need to resolve @Ref, then please use
>> >>>> RELATIVE links". This reduces a lot of clutter. If anybody would ever want
>> >>>> ABSOLUTE style I assume he wants it for anything the resource does, not just
>> >>>> for one particular link.
>> >>>>
>> >>>>
>> >>>>
>> >>>> @Ref.bindings -- In our already shipping application we are not using
>> >>>> implicit bindings, i. e. we expect (unless otherwise specified) that the
>> >>>> parameter names are matching the JAXB's property names. It would reduce a
>> >>>> lot of clutter if we could agree upon such a fallback, so people only need
>> >>>> to give the bindings parameter in case of differing names.
>> >>>>
>> >>>>
>> >>>>
>> >>>> Using this defaults it would be possible to enable HATEOAS with just an
>> >>>> unparameterized @Ref written into the JAXB document. This is how we
>> >>>> implemented it in our current app, and we would be not very happy to get a
>> >>>> more flexible but more cluttering standard… :-)
>> >>>>
>> >>>>
>> >>>>
>> >>>> @Ref.condition -- Interesting idea, but the question is, whether there will
>> >>>> be any other conditions besides "is null"? If not, we can omit that, since
>> >>>> null will not get rendered by a JAXB marshaller anyways. If there are more
>> >>>> conditions, I would be more happy with a Java API than a String based
>> >>>> syntax. In our application we solved this by the general invention of a
>> >>>> "Constraint" interface (which is not HATEOAS dependend, but more general
>> >>>> like java.lang or java.util things are). This would not only run faster, but
>> >>>> also allows to syntax-check for typos (which always is hard to find).
>> >>>>
>> >>>>
>> >>>>
>> >>>> @Binding -- I would prefer not using String syntax here, too, due to the
>> >>>> same reasons.
>> >>>>
>> >>>>
>> >>>>
>> >>>> @Link -- Actually this looks scary. If I want to make the JAXB marshaller
>> >>>> render LINK headers instead of XML URLs, it should be sufficient to
>> >>>> configure that in one line instead of that huge code block. Something like a
>> >>>> boolean parameter set at the marshaller or like that. I do not think that it
>> >>>> should be part of the representation class itself, but more a general
>> >>>> rendering configuration.
>> >>>>
>> >>>>
>> >>>>
>> >>>> Regards
>> >>>>
>> >>>> Markus
>> >>>>
>> >>>>
>> >>>>
>> >>>> From: Santiago Pericas-Geertsen [mailto:Santiago.PericasGeertsen_at_oracle.com
>> <mailto:Santiago.PericasGeertsen_at_oracle.com>]
>> >>>> Sent: Mittwoch, 6. Juli 2011 21:09
>> >>>>
>> >>>> To: jsr339-experts_at_jax-rs-spec.java.net <mailto:jsr339-experts_at_jax-rs-spec.java.net>
>> >>>> Subject: [jsr339-experts] Re: Hypermedia Proposals
>> >>>>
>> >>>>
>> >>>>
>> >>>> Hi All,
>> >>>>
>> >>>>
>> >>>>
>> >>>> I've updated the wiki [1] to describe the type of declarative hyperlinking
>> >>>> supported in Jersey using @Ref and @Link. Declarative hyperlinking in Jersey
>> >>>> supports both links in representations and link headers.
>> >>>>
>> >>>>
>> >>>>
>> >>>> Hyperlinking is a first step, but HATEOAS is more than that. I've also
>> >>>> added some links to related work towards the end of the page. Please feel
>> >>>> free to include other links there.
>> >>>>
>> >>>>
>> >>>>
>> >>>> Guilherme: I came across [2]. Is this the latest on your research in this
>> >>>> area?
>> >>>>
>> >>>>
>> >>>>
>> >>>> -- Santiago
>> >>>>
>> >>>>
>> >>>>
>> >>>> [1] http://java.net/projects/jax-rs-spec/pages/Hypermedia
>> >>>>
>> >>>> [2] https://github.com/caelum/restfulie-java/wiki/java_hypermedia
>> >>>>
>> >>>>
>> >>>>
>> >>>> On Jul 5, 2011, at 12:47 PM, Guilherme Silveira wrote:
>> >>>>
>> >>>> Cant we support link headers? Would already incentivate people doing rest...
>> >>>> Even if limited to links.
>> >>>>
>> >>>> Cant we also incentivate response based links and forms as in
>> >>>>
>> >>>> Response.getLinksFor(myEntity)
>> >>>>
>> >>>> An http api withou hypermedia is, in the best case, an http api - not a rest
>> >>>> one.
>> >>>>
>> >>>> Regards
>> >>>>
>> >>>> Guilherme Silveira
>> >>>>
>> >>>>
>> >>>>
>> >>>> 2011. 7. 5. 오후 12:40에 "Bill Burke" <bburke_at_redhat.com <mailto:bburke_at_redhat.com>>님이 작성:
>> >>>>
>> >>>> Hypermedia is entity body driven, so, other than Link header support, I
>> >>>> don't see what we can be done in regards to a specification. XML/JAXB is
>> >>>> the only standardized media type JCP has dealt with and I'm very doubtful
>> >>>> meaningful integration can be done with it considering JAXB's limitations.
>> >>>>
>> >>>> On 7/1/11 1:47 PM, Santiago Pericas-Geertsen wrote:
>> >>>>>
>> >>>>> Hello Experts,
>> >>>>>
>> >>>>> Even though we are stil...
>> >>>>
>> >>>> --
>> >>>> Bill Burke
>> >>>> JBoss, a division of Red Hat
>> >>>> http://bill.burkecentral.com
>> >>>>
>> >>>>
>> >>>>
>> >>>>
>> >>
>> >>
>>
>>