2016-05-31 18 views
5

Şimdi bir çok şey denedim ama bulmacanın bir parçasını kaçırıyor gibiyim. İşte hikayem: HttpServletRequest'ten bazı SessionContext dosyalarını okuyan bir fasulyesi isteğim var. Bu özellik bir filtrede ayarlanır. Bu kod, doğru iş parçacığı üzerinde çalışırken kesinlikle çalışıyor. Bahar teşvik talebi çocuk için iş parçacığı fasulyesi (HttpServletRequest)

@Component 
@Scope(value = WebApplicationContext.SCOPE_REQUEST, proxyMode = ScopedProxyMode.INTERFACES) 
public class SessionContextProviderImpl implements SessionContextProvider<SessionContext> { 
    private final HttpServletRequest _request; 

    @Autowired 
    public SessionContextProviderImpl(HttpServletRequest request) { 
     _request = request; 
    } 

    @Override 
    public SessionContext get() { 
     return (SessionContext) _request.getAttribute(Constants.SESSION_CONTEXT_IDENTIFIER); 
    } 
} 

Şimdi java 8'ler yeni özellik CompletableFuture kullanmaya başladı ve ben paralel şeyler bilgisayar bu özelliklerin üçü varken sonucu için istek iplik bekler. Ne yapmak istediğim/üzerinde/eli teşvik orijinal http iplikten kökenli olan çocuk parçacığı üzerinde kullanılabilir bir şekilde fasulye veya istek yaymaktır. Özellikle, SessionContext'i HttpServletRequest'ten asenkronize tedarik edilen bir CompletableFuture içinden almak istiyorum. denedim Ne

bu (get'in yerini uygulama) 'dir:

final HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest(); 
request.getAttribute(Constants.SESSION_CONTEXT_IDENTIFIER); 

Ama bu istek fasulye kapsamlı olarak besbelli aynı sonucu verir. Peki "getRequest", atılan bir istisna yerine null değerini döndürür. Üçüncü yaklaşım olarak

bu original post çalıştı:

ConfigurableBeanFactory cbf = (ConfigurableBeanFactory) beanFactory; 

org.springframework.beans.factory.config.Scope simpleThreadScope = new SimpleThreadScope(); 

cbf.registerScope("simpleThreadScope", simpleThreadScope); 

Ve "simpleThreadScope" olarak SessionContextProviderImpl kapsamını ayarlayın. Ne yazık ki bu da işe yaramadı ve bir istek kapsamı dışında kullanıldığı bir istisna attı.

Kullandığım ortam: Forma ile birlikte enjeksiyon.

Belki birileri hakkında bir fikri var?

Saygılarımızla gelecekteki maceraperest için

cevap

6

:

Spring kodu ile kazmak için biraz zaman aldı ve bir inheritableRequestAttributesHolder sahiptir RequestContextHolder bulundu. Bunun ne olduğuna dair belgelere bakarsanız (InheritableThreadLocal'dan devralınır) aşağıdakileri okuyabilirsiniz:

Kalıtımsal iş parçacığı yerel değişkenleri, iş parçacığı özniteliği korunurken sıradan iş parçacığı yerel değişkenleri tercih edilirken kullanılır. değişkendeki (örneğin, Kullanıcı Kimliği, İşlem Kimliği), oluşturulan tüm çocuk konularına otomatik olarak iletilmesi gerekir.

RequestContextHolder bunun için bir alana sahiptir ve aslında setRequestAttributes, inheritableRequestAttributesHolder kullanmak için bir bayrağı destekler. Eğer RequestContextListener bakmak Dahası eğer -> Eğer bayrak (= false) olmadan denir bulmak requestInitialized.

public class InheritableRequestContextListener extends RequestContextListener { 
    private static final String REQUEST_ATTRIBUTES_ATTRIBUTE = 
     InheritableRequestContextListener.class.getName() + ".REQUEST_ATTRIBUTES"; 

    @Override 
    public void requestInitialized(ServletRequestEvent requestEvent) { 
     if (!(requestEvent.getServletRequest() instanceof HttpServletRequest)) { 
      throw new IllegalArgumentException(
        "Request is not an HttpServletRequest: " + requestEvent.getServletRequest()); 
     } 
     HttpServletRequest request = (HttpServletRequest) requestEvent.getServletRequest(); 
     ServletRequestAttributes attributes = new ServletRequestAttributes(request); 
     request.setAttribute(REQUEST_ATTRIBUTES_ATTRIBUTE, attributes); 
     LocaleContextHolder.setLocale(request.getLocale()); 
     RequestContextHolder.setRequestAttributes(attributes, true); 
    } 
} 

Ve işte, ben çocuk konuda SessionContextProvider erişebilir: Yani ne yaptığını sona erdi budur. istek tamamlandıktan sonra

+0

nasıl requestattributes kullanıyor. İstek tamamlandığında, başlık öznitelikleri gibi istek özniteliklerimi kaybediyorum. RequestContextHolder.setRequestAttributes (öznitelikleri, true) kullanmayı denedim; hala hayır şans. –

+0

Bağlamı, istek yürütme işlemini bozmayacak ve böylece tamamen bağımsız hareket edecek bir iş parçacığı üzerinde kullanmak isterseniz, bunun gibi farklı çözümler aramalısınız: DelegatingSecurityContextExecutor https: // docs.spring.io/spring-security/site/docs/current/reference/html/concurrency.html –

+0

Bu bir bileşen midir? Bir yapılandırma sınıfı? Derse ne tür bir açıklama eklemem gerekiyor? –