简体   繁体   English

创建RequestScope bean或回退到单例

[英]Create RequestScope bean or fallback to singleton

I need to create RequestScope bean to handle web code in a specific way, however this code can sometimes be called from non web thread and in that case I need to use standard Singleton. 我需要创建RequestScope bean来以特定方式处理Web代码,但是有时可以从非Web线程调用此代码,在这种情况下,我需要使用标准Singleton。

Is there any good pattern to fallback during bean creation process based on the web thread availability? 根据Web线程的可用性,在bean创建过程中是否有任何好的模式可以回退?

The only thing that I can think of at this moment is to try to create bean with BeanFactory.getBean and return Singleton on BeanCreationException . 我现在唯一能想到的就是尝试使用BeanFactory.getBean创建bean并在BeanCreationException上返回Singleton。

The solution below allows to get singleton or get/create request scope bean based on the execution context. 下面的解决方案允许根据执行上下文获取单例或获取/创建请求范围Bean。

interface Consumer{}
class SingletonConsumer implements Consumer{}
class WebRequestBasedConsumer implements Consumer{}


class ConsumerFactory {
    private final BeanFactory beanFactory;
    private final SingletonConsumer singletonConsumer;

    Consumer getConsumer() {
        if (RequestContextHolder.getRequestAttributes() != null) {
            return beanFactory.getBean(WebRequestBasedConsumer.class);
        }
        return singletonConsumer;
    }
}

If I understand your requirement correctly, you can define two beans of the same class but configured them with different bean names and different scopes . 如果我正确理解了您的需求,那么可以定义两个相同类的bean,但是用不同的bean名称和不同的作用域配置它们。 Then use @Qualifer to differentiate which bean (ie which scoped of the bean) you want to inject. 然后使用@Qualifer来区分要注入的bean(即bean的作用域)。

For example ,the bean definitions look like: 例如,bean定义如下所示:

@Bean(name="singletonFoo")
@Scope(scopeName = "singleton") //can omit it as the default scope is singleton already.
public Foo singletonFoo(){

}

@Bean(name="requestScopedFoo")
@Scope(scopeName = "request")
public Foo requestScopedFoo(){

}

Then to inject singleton bean : 然后注入单例豆:

@Autowired
@Qualifier("singletonFoo")
private Foo foo;

And to inject requested scoped bean: 并注入请求的作用域bean:

@Autowired
@Qualifier("requestScopedFoo")
private Foo foo;

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM