概述:

在开发过程中,经常有这样的需求,需要在web启动时去执行一些任务,比如:缓存处理、数据库清理、读取配置信息等等。在Spring框架中可以使用ApplicationListener监听器来实现,在Springboot中有两个接口可以供我们使用,分别是CommandLineRunner和ApplicationRunner。执行时机为 容器启动完成的时候。

CommandLineRunner和ApplicationRunner异同:

@FunctionalInterface
public interface CommandLineRunner {
    void run(String... var1) throws Exception;
}

@FunctionalInterface
public interface ApplicationRunner {
    void run(ApplicationArguments var1) throws Exception;
}

从源码可以看出,这两个接口都只有一个方法 run,但是参数不一样,分别是String数组和ApplicationArguments对象

使用:

比如自定义一个MyApplicationRunner实现类,用于实现ApplicationRunner

注意:类前面需要加上@Component注解,让Spring可以识别

@Component
public class MyApplicationRunner implements ApplicationRunner{
    @Override
    public void run(ApplicationArguments args) throws Exception {
        System.out.println("============");
        System.out.println("name = "+ args.getOptionNames());
        System.out.println("values ==== " + args.getOptionValues("developer.name"));
        System.out.println("values ==== " + args.getOptionValues("value"));
        System.out.println("=============MyApplicationRunner");
    }
}

在Springboot的main函数中加入打印输出,查看执行顺序:

@SpringBootApplication
public class ExApplication {

	public static void main(String[] args) {
		System.out.println("==================enter");
		SpringApplication.run(ExApplication.class, args);
		System.out.println("==================finish");
	}
}

然后在编译中 指定输入参数,我用的是Idea,在右上角 Edit Configurations中,具体设置如下:

Springboot 启动时运行自己的代码

运行后,可查看打印信息:

Springboot 启动时运行自己的代码

Springboot 启动时运行自己的代码

 

可以看到ApplicationLineRunner实现类是在容器运行后 执行的,并且可以获取到输入参数。

CommandLineRunner在使用上也差不多

执行顺序:

当有多个Runner需要执行时,可以指定运行顺序,使用时主要是在实现类上加入@Order(1)序号来标记

使用举例:

@Component
@Order(2)
public class MyApplicationRunner implements ApplicationRunner{
    @Override
    public void run(ApplicationArguments args) throws Exception {
        System.out.println("====================MyApplicationRunner order(2)");
        System.out.println("============");
        System.out.println("name = "+ args.getOptionNames());
        System.out.println("values ==== " + args.getOptionValues("developer.name"));
        System.out.println("values ==== " + args.getOptionValues("value"));
        System.out.println("=============MyApplicationRunner");
    }
}


@Component
@Order(1)
public class OtherApplicationRunner implements ApplicationRunner {
    @Override
    public void run(ApplicationArguments args) throws Exception {
        System.out.println("====================OtherApplicationRunner order(1)");
    }
}

分别定义两个ApplicationRunner的实现类,MyApplicationRunner指定Order为2,OtherApplicationRunner指定Order为1,执行查看结果如下:

Springboot 启动时运行自己的代码

可以看到 两个ApplicationRunner都执行了,并且按照指定的Order顺序来执行,Order序号越小 执行越靠前。

相关文章: