编程语言
首页 > 编程语言> > springboot源码解析-管中窥豹系列之Runner(三)

springboot源码解析-管中窥豹系列之Runner(三)

作者:互联网

一、前言

 简介

二、Runner

这一节我们讨论一下springboot项目的Runner,Runner是在spring加载完毕执行的,springboot有两种Runner:

@FunctionalInterface
public interface ApplicationRunner {

	void run(ApplicationArguments args) throws Exception;

}

@FunctionalInterface
public interface CommandLineRunner {

	void run(String... args) throws Exception;

}

三、用法

实现接口就可以了

import org.springframework.boot.ApplicationArguments;
import org.springframework.boot.ApplicationRunner;
import org.springframework.stereotype.Component;

@Component
public class HelloRunner implements ApplicationRunner {
    
    @Override
    public void run(ApplicationArguments args) throws Exception {
        System.out.println("hello runner");
    }
}

四、源码解读

我们直接找SpringApplication类的run方法,想看整体框架的去第一节。

public ConfigurableApplicationContext run(String... args) {
		
    ...

    try {
        
        ...

        callRunners(context, applicationArguments);
        
        ...

    }
    catch (Throwable ex) {
        
        ...

    }

    ...

    return context;
}

我们直接定位到callRunners方法。

private void callRunners(ApplicationContext context, ApplicationArguments args) {
    List<Object> runners = new ArrayList<>();
    // (1) 找到ApplicationRunner的实现类,加到list里面
    runners.addAll(context.getBeansOfType(ApplicationRunner.class).values());
    // (2) 找到CommandLineRunner的实现类,加到list里面
    runners.addAll(context.getBeansOfType(CommandLineRunner.class).values());
    // (3) 排序
    AnnotationAwareOrderComparator.sort(runners);
    // (4) 钩子回调
    for (Object runner : new LinkedHashSet<>(runners)) {
        if (runner instanceof ApplicationRunner) {
            callRunner((ApplicationRunner) runner, args);
        }
        if (runner instanceof CommandLineRunner) {
            callRunner((CommandLineRunner) runner, args);
        }
    }
}

总共分四步:

我们看一下canllRunner

private void callRunner(ApplicationRunner runner, ApplicationArguments args) {
    try {
        (runner).run(args);
    }
    catch (Exception ex) {
        throw new IllegalStateException("Failed to execute ApplicationRunner", ex);
    }
}

private void callRunner(CommandLineRunner runner, ApplicationArguments args) {
    try {
        (runner).run(args.getSourceArgs());
    }
    catch (Exception ex) {
        throw new IllegalStateException("Failed to execute CommandLineRunner", ex);
    }
}

欢迎关注公众号:丰极,更多技术学习分享。

标签:...,CommandLineRunner,springboot,runner,args,ApplicationArguments,管中窥豹,源码,Applic
来源: https://www.cnblogs.com/zhangbin1989/p/14260778.html