注入方式
实现FactoryBean 接口
实现BeanDefinitionRegistryPostProcessor 接口
public class MyBeanRegister implements BeanDefinitionRegistryPostProcessor {
@Override
public void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry beanDefinitionRegistry) throws BeansException {
RootBeanDefinition rootBeanDefinition = new RootBeanDefinition();
rootBeanDefinition.setBeanClass(Student.class);
beanDefinitionRegistry.registerBeanDefinition("student",rootBeanDefinition);
}
@Override
public void postProcessBeanFactory(ConfigurableListableBeanFactory configurableListableBeanFactory) throws BeansException {
}
}
实现ImportBeanDefinitionRegistrar接口
public class MyBeanRegister implements ImportBeanDefinitionRegistrar{
@Override
public void registerBeanDefinitions(AnnotationMetadata importingClassMetadata, BeanDefinitionRegistry registry, BeanNameGenerator importBeanNameGenerator) {
RootBeanDefinition rootBeanDefinition = new RootBeanDefinition();
rootBeanDefinition.setBeanClass(Student.class);
registry.registerBeanDefinition("student",rootBeanDefinition);
}
}
springboot 启动refresh 方法
SpringApplication
public ConfigurableApplicationContext run(String... args) {
StopWatch stopWatch = new StopWatch();
stopWatch.start();
ConfigurableApplicationContext context = null;
Collection<SpringBootExceptionReporter> exceptionReporters = new ArrayList<>();
configureHeadlessProperty();
SpringApplicationRunListeners listeners = getRunListeners(args);
listeners.starting();
try {
ApplicationArguments applicationArguments = new DefaultApplicationArguments(args);
ConfigurableEnvironment environment = prepareEnvironment(listeners, applicationArguments);
configureIgnoreBeanInfo(environment);
Banner printedBanner = printBanner(environment);
context = createApplicationContext();
exceptionReporters = getSpringFactoriesInstances(SpringBootExceptionReporter.class,
new Class[] { ConfigurableApplicationContext.class }, context);
prepareContext(context, environment, listeners, applicationArguments, printedBanner);
// 核心方法入口
refreshContext(context);
afterRefresh(context, applicationArguments);
stopWatch.stop();
if (this.logStartupInfo) {
new StartupInfoLogger(this.mainApplicationClass).logStarted(getApplicationLog(), stopWatch);
}
listeners.started(context);
callRunners(context, applicationArguments);
}
catch (Throwable ex) {
handleRunFailure(context, ex, exceptionReporters, listeners);
throw new IllegalStateException(ex);
}
try {
listeners.running(context);
}
catch (Throwable ex) {
handleRunFailure(context, ex, exceptionReporters, null);
throw new IllegalStateException(ex);
}
return context;
}
AbstractApplicationContext
@Override
public void refresh() throws BeansException, IllegalStateException {
synchronized (this.startupShutdownMonitor) {
// Prepare this context for refreshing.
// 刷新前准备
1.设置容器状态 active
2.初始化属性设置 比如监听器
3.检查必备属性是否存在
prepareRefresh();
// Tell the subclass to refresh the internal bean factory.
// 获取bean 工厂
1.设置beanFactory 序列化id
2.获取beanFactory
ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();
// Prepare the bean factory for use in this context.
1.设置beanFactory一些属性
2.添加后置处理器
3.设置忽略的自动装配接口
4.注册一些组件
prepareBeanFactory(beanFactory);
try {
// Allows post-processing of the bean factory in context subclasses.
1.子类重写以在BeanFactory完成创建后进一步设置
postProcessBeanFactory(beanFactory);
1.调用BeanDefinitionRegistryPostProcessor 向容器内添加bean 的定义
2.调用 BeanFactoryPostProcessor 实现向容器内bean的 定义添加属性
// Invoke factory processors registered as beans in the context.
invokeBeanFactoryPostProcessors(beanFactory);
1.找到BeanPostProcessor的实现
2.排序后注册到容器内
// Register bean processors that intercept bean creation.
registerBeanPostProcessors(beanFactory);
1.初始化国际化相关的属性
// Initialize message source for this context.
initMessageSource();
1.初始化时间广播器
// Initialize event multicaster for this context.
initApplicationEventMulticaster();
1.创建web容器
// Initialize other special beans in specific context subclasses.
onRefresh();
1.添加容器内事件监听器至事件广播器中
2.派发早期记录还未处理事件
// Check for listener beans and register them.
registerListeners();
1.初始化单实例bean
// Instantiate all remaining (non-lazy-init) singletons.
BeanDefinition :
1.一个对象再spring 中的描述,RootBeanDefinition 是其常见的实现
2.通过操作BeanDefinition 来完成bean 的实例化和属性注入
finishBeanFactoryInitialization(beanFactory);
1.初始化生命周期处理器
2.调用生命周期处理器onRfresh方法
3.发布ContextRefreshedEvent 事件
4.JMX 相关处理
// Last step: publish corresponding event.
finishRefresh();
}
catch (BeansException ex) {
if (logger.isWarnEnabled()) {
logger.warn("Exception encountered during context initialization - " +
"cancelling refresh attempt: " + ex);
}
// Destroy already created singletons to avoid dangling resources.
destroyBeans();
// Reset 'active' flag.
cancelRefresh(ex);
// Propagate exception to caller.
throw ex;
}
finally {
// Reset common introspection caches in Spring's core, since we
// might not ever need metadata for singleton beans anymore...
resetCommonCaches();
}
}
}
prepareRefresh();
1.设置容器状态 active
2.初始化属性设置 比如监听器
3.检查必备属性是否存在
AnnotationConfigReactiveWebServerApplicationContext
@Override
protected void prepareRefresh() {
this.scanner.clearCache();
super.prepareRefresh();
}
AbstractApplicationContext
protected void prepareRefresh() {
// Switch to active.
this.startupDate = System.currentTimeMillis();
this.closed.set(false);
// 标识上下文状态
this.active.set(true);
if (logger.isDebugEnabled()) {
if (logger.isTraceEnabled()) {
logger.trace("Refreshing " + this);
}
else {
logger.debug("Refreshing " + getDisplayName());
}
}
// Initialize any placeholder property sources in the context environment.
initPropertySources();
// Validate that all properties marked as required are resolvable:
// see ConfigurablePropertyResolver#setRequiredProperties
getEnvironment().validateRequiredProperties();
// Store pre-refresh ApplicationListeners...
if (this.earlyApplicationListeners == null) {
this.earlyApplicationListeners = new LinkedHashSet<>(this.applicationListeners);
}
else {
// Reset local application listeners to pre-refresh state.
this.applicationListeners.clear();
this.applicationListeners.addAll(this.earlyApplicationListeners);
}
// Allow for the collection of early ApplicationEvents,
// to be published once the multicaster is available...
this.earlyApplicationEvents = new LinkedHashSet<>();
}