Uploaded image for project: 'CXF'
  1. CXF
  2. CXF-5104

JAX-RS not injecting contexts after resuming a suspended continuation

    XMLWordPrintableJSON

Details

    • Unknown

    Description

      Problem:

      In order to use continuations, I have a 'MessageContext' injected into the JAX-RS resource using @Context annotation. When the request is initially handled, JAX-RS properly sets the thread-local MessageContext (ThreadLocalMessageContext) for that particular instance of thread, and am able to retrieve the ContinuationProvider (in my case org.apache.cxf.transport.http.Servlet3ContinuationProvider) from context. Once I suspend the continuation and resume the same later, however, the thread-local MessageContext instance is not being set and therefore am unable to retrieve the resumed continuation (as ThreadLocalMessageContext is null through which continuation provider has to be retrieved).

      Possible Fix:

      Looks like the cause of the problem is in org.apache.cxf.jaxrs.JAXRSInvoker.invoke(Exchange, Object, Object) implementation, when a continuation is resumed, wasSuspended would be true and there is a conditional block which injects params and contexts only when wasSuspended = false. Extracting the injection of the params and contexts out of this conditional block would fix the issue as so:

      ******

      boolean wasSuspended = exchange.remove(REQUEST_WAS_SUSPENDED) != null;

      if (!wasSuspended) {
      pushOntoStack(ori, ClassHelper.getRealClass(resourceObject), inMessage);
      }

      final boolean contextsAvailable = cri.contextsAvailable();
      final boolean paramsAvailable = cri.paramsAvailable();
      if (contextsAvailable || paramsAvailable) {
      Object realResourceObject = ClassHelper.getRealObject(resourceObject);
      if (paramsAvailable)

      { JAXRSUtils.injectParameters(ori, realResourceObject, inMessage); }

      if (contextsAvailable)

      { InjectionUtils.injectContexts(realResourceObject, cri, inMessage); }

      }
      if (cri.isRoot()) {
      ProviderInfo<?> appProvider =
      (ProviderInfo<?>)exchange.getEndpoint().get(Application.class.getName());
      if (appProvider != null)

      { InjectionUtils.injectContexts(appProvider.getProvider(), appProvider, inMessage); }

      }

      ******

      Attachments

        1. AsyncResource.java
          2 kB
          Sharath P
        2. web.xml
          0.9 kB
          Sharath P
        3. beans.xml
          1 kB
          Sharath P
        4. JsonBean.java
          0.3 kB
          Sharath P
        5. CXF-5104.patch
          3 kB
          Sharath P

        Activity

          People

            sergey_beryozkin Sergey Beryozkin
            chandra.ps Sharath P
            Votes:
            0 Vote for this issue
            Watchers:
            2 Start watching this issue

            Dates

              Created:
              Updated:
              Resolved: