创建RequestScope bean或回退到单例

时间:2019-01-14 06:26:28

标签: spring spring-boot

我需要创建RequestScope bean来以特定方式处理Web代码,但是有时可以从非Web线程调用此代码,在这种情况下,我需要使用标准的Singleton。

在基于Web线程可用性的bean创建过程中,是否有任何好的模式可以回退?

此刻,我唯一想到的就是尝试使用BeanFactory.getBean创建bean并在BeanCreationException上返回Singleton。

2 个答案:

答案 0 :(得分:0)

如果我正确理解了您的需求,那么您可以定义两个相同类的bean,但是用不同的bean名称和不同的作用域配置它们。然后使用@Qualifer来区分要注入的bean(即bean的作用域)。

例如,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(){

}

然后注入单例bean:

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

并注入请求的作用域bean:

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

答案 1 :(得分:0)

以下解决方案允许根据执行上下文获取单例或获取/创建请求范围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;
    }
}