如何延迟Spring @Conditional配置注释的求值?



我有一个Spring @Configuration类,当在环境中设置特定属性值时,它应该注册一个bean。我编写了一个自定义的Condition实现来检查该值是否存在,当我在Spring Boot中启动应用程序时,它可以工作,但是在运行JUnit测试时,bean从未注册过。我调试了应用程序,确定在实例化PropertySourcesPlaceholderConfigurer之前对Condition进行了评估。

我修改了我的Condition来实现ConfigurationCondition,并在REGISTER_BEAN阶段指定评估。在配置器实例化之前仍然调用该方法,但是当我从属性文件中添加或删除属性时,注册的bean就会出现或消失。

这是重新排序求值的最好方法吗?这是ConfigurationCondition接口的目的,还是我只是不小心让它现在工作?

@Conditional(PropertyCondition.class)
@Configuration
public class PostbackUrlConfiguration {
    @Value("${serviceName.postbackUrl}")
    String postbackUrl;
    @Bean
    public PostbackUrlProvider provider() {
        return new FixedUrlProvider(postbackUrl);
    }
}

,

public class PropertyCondition implements ConfigurationCondition {
    @Override
    public boolean matches(ConditionContext context, AnnotatedTypeMetadata metadata) {
        return context.getEnvironment().containsProperty("serviceName.postbackUrl");
    }
    @Override
    public ConfigurationPhase getConfigurationPhase() {
        return ConfigurationPhase.REGISTER_BEAN;
    }
}

测试配置是我的测试用例中的静态类:

@Configuration
@ComponentScan
@PropertySource("classpath:/postback.properties")
@Import(PostbackUrlConfiguration.class)
public static class TestConfig {
    @Bean
    public static PropertySourcesPlaceholderConfigurer propertySourcesPlaceholderConfigurer() {
        return new PropertySourcesPlaceholderConfigurer();
    }
}

@Configuration类的解析阶段包括读取它的类定义、填充Configuration对象的集合(因为一个@Configuration类可能会@Import另一个@Configuration类,所以这些导入也会被解析)、处理@PropertySources@ImportResources等。

处理@PropertySources也不会加载这些属性。解析阶段完成后,将加载@PropertySources属性。加载这些之后,然后注册来自@Configuration类内部的bean定义(REGISTER_BEAN阶段)。

因此,您使用ConfigurationConditionConfigurationPhase.REGISTER_BEAN阶段所看到的是预期的,因为在注册bean定义时以及在解析@Configuration类之后,这些属性实际上在Environment中可用。仅使用Condition,我相信它甚至没有达到@Configuration的解析阶段,评估甚至在此之前完成,当@Configuration类定义要注册时。

最新更新