述
在我们的日常开发中,可能需要在容器启动之后,立马做一些事情,这时候就可以借助 Spring Boot 的启动加载器去实现.
启动加载器
启动加载器有两种方式实现,分别是实现 CommandLineRunner
和 ApplicationRunner
,然后重写里面的 run 方法
实现CommandLineRunner方式
新建类 FirstCommandLineRunner
然后实现 CommandLineRunner
,代码如下:1
2
3
4
5
6
7
8
9
10
11@Component
@Order(1)
@Slf4j
public class FirstCommandLineRunner implements CommandLineRunner {
@Override
public void run(String... args) throws Exception {
log.info("First CommandLineRunner ...");
}
}
再搞一个 SecondCommandLineRunner
1 | @Component |
然后启动项目, 控制台输出如下:1
2
32020-02-13 18:15:55.765 INFO 32312 --- [ main] com.zhou.springboot.example.App : Started App in 3.444 seconds (JVM running for 8.238)
2020-02-13 18:15:55.768 INFO 32312 --- [ main] c.z.s.e.startup.FirstCommandLineRunner : First CommandLineRunner ...
2020-02-13 18:15:55.768 INFO 32312 --- [ main] c.z.s.e.startup.SecondCommandLineRunner : Second CommandLineRunner ...
可以看到这里的启动加载器已经正常执行,而且执行顺序只需要通过 @Order
注解来指定执行顺序即可
再来看下第二种方式
实现ApplicationRunner方式
新建类 FirstApplicationRunner
实现 ApplicationRunner
,如下:1
2
3
4
5
6
7
8
9
10
11@Component
@Slf4j
@Order(1)
public class FirstApplicationRunner implements ApplicationRunner {
@Override
public void run(ApplicationArguments args) throws Exception {
log.info("first application runner...");
}
}
同样的再搞一个1
2
3
4
5
6
7
8
9
10
11@Component
@Slf4j
@Order(2)
public class SecondApplicationRunner implements ApplicationRunner {
@Override
public void run(ApplicationArguments args) throws Exception {
log.info("second application runner...");
}
}
同样的这种方式的执行顺序也是通过 @Order
指定的
执行顺序
上面四个启动加载器 FirstApplicationRunner
和 FirstCommandLineRunner
的 Order
值都是1, 然后 SecondApplicationRunner
和 SecondCommandLineRunner
的 Order
值都是2, 启动项目看以下这四个的执行顺序
1 | 2020-02-13 18:15:55.767 INFO 32312 --- [ main] c.z.s.e.startup.FirstApplicationRunner : first application runner... |
这里可以看到,在 Order
值相同的情况下, ApplicationRunner
要优先于 CommandLineRunner
执行
原因是什么,下面来看一下启动加载器的源码
源码跟踪
还是先进入启动类的run方法,如下:
然后再进入 callRunners()
方法
具体调用源码就是这样,比较简单
总结
实现启动加载器的两种方式:
- 实现
ApplicationRunner
接口,重写run()
方法 - 实现
CommandLineRunner
接口,重写run()
方法
执行优先级
- 在
Order
值相同的情况下,ApplicationRunner
要优先于CommandLineRunner
执行