users@jersey.java.net

Re: sporadic IllegalStateException when accessing _at_Context HttpServletResponse within a single thread

From: Paul Sandoz <Paul.Sandoz_at_oracle.com>
Date: Thu, 25 Nov 2010 13:30:45 +0100

On Nov 17, 2010, at 11:52 AM, elmar.vaneersel_at_emc.com wrote:

> Hi,
>
> I am encountering sporadic IllegalStateExceptions when accessing
> @Context injected HttpServletResponse objects.
> I have read several other posts that seem to address the same issue,
> but there the problem was usually caused by unsupported
> multithreaded access to the injected @Context objects.
>

Yes, if the thread local proxy reference is passed across thread
boundaries that can be an issue.

Another possible issue is if the thread local proxy is accessed out of
scope of a request.

The code that sets the thread local is as follows:

         try {
             UriRuleProbeProvider.requestStart(requestUri);

             requestInvoker.set(request);
             responseInvoker.set(response);

             final Writer w = new Writer(useSetStatusOn404, response);
             _application.handleRequest(cRequest, w);
             return w.cResponse.getStatus();
         } catch (MappableContainerException ex) {
             traceOnException(cRequest, response);
             throw new ServletException(ex.getCause());
         } catch (ContainerException ex) {
             traceOnException(cRequest, response);
             throw new ServletException(ex);
         } catch (RuntimeException ex) {
             traceOnException(cRequest, response);
             throw ex;
         } finally {
             UriRuleProbeProvider.requestEnd();

             requestInvoker.set(null);
             responseInvoker.set(null);
         }

As you can see it should be fairly robust in setting and unsetting the
thread local for a request.

Note also that the thread local variables are not static (which I
heard can cause issues in OSGi environments).

Without more information i really do not know what is going on.

Can you confirm that the ISE is being thrown from the class
ThreadLocalInvoker ?


> As far as I can tell my problem is different as my code is not using
> any other threads to access these objects at all.
> On top of that, this problem occurs only very sporadically, though
> when it does occur, it occurs for (practically?) every request to
> that particular resource path immediately after starting the
> container.
> Restarting the container has so far resolved this problem each time,
> but since in a development environment, restarts are fairly
> frequent, I have encountered this problem already a fair number of
> times.
>
> I am considering the workaround of injecting
> ThreadLocal<HttpServletResponse> objects instead, but since I highly
> doubt the cause of this problem is the same as for which this
> workaround was suggested as a possible solution ( http://markmail.org/message/sznf6mifapqtrswm
> ), as I am not accessing these objects by any other thread than the
> one that received the request, I am unsure it will actually address
> my problem.
>

I doubt that using ThreadLocal<HttpServletResponse> will make any
difference as the thread local proxy will use the same thread local
reference.


> Perhaps the fact that I am running this in an OSGi environment could
> have anything to with it, though without more in-depth knowledge
> about Jersey’s internals I can’t really imagine why.
>
> Perhaps this is a bug that has already been resolved by now;

No, you are the first to report such behavior.

Paul.

> I am currently working on Jersey 1.3, but due to another problem I
> have already sent to the Jersey user mailing list (http://java.net/projects/jersey/lists/users/archive/2010-11/message/60
> ), I can’t really upgrade to 1.4, but I would like to know in any
> case.
>
> Thanks