SpringBoot之Conditional自动配置类是否加载调试工具类

3 篇文章 0 订阅
2 篇文章 0 订阅

在写一些自动配置类的时候,有时候需要基于应用环境中的变量是否匹配或者类是否加载来决定该配置类是否被加载,或者再引入一些第三方star的时候,不确定某些配置类是否被加载,但是又不是特别好调试。

基于此写了一个判断该配置是否加载的工具类,如果没有被加载,则会打印其未被加载的原因。


@Component
public class SpringDebugTrace implements ApplicationContextAware {
    private final Logger logger = LoggerFactory.getLogger(getClass());
    private ApplicationContext applicationContext;

    @Override
    public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
        this.applicationContext = applicationContext;
    }

    public void printLogConditionalResult(Class<?> clazz) {
        printLogConditionalResult(clazz.getName(), true);
    }

    public void printLogConditionalResult() {
        final Map<String, ConditionEvaluationReport.ConditionAndOutcomes> conditionAndOutcomesBySource =
            this.applicationContext.getBean(ConditionEvaluationReport.class).getConditionAndOutcomesBySource();
        for (String key : conditionAndOutcomesBySource.keySet()) {
            printLogConditionalResult(key, false);
        }
    }

    public void printLogConditionalResult(String clazzName, boolean match) {
        final Map<String, ConditionEvaluationReport.ConditionAndOutcomes> conditionAndOutcomesBySource =
            this.applicationContext.getBean(ConditionEvaluationReport.class).getConditionAndOutcomesBySource();
        if (!logConditionalReport(conditionAndOutcomesBySource, clazzName, match)) {
            for (String key : conditionAndOutcomesBySource.keySet()) {
                if (key.startsWith(clazzName)) {
                    logConditionalReport(conditionAndOutcomesBySource, key, match);
                }
            }
        }
    }

    /**
     * 打印条件匹配结果日志
     *
     * @param conditionAndOutcomesMap 结果源
     * @param key                     类名
     * @param match                   是否展示匹配上
     * @return
     */
    private boolean logConditionalReport(
        Map<String, ConditionEvaluationReport.ConditionAndOutcomes> conditionAndOutcomesMap, String key,
        boolean match) {
        final ConditionEvaluationReport.ConditionAndOutcomes conditionAndOutcomes = conditionAndOutcomesMap.get(key);
        if (conditionAndOutcomes != null) {
            for (ConditionEvaluationReport.ConditionAndOutcome next : conditionAndOutcomes) {
                final ConditionOutcome outcome = next.getOutcome();
                if (match || !outcome.isMatch()) {
                    logger.info(" 调试条件类:[{}] 是否满足条件:{} , 结果:{}", key, outcome.isMatch(), outcome.getMessage());
                }
            }
            return true;
        }
        return false;
    }

    /**
     * 查找基于SPI加载的接口类
     * @param clazz
     * @param <T>
     * @return
     */
    public <T> List<T> getSpringFactories(Class<T> clazz) {
        return SpringFactoriesLoader.loadFactories(clazz, this.applicationContext.getClassLoader());
    }

}

使用方式:

// 注入该类
@Autowired
private SpringDebugTrace springDebugTrace;

// 调试某个配置类
springDebugTrace.printLogConditionalResult(ElasticsearchDataAutoConfiguration.class);
// @ConditionalOnProperty(prefix = "spring.lkx", name = "abc") ,上下文中没有配置
springDebugTrace.printLogConditionalResult(RestAutoConfiguration.class);

打印结果:

调试条件类:[org.springframework.boot.autoconfigure.data.elasticsearch.ElasticsearchDataAutoConfiguration] 是否满足条件:false , 结果:@ConditionalOnClass did not find required class 'org.springframework.data.elasticsearch.core.ElasticsearchRestTemplate'
调试条件类:[com.enjoy.spring.boot.example.bean.RestAutoConfiguration] 是否满足条件:false , 结果:@ConditionalOnProperty (spring.lkx.abc) did not find property 'abc'

这样你在需要加载某些配置类的时候,能够清楚知道没有被加载的原因。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值