On 19 December 2014 at 10:05, Mark Thomas <markt_at_apache.org> wrote:
>
> However, I don't see why we have this restriction in the first place. As
> I have stated elsewhere on this thread, no explanation was given when
> this restriction was introduced and right now I don't see why we need it
> for sync or async.
>
I agree that this issue is really independent of sync or async.
However, I do not believe it was a restriction that was added - only a
clarification of the expected behaviour. The reasons I believe that
included:
- There is an expectation that exceptions thrown by a servlet/filter may
be caught by an upstream filter or servlet using a RequestDispatcher.
Allowing arbitrary threads to call into doFilter will break this.
- ThreadLocals are frequently use by authentication and authorisation
mechanisms, specially when invoking JEE components. Allowing the filter
chain to not be scoped by a thread will break all usage of thread locals.
- Code within a filter/servlet chain can expect to be single threaded
with respect to a particular request. ie while there may be many threads
within a filter/servlet, there will only be a single thread per request.
Allowing arbitrary threads to call doFilter would allows for the
possibility of a request being dispatched multiple times.
- If a new thread calls doFilter before the dispatched thread returns to
the container, then the values of methods like getPathInfo will be
different for each calling thread.
- Such a pattern does no scale to multiple uses. If filter A used an
new thread to call filter B which used a new thread to call filter C, then
what can filter A assume when it's new thread returns? Is the request
handled and the response generated? It does not know because that depends
on thread created by B. To resolve such issues, we would need to create
a whole bunch of listeners, that we pretty much have already for normally
dispatched requests.
> The original use case [1] that triggered this thread looks reasonable
> and I'd like to support it if possible. The clarification proposed above
> would not allow the use case to be supported.
>
>
I'm not so sure it is a valid use case. The issue is that a different
threading paradigm (fibers from quasar) want to be used to invoke
servlets. I think changing the very nature of the threading of a servlet
container has to be something done with the involvement of the container
and not as a filter in an application.
If the application wishes to use fibers to generate a response, then they
are free to create a framework to do so that writes (async or blocking) to
the servlet response. But I don't see why it is reasonable that such a
new/different threading paradigm should expect to be able to takeover the
dispatch and handling model of the servlet container. Specially if
authentication and authorisation are involved.
> Regarding 2) my current thinking is that the return values are as they
> were for the request/response at the point async was started and remain
> unchanged until the async request is dispatched at which point they
> change to reflect the target of the dispatch. It is TBD if some
> mechanism is provided along the lines of 9.4.2 to expose some of the
> original (remembering there may be multiple async/dispatch sequences)
> values.
>
That is a big change in the current semantic. Currently after a
doFilter/forward/include the forwarding/including filter/servlet can expect
to be able to access those methods and see the values that were there
before the dispatch. I have definitely seen application code that
accesses the request methods on the way out that will break if a call to
startAsync suddenly freezes those values.
> Mark
>
> [1] https://issues.apache.org/bugzilla/show_bug.cgi?id=57284
>
--
Greg Wilkins <gregw_at_intalio.com> @ Webtide - *an Intalio subsidiary*
http://eclipse.org/jetty HTTP, SPDY, Websocket server and client that scales
http://www.webtide.com advice and support for jetty and cometd.