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

[jsr339-experts] Re: Updated Client API and Interceptors/Filters proposal is available - please review

From: Marek Potociar <marek.potociar_at_oracle.com>
Date: Thu, 09 Jun 2011 15:25:48 +0200

On 06/07/2011 08:19 PM, Markus KARG wrote:
> Just a few notes I made while reading the samples in the WIKI.
>
>
> * As ResourceUri is not an URI but actually a factory for invocations, it might be better to stick with WebResource, or use a
>
> name like Endpoint or InvocationFactory. All those names make clear the "active" aspect of the class, while with ResourceUri
>
> everybody might be surprised that it is a factory actually.

We have received numerous complains about WebResource being just a "glorified URI" and the WebResource name being too
server-side oriented. After hearing lots of suggestions, the ResourceUri seemed the best fit in the end. It is a
glorified URI, esp. with it's currently limited scope of responsibilities and it does not evoke the feeling of being a
server-side component.

>
> * While I understand that technically ".perpareX()" is the correct method name, I assume that end users might like to use the
>
> simpler ".x()" instead (without "prepare"), as it is just so much shorter and better to read.

Actually, that's what I had in my proposal initially, but then I have received strong negative internal feedback, since
the x() is (except for "method") a verb and many people associated the verbs with performing the action, which was found
very confusing. Personally, I don't share those feelings, but I was really outnumbered, so I did change the name in the
end before publishing the proposal. It would be good to see what other people think. Maybe we could also vote on this?

>
> * What WebDAV people expect to see with regards to extensibility is not only ResourceUri.prepareMethod("COPY") but actually
>
> ResourceUri.prepareCopy(). To be able to do that, obviously there must be a pluggable factory for ResourceUri subclasses to be
>
> registered with Client, or Client itself must be WebDAVClient at runtime using some kind of WebDAVClientFactory. In the class
>
> diagram I see that factories are planned, but it is not told how they get enabled. What would be the JAX RS 2.0 way to enable
>
> a different factory to use WebDAV instead of simple HTTP? Note that I do not want to replace the JAX RS implementation but
>
> just want to add WebDAV methods to be processed by the current implementation.

Can this be simply solved by:

WebDAVClient c = Client.providedBy(WebDAVClientFactory.class).create();
WebDAVResourceUri ru = c.resource("http://some.uri/webdav/resource");
HttpRequest req = ru.prepareCopy();
...

where WebDAVClient.resource(...) methods are overriden to return WebDAVResourceUri instead of the ResourceUri?

>
> * I do not see what the befit of asynchronous client API should be compared to a simple Executor used within the client
>
> application itself (besides two or three lines of less code in the complete client application which might be millions of code
>
> long)? Will the specification define clear aspects what the Client implementation must fulfil ontop of a simple Executor or
>
> will it be such vague as it currently is? I expect this to be defined clearly, as this was one criteria against the caching
>
> proposal and we should balance the criteria detail of all features.

The benefit is that a good async implementation is able manage many open connections with a single thread or a small
thread pool (even for multiple clients or applications) thus dramatically reducing the resource and memory footprint
esp. vital in container deployment models. This would not be achievable from the application layer without exposing the
low connection management layers to the application client.

Having said that, we are not forcing anyone to use the async API. Using a custom executor service + sync API may be
suitable for certain (esp. GUI related) scenarios too.

> * From the view of the end user it is a bit verbose to write Client.create().request(). It would be very much more comfortable
>
> to just write Client.request(), since obviously a create() will use a default config anyways, so this could be implied by a
>
> direct Client.request() call. Only programmers wanting to share Client instances or wanting to use custom configs would have
>
> to write Client.create() then (which will be the minority I assume and such support CoC).
>
> * The filter example says a possible use of FilterAction.STOP could be a caching filter. Such a filter might need to not only
>
> stop the filter chain, but replace the actual uncoditional call by a conditional one. In what way could the filter API solve
>
> this?

The idea is that client is a potentially heavy-weight instance to be reused across the application as much as possible.
It would not be good to encourage users to silently construct a new client instance per request IMO. There are also
other environment-specific issues that would prevent effective caching of the internal default client instance, see
e.g.: http://java.net/jira/browse/JAX_RS_SPEC-110

>
> * The interceptor sample says a possible use of interceptors would be GZIP. As GZIP is a transparent but essential part of
>
> HTTP, I doubt that end users will understand that they must user interceptors to add GZIP. I think most would just expect that
>
> GZIP is handled transparently by the JAX RS engine or it's transport delegate. I do not think that people would love to see
>
> that they must handle GZIP again and again in every application they write. So the GZIP Interceptor should be a mandatory part
>
> of any JAX RS implementation.

I share the opinion with Bill and Santiago here. We should first standardize on the most necessary parts, ideally those
ones that are already proven to work well in the proprietary APIs. We should defer adding such "derived" features to a
later revision of the spec.

Marek