首页 > 技术文章 > SpringBoot学习(三)准备阶段

VVII 2020-03-10 21:49 原文

准备阶段概览

	public SpringApplication(ResourceLoader resourceLoader, Class<?>... primarySources) {
		this.resourceLoader = resourceLoader;
		Assert.notNull(primarySources, "PrimarySources must not be null");
		this.primarySources = new LinkedHashSet<>(Arrays.asList(primarySources));
		this.webApplicationType = WebApplicationType.deduceFromClasspath();
		setInitializers((Collection) getSpringFactoriesInstances(ApplicationContextInitializer.class));
		setListeners((Collection) getSpringFactoriesInstances(ApplicationListener.class));
		this.mainApplicationClass = deduceMainApplicationClass();
	}

加载应用上下文初始器(ApplicationContextInitializer)

  • 在刷新容器之前初始化Spring的回调接口
  • 用于需要对应用程序进行某些初始化工作的web程序中。例如利用Environment上下文环境注册属性源、激活配置文件等
  • 加载顺序由Ordered决定,可使用注解方式或接口编程方式

使用方法

方法一

public class FirstApplicationContextInitializer implements ApplicationContextInitializer,Ordered {

    @Override
    public void initialize(ConfigurableApplicationContext applicationContext) {
        System.out.println("FirstApplicationContextInitializer- --- ");
    }

    @Override
    public int getOrder() {
        return Ordered.HIGHEST_PRECEDENCE;
    }
}

  • 启动类
@SpringBootApplication(scanBasePackages = {"com.example"})
@MapperScan(value = {"com.example.mapper"})
@ServletComponentScan("com.example.servlet")
public class SpringbootApplication {


    public static void main(String[] args) {

//        System.out.println(" -- hello --");
//        // 完全禁用重启
//        //System.setProperty("spring.devtools.restart.enabled", "false");
//        SpringApplication application = new SpringApplication(SpringbootApplication.class);
//        application.addInitializers(new FirstApplicationContextInitializer());
//        application.run(args);
//        System.out.printf(" -- world --");


        new SpringApplicationBuilder(SpringbootApplication.class)
                .initializers(new FirstApplicationContextInitializer())
                .run(args);
    }
}

方法二 (推荐)

@Order(Ordered.HIGHEST_PRECEDENCE-1)
public class SecondApplicationContextInitializer implements ApplicationContextInitializer {

    @Override
    public void initialize(ConfigurableApplicationContext applicationContext) {
        System.out.println("SecondApplicationContextInitializer- --- ");
    }
}
  • /META-INF/spring.factories
# Initializers
org.springframework.context.ApplicationContextInitializer=\
com.example.config.context.SecondApplicationContextInitializer

方法三

public class ThirdApplicationContextInitializer<C extends ConfigurableApplicationContext> implements ApplicationContextInitializer<C>,Ordered {

    @Override
    public void initialize(ConfigurableApplicationContext applicationContext) {
        System.out.println("ThirdApplicationContextInitializer- --- ");
    }

    @Override
    public int getOrder() {
        return Ordered.LOWEST_PRECEDENCE;
    }
}
  • application.properties
context.initializer.classes=com.example.config.context.ThirdApplicationContextInitializer

结构如下

加载应用事件监听器(ApplicationListener)

使用

@Order(Ordered.LOWEST_PRECEDENCE)
public class FirstApplicationListener implements ApplicationListener<ContextRefreshedEvent> {
    @Override
    public void onApplicationEvent(ContextRefreshedEvent event) {
        System.out.println("FirstApplicationListener--");
    }
}
# Application Listeners
org.springframework.context.ApplicationListener=\
com.example.config.listener.FirstApplicationListener,\
com.example.config.listener.SecondApplicationListener

监听器事件

监听方法 对应事件 监听阶段 备注
starting ApplicationStartingEvent 应用刚启动
environmentPrepared ApplicationEnvironmentPreparedEvent
contextPrepared ApplicationContextInitializedEvent
contextLoaded ApplicationPreparedEvent
started ApplicationStartedEvent Spring Bean已完成初始化
running ApplicationReadyEvent
failed ApplicationFailedEvent

推荐阅读