zoukankan      html  css  js  c++  java
  • Spring Boot源码分析

    1.核心:

    SpringApplication.run(SpringbootdemoApplication.class, args);

    内部

    2.初始化:

    new SpringApplication(primarySources)

    其中重要的:

    this.webApplicationType = this.deduceWebApplicationType();//根据是否存在"javax.servlet.Servlet", "org.springframework.web.context.ConfigurableWebApplicationContext"返回类型,这里返回WebApplicationType.SERVLET
    this.setInitializers(this.getSpringFactoriesInstances(ApplicationContextInitializer.class));//设置初始化工厂类
    this.setListeners(this.getSpringFactoriesInstances(ApplicationListener.class));//设置初始化监听
    this.mainApplicationClass = this.deduceMainApplicationClass();//设置含"main"的主类

    其中

    this.getSpringFactoriesInstances

    方法从classpath的所有

    "META-INF/spring.factories"

    中加载方法参数对应的类(一个集合),返回其中每个类的实例的集合,这里

    工厂类集合:

    # Application Context Initializers
    org.springframework.context.ApplicationContextInitializer=
    org.springframework.boot.context.ConfigurationWarningsApplicationContextInitializer,
    org.springframework.boot.context.ContextIdApplicationContextInitializer,
    org.springframework.boot.context.config.DelegatingApplicationContextInitializer,
    org.springframework.boot.web.context.ServerPortInfoApplicationContextInitializer

    监听集合:

    # Application Listeners
    org.springframework.context.ApplicationListener=
    org.springframework.boot.ClearCachesApplicationListener,
    org.springframework.boot.builder.ParentContextCloserApplicationListener,
    org.springframework.boot.context.FileEncodingApplicationListener,
    org.springframework.boot.context.config.AnsiOutputApplicationListener,
    org.springframework.boot.context.config.ConfigFileApplicationListener,
    org.springframework.boot.context.config.DelegatingApplicationListener,
    org.springframework.boot.context.logging.ClasspathLoggingApplicationListener,
    org.springframework.boot.context.logging.LoggingApplicationListener,
    org.springframework.boot.liquibase.LiquibaseServiceLocatorApplicationListener

    3.run方法:

    (new SpringApplication(primarySources)).run(args)

    其中重要的:

    SpringApplicationRunListeners listeners = this.getRunListeners(args);

    内部同样调用上面的

    this.getSpringFactoriesInstances

    方法加载并实例化

    EventPublishingRunListener

    使用其

    EventPublishingRunListener(SpringApplication application, String[] args)

    构造方法,第一个参数传递的是上面初始化好的SpringApplication,第二个参数是启动类传递的命令行参数数组

    然后

    listeners.starting();

    将每个监听开启。

    4.run方法中的Spring容器初始化部分

    context = this.createApplicationContext();

    方法,根据

    this.webApplicationType

    加载、实例化不同的BeanFactory实例,这里实例化

    org.springframework.boot.web.servlet.context.AnnotationConfigServletWebServerApplicationContext

    这个实例化当中,AnnotationConfigServletWebServerApplicationContext最终继承GenericApplicationContext,该父类构造方法中:

    public GenericApplicationContext() {
    this.customClassLoader = false;
    this.refreshed = new AtomicBoolean();
    this.beanFactory = new DefaultListableBeanFactory();
    }

    实例化了一个DefaultListableBeanFactory,它是Spring和核心BeanFactory类,将完成下面重要的Spring容器初始化过程。

    但这里的Spring初始化入口是AnnotationConfigServletWebServerApplicationContext自己的构造方法:

    public AnnotationConfigServletWebServerApplicationContext() {
    this.annotatedClasses = new LinkedHashSet();
    this.reader = new AnnotatedBeanDefinitionReader(this);
    this.scanner = new ClassPathBeanDefinitionScanner(this);
    }

    加粗方法内部,执行的是AnnotatedBeanDefinitionReader类的构造方法:

    public AnnotatedBeanDefinitionReader(BeanDefinitionRegistry registry, Environment environment) {
    this.beanNameGenerator = new AnnotationBeanNameGenerator();
    this.scopeMetadataResolver = new AnnotationScopeMetadataResolver();
    Assert.notNull(registry, "BeanDefinitionRegistry must not be null");
    Assert.notNull(environment, "Environment must not be null");
    this.registry = registry;
    this.conditionEvaluator = new ConditionEvaluator(registry, environment, (ResourceLoader)null);
    AnnotationConfigUtils.registerAnnotationConfigProcessors(this.registry);
    }

    这里的BeanDefinitionRegistry就是实例化AnnotatedBeanDefinitionReader时传入的AnnotationConfigServletWebServerApplicationContext实例,它最终(通过GenericApplicationContext)实现了BeanDefinitionRegistry.

    加粗方法进入AnnotationConfigUtils的registerAnnotationConfigProcessors方法:

    public static Set<BeanDefinitionHolder> registerAnnotationConfigProcessors(BeanDefinitionRegistry registry, @Nullable Object source) {
    DefaultListableBeanFactory beanFactory = unwrapDefaultListableBeanFactory(registry);
    if (beanFactory != null) {
    if (!(beanFactory.getDependencyComparator() instanceof AnnotationAwareOrderComparator)) {
    beanFactory.setDependencyComparator(AnnotationAwareOrderComparator.INSTANCE);
    }

    if (!(beanFactory.getAutowireCandidateResolver() instanceof ContextAnnotationAutowireCandidateResolver)) {
    beanFactory.setAutowireCandidateResolver(new ContextAnnotationAutowireCandidateResolver());
    }
    }

    Set<BeanDefinitionHolder> beanDefs = new LinkedHashSet(8);
    RootBeanDefinition def;
    if (!registry.containsBeanDefinition("org.springframework.context.annotation.internalConfigurationAnnotationProcessor")) {
    def = new RootBeanDefinition(ConfigurationClassPostProcessor.class);
    def.setSource(source);
    beanDefs.add(registerPostProcessor(registry, def, "org.springframework.context.annotation.internalConfigurationAnnotationProcessor"));
    }

    if (!registry.containsBeanDefinition("org.springframework.context.annotation.internalAutowiredAnnotationProcessor")) {
    def = new RootBeanDefinition(AutowiredAnnotationBeanPostProcessor.class);
    def.setSource(source);
    beanDefs.add(registerPostProcessor(registry, def, "org.springframework.context.annotation.internalAutowiredAnnotationProcessor"));
    }

    if (!registry.containsBeanDefinition("org.springframework.context.annotation.internalRequiredAnnotationProcessor")) {
    def = new RootBeanDefinition(RequiredAnnotationBeanPostProcessor.class);
    def.setSource(source);
    beanDefs.add(registerPostProcessor(registry, def, "org.springframework.context.annotation.internalRequiredAnnotationProcessor"));
    }

    if (jsr250Present && !registry.containsBeanDefinition("org.springframework.context.annotation.internalCommonAnnotationProcessor")) {
    def = new RootBeanDefinition(CommonAnnotationBeanPostProcessor.class);
    def.setSource(source);
    beanDefs.add(registerPostProcessor(registry, def, "org.springframework.context.annotation.internalCommonAnnotationProcessor"));
    }

    if (jpaPresent && !registry.containsBeanDefinition("org.springframework.context.annotation.internalPersistenceAnnotationProcessor")) {
    def = new RootBeanDefinition();

    try {
    def.setBeanClass(ClassUtils.forName("org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor", AnnotationConfigUtils.class.getClassLoader()));
    } catch (ClassNotFoundException var6) {
    throw new IllegalStateException("Cannot load optional framework class: org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor", var6);
    }

    def.setSource(source);
    beanDefs.add(registerPostProcessor(registry, def, "org.springframework.context.annotation.internalPersistenceAnnotationProcessor"));
    }

    if (!registry.containsBeanDefinition("org.springframework.context.event.internalEventListenerProcessor")) {
    def = new RootBeanDefinition(EventListenerMethodProcessor.class);
    def.setSource(source);
    beanDefs.add(registerPostProcessor(registry, def, "org.springframework.context.event.internalEventListenerProcessor"));
    }

    if (!registry.containsBeanDefinition("org.springframework.context.event.internalEventListenerFactory")) {
    def = new RootBeanDefinition(DefaultEventListenerFactory.class);
    def.setSource(source);
    beanDefs.add(registerPostProcessor(registry, def, "org.springframework.context.event.internalEventListenerFactory"));
    }

    return beanDefs;
    }

    该方法创建了后处理器Bean的BeanDefinition,并使用BeanDefinitionRegistry注册了一些后处理器,比如:

    registerPostProcessor(registry, def, "org.springframework.context.annotation.internalRequiredAnnotationProcessor")

    在这个registerPostProcessor方法中:

    private static BeanDefinitionHolder registerPostProcessor(BeanDefinitionRegistry registry, RootBeanDefinition definition, String beanName) {
    definition.setRole(2);
    registry.registerBeanDefinition(beanName, definition);
    return new BeanDefinitionHolder(definition, beanName);
    }

    加粗方法最终进入GenericApplicationContext中实例化的DefaultListableBeanFactory进行BeanDefinition的注册,这里是注册后处理器Bean,以下就是DefaultListableBeanFactory中重要的BeanDefinition注册方法:

    public void registerBeanDefinition(String beanName, BeanDefinition beanDefinition) throws BeanDefinitionStoreException {
    Assert.hasText(beanName, "Bean name must not be empty");
    Assert.notNull(beanDefinition, "BeanDefinition must not be null");
    if (beanDefinition instanceof AbstractBeanDefinition) {
    try {
    ((AbstractBeanDefinition)beanDefinition).validate();
    } catch (BeanDefinitionValidationException var9) {
    throw new BeanDefinitionStoreException(beanDefinition.getResourceDescription(), beanName, "Validation of bean definition failed", var9);
    }
    }

    BeanDefinition existingDefinition = (BeanDefinition)this.beanDefinitionMap.get(beanName);
    if (existingDefinition != null) {
    if (!this.isAllowBeanDefinitionOverriding()) {
    throw new BeanDefinitionStoreException(beanDefinition.getResourceDescription(), beanName, "Cannot register bean definition [" + beanDefinition + "] for bean '" + beanName + "': There is already [" + existingDefinition + "] bound.");
    }

    if (existingDefinition.getRole() < beanDefinition.getRole()) {
    if (this.logger.isWarnEnabled()) {
    this.logger.warn("Overriding user-defined bean definition for bean '" + beanName + "' with a framework-generated bean definition: replacing [" + existingDefinition + "] with [" + beanDefinition + "]");
    }
    } else if (!beanDefinition.equals(existingDefinition)) {
    if (this.logger.isInfoEnabled()) {
    this.logger.info("Overriding bean definition for bean '" + beanName + "' with a different definition: replacing [" + existingDefinition + "] with [" + beanDefinition + "]");
    }
    } else if (this.logger.isDebugEnabled()) {
    this.logger.debug("Overriding bean definition for bean '" + beanName + "' with an equivalent definition: replacing [" + existingDefinition + "] with [" + beanDefinition + "]");
    }

    this.beanDefinitionMap.put(beanName, beanDefinition);
    } else {
    if (this.hasBeanCreationStarted()) {
    Map var4 = this.beanDefinitionMap;
    synchronized(this.beanDefinitionMap) {
    this.beanDefinitionMap.put(beanName, beanDefinition);
    List<String> updatedDefinitions = new ArrayList(this.beanDefinitionNames.size() + 1);
    updatedDefinitions.addAll(this.beanDefinitionNames);
    updatedDefinitions.add(beanName);
    this.beanDefinitionNames = updatedDefinitions;
    if (this.manualSingletonNames.contains(beanName)) {
    Set<String> updatedSingletons = new LinkedHashSet(this.manualSingletonNames);
    updatedSingletons.remove(beanName);
    this.manualSingletonNames = updatedSingletons;
    }
    }
    } else {
    this.beanDefinitionMap.put(beanName, beanDefinition);
    this.beanDefinitionNames.add(beanName);
    this.manualSingletonNames.remove(beanName);
    }

    this.frozenBeanDefinitionNames = null;
    }

    if (existingDefinition != null || this.containsSingleton(beanName)) {
    this.resetBeanDefinition(beanName);
    }

    }

    该方法最终在beanDefinitionMap中存储了7个后处理器:

    这里的context就是创建的AnnotationConfigServletWebServerApplicationContext,内部的BeanFactory就是其内部实例化的DefaultListableBeanFactory,beanDefinitionMap就在它内部。

    这个方法在后面我们自定义Bean的注册中会反复使用。

    5.下一个重要方法:

    this.prepareContext(context, environment, listeners, applicationArguments, printedBanner);

    该方法:

    private void prepareContext(ConfigurableApplicationContext context, ConfigurableEnvironment environment, SpringApplicationRunListeners listeners, ApplicationArguments applicationArguments, Banner printedBanner) {
    context.setEnvironment(environment);
    this.postProcessApplicationContext(context);
    this.applyInitializers(context);
    listeners.contextPrepared(context);
    if (this.logStartupInfo) {
    this.logStartupInfo(context.getParent() == null);
    this.logStartupProfileInfo(context);
    }

    context.getBeanFactory().registerSingleton("springApplicationArguments", applicationArguments);
    if (printedBanner != null) {
    context.getBeanFactory().registerSingleton("springBootBanner", printedBanner);
    }

    Set<Object> sources = this.getAllSources();
    Assert.notEmpty(sources, "Sources must not be empty");
    this.load(context, sources.toArray(new Object[0]));
    listeners.contextLoaded(context);
    }

    中,sources代表初始化资源,这里是SpringApplication实例化时传入的主类SpringbootdemoApplication,然后带着资源进入load方法:

    protected void load(ApplicationContext context, Object[] sources) {
    if (logger.isDebugEnabled()) {
    logger.debug("Loading source " + StringUtils.arrayToCommaDelimitedString(sources));
    }

    BeanDefinitionLoader loader = this.createBeanDefinitionLoader(this.getBeanDefinitionRegistry(context), sources);
    if (this.beanNameGenerator != null) {
    loader.setBeanNameGenerator(this.beanNameGenerator);
    }

    if (this.resourceLoader != null) {
    loader.setResourceLoader(this.resourceLoader);
    }

    if (this.environment != null) {
    loader.setEnvironment(this.environment);
    }

    loader.load();
    }

    第一个加粗方法使用AnnotationConfigServletWebServerApplicationContext(实现了BeanDefinitionRegistry)和资源创建一个BeanDefinitionLoader:

    BeanDefinitionLoader(BeanDefinitionRegistry registry, Object... sources) {
    Assert.notNull(registry, "Registry must not be null");
    Assert.notEmpty(sources, "Sources must not be empty");
    this.sources = sources;
    this.annotatedReader = new AnnotatedBeanDefinitionReader(registry);
    this.xmlReader = new XmlBeanDefinitionReader(registry);
    if (this.isGroovyPresent()) {
    this.groovyReader = new GroovyBeanDefinitionReader(registry);
    }

    this.scanner = new ClassPathBeanDefinitionScanner(registry);
    this.scanner.addExcludeFilter(new BeanDefinitionLoader.ClassExcludeFilter(sources));
    }

    第一句加粗和上面一样,使用registry创建了一个AnnotatedBeanDefinitionReader,内部还是DefaultListableBeanFactory的那7个后处理器

    第二句加粗,创建了

    出了BeanDefinitionLoader的整个创建后,接着上面SpringApplication的load方法,使用刚刚创建的BeanDefinitionLoader的load方法,该方法最终调用其重载方法:

    private int load(Class<?> source) {
    if (this.isGroovyPresent() && BeanDefinitionLoader.GroovyBeanDefinitionSource.class.isAssignableFrom(source)) {
    BeanDefinitionLoader.GroovyBeanDefinitionSource loader = (BeanDefinitionLoader.GroovyBeanDefinitionSource)BeanUtils.instantiateClass(source, BeanDefinitionLoader.GroovyBeanDefinitionSource.class);
    this.load(loader);
    }

    if (this.isComponent(source)) {
    this.annotatedReader.register(new Class[]{source});
    return 1;
    } else {
    return 0;
    }
    }

    其中的资源就是主类SpringbootdemoApplication,这个方法最终进入AnnotatedBeanDefinitionReader的方法:

    <T> void doRegisterBean(Class<T> annotatedClass, @Nullable Supplier<T> instanceSupplier, @Nullable String name, @Nullable Class<? extends Annotation>[] qualifiers, BeanDefinitionCustomizer... definitionCustomizers) {
    AnnotatedGenericBeanDefinition abd = new AnnotatedGenericBeanDefinition(annotatedClass);
    if (!this.conditionEvaluator.shouldSkip(abd.getMetadata())) {
    abd.setInstanceSupplier(instanceSupplier);
    ScopeMetadata scopeMetadata = this.scopeMetadataResolver.resolveScopeMetadata(abd);
    abd.setScope(scopeMetadata.getScopeName());
    String beanName = name != null ? name : this.beanNameGenerator.generateBeanName(abd, this.registry);
    AnnotationConfigUtils.processCommonDefinitionAnnotations(abd);
    int var10;
    int var11;
    if (qualifiers != null) {
    Class[] var9 = qualifiers;
    var10 = qualifiers.length;

    for(var11 = 0; var11 < var10; ++var11) {
    Class<? extends Annotation> qualifier = var9[var11];
    if (Primary.class == qualifier) {
    abd.setPrimary(true);
    } else if (Lazy.class == qualifier) {
    abd.setLazyInit(true);
    } else {
    abd.addQualifier(new AutowireCandidateQualifier(qualifier));
    }
    }
    }

    BeanDefinitionCustomizer[] var13 = definitionCustomizers;
    var10 = definitionCustomizers.length;

    for(var11 = 0; var11 < var10; ++var11) {
    BeanDefinitionCustomizer customizer = var13[var11];
    customizer.customize(abd);
    }

    BeanDefinitionHolder definitionHolder = new BeanDefinitionHolder(abd, beanName);
    definitionHolder = AnnotationConfigUtils.applyScopedProxyMode(scopeMetadata, definitionHolder, this.registry);
    BeanDefinitionReaderUtils.registerBeanDefinition(definitionHolder, this.registry);
    }
    }

    这里的最后,将主类处理成BeanDefinitionHolder,和registry一起传入,进入BeanDefinitionReaderUtils:

    public static void registerBeanDefinition(BeanDefinitionHolder definitionHolder, BeanDefinitionRegistry registry) throws BeanDefinitionStoreException {
    String beanName = definitionHolder.getBeanName();
    registry.registerBeanDefinition(beanName, definitionHolder.getBeanDefinition());
    String[] aliases = definitionHolder.getAliases();
    if (aliases != null) {
    String[] var4 = aliases;
    int var5 = aliases.length;

    for(int var6 = 0; var6 < var5; ++var6) {
    String alias = var4[var6];
    registry.registerAlias(beanName, alias);
    }
    }

    }

    加粗一句和上面的分析是一样的,最终使用将主类实例注册到DefaultListableBeanFactory的beanDefinitionMap中。

    6.下一个重要的方法:

    this.refreshContext(context);

    最终将我们的AnnotationConfigServletWebServerApplicationContext强转成底层基类

    AbstractApplicationContext

    调用其refresh方法:

    public void refresh() throws BeansException, IllegalStateException {
    Object var1 = this.startupShutdownMonitor;
    synchronized(this.startupShutdownMonitor) {
    this.prepareRefresh();
    ConfigurableListableBeanFactory beanFactory = this.obtainFreshBeanFactory();
    this.prepareBeanFactory(beanFactory);

    try {
    this.postProcessBeanFactory(beanFactory);
    this.invokeBeanFactoryPostProcessors(beanFactory);
    this.registerBeanPostProcessors(beanFactory);
    this.initMessageSource();
    this.initApplicationEventMulticaster();
    this.onRefresh();
    this.registerListeners();
    this.finishBeanFactoryInitialization(beanFactory);
    this.finishRefresh();
    } catch (BeansException var9) {
    if (this.logger.isWarnEnabled()) {
    this.logger.warn("Exception encountered during context initialization - cancelling refresh attempt: " + var9);
    }

    this.destroyBeans();
    this.cancelRefresh(var9);
    throw var9;
    } finally {
    this.resetCommonCaches();
    }

    }
    }

    这里的beanFactory仍然是AnnotationConfigServletWebServerApplicationContext内部创建的DefaultListableBeanFactory,且当前一共有包括主类和后处理器在内的8个BeanDefinition.这里进入invokeBeanFactoryPostProcessors方法,该方法最终进入PostProcessorRegistrationDelegate类的静态方法:

    public static void invokeBeanFactoryPostProcessors(ConfigurableListableBeanFactory beanFactory, List<BeanFactoryPostProcessor> beanFactoryPostProcessors) {
    Set<String> processedBeans = new HashSet();
    ArrayList regularPostProcessors;
    ArrayList registryProcessors;
    int var9;
    ArrayList currentRegistryProcessors;
    String[] postProcessorNames;
    if (beanFactory instanceof BeanDefinitionRegistry) {
    BeanDefinitionRegistry registry = (BeanDefinitionRegistry)beanFactory;
    regularPostProcessors = new ArrayList();
    registryProcessors = new ArrayList();
    Iterator var6 = beanFactoryPostProcessors.iterator();

    while(var6.hasNext()) {
    BeanFactoryPostProcessor postProcessor = (BeanFactoryPostProcessor)var6.next();
    if (postProcessor instanceof BeanDefinitionRegistryPostProcessor) {
    BeanDefinitionRegistryPostProcessor registryProcessor = (BeanDefinitionRegistryPostProcessor)postProcessor;
    registryProcessor.postProcessBeanDefinitionRegistry(registry);
    registryProcessors.add(registryProcessor);
    } else {
    regularPostProcessors.add(postProcessor);
    }
    }

    currentRegistryProcessors = new ArrayList();
    postProcessorNames = beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
    String[] var16 = postProcessorNames;
    var9 = postProcessorNames.length;

    int var10;
    String ppName;
    for(var10 = 0; var10 < var9; ++var10) {
    ppName = var16[var10];
    if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
    currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class));
    processedBeans.add(ppName);
    }
    }

    sortPostProcessors(currentRegistryProcessors, beanFactory);
    registryProcessors.addAll(currentRegistryProcessors);
    invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry);
    currentRegistryProcessors.clear();
    postProcessorNames = beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
    var16 = postProcessorNames;
    var9 = postProcessorNames.length;

    for(var10 = 0; var10 < var9; ++var10) {
    ppName = var16[var10];
    if (!processedBeans.contains(ppName) && beanFactory.isTypeMatch(ppName, Ordered.class)) {
    currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class));
    processedBeans.add(ppName);
    }
    }

    sortPostProcessors(currentRegistryProcessors, beanFactory);
    registryProcessors.addAll(currentRegistryProcessors);
    invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry);
    currentRegistryProcessors.clear();
    boolean reiterate = true;

    while(reiterate) {
    reiterate = false;
    postProcessorNames = beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
    String[] var19 = postProcessorNames;
    var10 = postProcessorNames.length;

    for(int var26 = 0; var26 < var10; ++var26) {
    String ppName = var19[var26];
    if (!processedBeans.contains(ppName)) {
    currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class));
    processedBeans.add(ppName);
    reiterate = true;
    }
    }

    sortPostProcessors(currentRegistryProcessors, beanFactory);
    registryProcessors.addAll(currentRegistryProcessors);
    invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry);
    currentRegistryProcessors.clear();
    }

    invokeBeanFactoryPostProcessors((Collection)registryProcessors, (ConfigurableListableBeanFactory)beanFactory);
    invokeBeanFactoryPostProcessors((Collection)regularPostProcessors, (ConfigurableListableBeanFactory)beanFactory);
    } else {
    invokeBeanFactoryPostProcessors((Collection)beanFactoryPostProcessors, (ConfigurableListableBeanFactory)beanFactory);
    }

    String[] postProcessorNames = beanFactory.getBeanNamesForType(BeanFactoryPostProcessor.class, true, false);
    regularPostProcessors = new ArrayList();
    registryProcessors = new ArrayList();
    currentRegistryProcessors = new ArrayList();
    postProcessorNames = postProcessorNames;
    int var20 = postProcessorNames.length;

    String ppName;
    for(var9 = 0; var9 < var20; ++var9) {
    ppName = postProcessorNames[var9];
    if (!processedBeans.contains(ppName)) {
    if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
    regularPostProcessors.add(beanFactory.getBean(ppName, BeanFactoryPostProcessor.class));
    } else if (beanFactory.isTypeMatch(ppName, Ordered.class)) {
    registryProcessors.add(ppName);
    } else {
    currentRegistryProcessors.add(ppName);
    }
    }
    }

    sortPostProcessors(regularPostProcessors, beanFactory);
    invokeBeanFactoryPostProcessors((Collection)regularPostProcessors, (ConfigurableListableBeanFactory)beanFactory);
    List<BeanFactoryPostProcessor> orderedPostProcessors = new ArrayList();
    Iterator var21 = registryProcessors.iterator();

    while(var21.hasNext()) {
    String postProcessorName = (String)var21.next();
    orderedPostProcessors.add(beanFactory.getBean(postProcessorName, BeanFactoryPostProcessor.class));
    }

    sortPostProcessors(orderedPostProcessors, beanFactory);
    invokeBeanFactoryPostProcessors((Collection)orderedPostProcessors, (ConfigurableListableBeanFactory)beanFactory);
    List<BeanFactoryPostProcessor> nonOrderedPostProcessors = new ArrayList();
    Iterator var24 = currentRegistryProcessors.iterator();

    while(var24.hasNext()) {
    ppName = (String)var24.next();
    nonOrderedPostProcessors.add(beanFactory.getBean(ppName, BeanFactoryPostProcessor.class));
    }

    invokeBeanFactoryPostProcessors((Collection)nonOrderedPostProcessors, (ConfigurableListableBeanFactory)beanFactory);
    beanFactory.clearMetadataCache();
    }

    该方法传入三个后处理器,重要的一个是ConfigurationClassPostProcessor,用来解析主类,将其所在包内所有类的注解配置解析,创建、注册需要的Bean,这里执行加粗方法:

    private static void invokeBeanDefinitionRegistryPostProcessors(Collection<? extends BeanDefinitionRegistryPostProcessor> postProcessors, BeanDefinitionRegistry registry) {
    Iterator var2 = postProcessors.iterator();

    while(var2.hasNext()) {
    BeanDefinitionRegistryPostProcessor postProcessor = (BeanDefinitionRegistryPostProcessor)var2.next();
    postProcessor.postProcessBeanDefinitionRegistry(registry);
    }

    }

    上面加粗方法,其中的ConfigurationClassPostProcessor执行的是其下面的方法:

    public void processConfigBeanDefinitions(BeanDefinitionRegistry registry) {
    List<BeanDefinitionHolder> configCandidates = new ArrayList();
    String[] candidateNames = registry.getBeanDefinitionNames();
    String[] var4 = candidateNames;
    int var5 = candidateNames.length;

    for(int var6 = 0; var6 < var5; ++var6) {
    String beanName = var4[var6];
    BeanDefinition beanDef = registry.getBeanDefinition(beanName);
    if (!ConfigurationClassUtils.isFullConfigurationClass(beanDef) && !ConfigurationClassUtils.isLiteConfigurationClass(beanDef)) {
    if (ConfigurationClassUtils.checkConfigurationClassCandidate(beanDef, this.metadataReaderFactory)) {
    configCandidates.add(new BeanDefinitionHolder(beanDef, beanName));
    }
    } else if (this.logger.isDebugEnabled()) {
    this.logger.debug("Bean definition has already been processed as a configuration class: " + beanDef);
    }
    }

    if (!configCandidates.isEmpty()) {
    configCandidates.sort((bd1, bd2) -> {
    int i1 = ConfigurationClassUtils.getOrder(bd1.getBeanDefinition());
    int i2 = ConfigurationClassUtils.getOrder(bd2.getBeanDefinition());
    return Integer.compare(i1, i2);
    });
    SingletonBeanRegistry sbr = null;
    if (registry instanceof SingletonBeanRegistry) {
    sbr = (SingletonBeanRegistry)registry;
    if (!this.localBeanNameGeneratorSet) {
    BeanNameGenerator generator = (BeanNameGenerator)sbr.getSingleton("org.springframework.context.annotation.internalConfigurationBeanNameGenerator");
    if (generator != null) {
    this.componentScanBeanNameGenerator = generator;
    this.importBeanNameGenerator = generator;
    }
    }
    }

    if (this.environment == null) {
    this.environment = new StandardEnvironment();
    }

    ConfigurationClassParser parser = new ConfigurationClassParser(this.metadataReaderFactory, this.problemReporter, this.environment, this.resourceLoader, this.componentScanBeanNameGenerator, registry);
    Set<BeanDefinitionHolder> candidates = new LinkedHashSet(configCandidates);
    HashSet alreadyParsed = new HashSet(configCandidates.size());

    do {
    parser.parse(candidates);
    parser.validate();
    Set<ConfigurationClass> configClasses = new LinkedHashSet(parser.getConfigurationClasses());
    configClasses.removeAll(alreadyParsed);
    if (this.reader == null) {
    this.reader = new ConfigurationClassBeanDefinitionReader(registry, this.sourceExtractor, this.resourceLoader, this.environment, this.importBeanNameGenerator, parser.getImportRegistry());
    }

    this.reader.loadBeanDefinitions(configClasses);
    alreadyParsed.addAll(configClasses);
    candidates.clear();
    if (registry.getBeanDefinitionCount() > candidateNames.length) {
    String[] newCandidateNames = registry.getBeanDefinitionNames();
    Set<String> oldCandidateNames = new HashSet(Arrays.asList(candidateNames));
    Set<String> alreadyParsedClasses = new HashSet();
    Iterator var12 = alreadyParsed.iterator();

    while(var12.hasNext()) {
    ConfigurationClass configurationClass = (ConfigurationClass)var12.next();
    alreadyParsedClasses.add(configurationClass.getMetadata().getClassName());
    }

    String[] var23 = newCandidateNames;
    int var24 = newCandidateNames.length;

    for(int var14 = 0; var14 < var24; ++var14) {
    String candidateName = var23[var14];
    if (!oldCandidateNames.contains(candidateName)) {
    BeanDefinition bd = registry.getBeanDefinition(candidateName);
    if (ConfigurationClassUtils.checkConfigurationClassCandidate(bd, this.metadataReaderFactory) && !alreadyParsedClasses.contains(bd.getBeanClassName())) {
    candidates.add(new BeanDefinitionHolder(bd, candidateName));
    }
    }
    }

    candidateNames = newCandidateNames;
    }
    } while(!candidates.isEmpty());

    if (sbr != null && !sbr.containsSingleton(IMPORT_REGISTRY_BEAN_NAME)) {
    sbr.registerSingleton(IMPORT_REGISTRY_BEAN_NAME, parser.getImportRegistry());
    }

    if (this.metadataReaderFactory instanceof CachingMetadataReaderFactory) {
    ((CachingMetadataReaderFactory)this.metadataReaderFactory).clearCache();
    }

    }
    }

    上面的

    parser.parse(candidates);

    ConfigurationClassParser的方法,

    进入其

    @Nullable
    protected final ConfigurationClassParser.SourceClass doProcessConfigurationClass(ConfigurationClass configClass, ConfigurationClassParser.SourceClass sourceClass) throws IOException {
    this.processMemberClasses(configClass, sourceClass);
    Iterator var3 = AnnotationConfigUtils.attributesForRepeatable(sourceClass.getMetadata(), PropertySources.class, PropertySource.class).iterator();

    AnnotationAttributes importResource;
    while(var3.hasNext()) {
    importResource = (AnnotationAttributes)var3.next();
    if (this.environment instanceof ConfigurableEnvironment) {
    this.processPropertySource(importResource);
    } else {
    this.logger.warn("Ignoring @PropertySource annotation on [" + sourceClass.getMetadata().getClassName() + "]. Reason: Environment must implement ConfigurableEnvironment");
    }
    }

    Set<AnnotationAttributes> componentScans = AnnotationConfigUtils.attributesForRepeatable(sourceClass.getMetadata(), ComponentScans.class, ComponentScan.class);
    if (!componentScans.isEmpty() && !this.conditionEvaluator.shouldSkip(sourceClass.getMetadata(), ConfigurationPhase.REGISTER_BEAN)) {
    Iterator var13 = componentScans.iterator();

    while(var13.hasNext()) {
    AnnotationAttributes componentScan = (AnnotationAttributes)var13.next();
    Set<BeanDefinitionHolder> scannedBeanDefinitions = this.componentScanParser.parse(componentScan, sourceClass.getMetadata().getClassName());
    Iterator var7 = scannedBeanDefinitions.iterator();

    while(var7.hasNext()) {
    BeanDefinitionHolder holder = (BeanDefinitionHolder)var7.next();
    BeanDefinition bdCand = holder.getBeanDefinition().getOriginatingBeanDefinition();
    if (bdCand == null) {
    bdCand = holder.getBeanDefinition();
    }

    if (ConfigurationClassUtils.checkConfigurationClassCandidate(bdCand, this.metadataReaderFactory)) {
    this.parse(bdCand.getBeanClassName(), holder.getBeanName());
    }
    }
    }
    }

    this.processImports(configClass, sourceClass, this.getImports(sourceClass), true);
    importResource = AnnotationConfigUtils.attributesFor(sourceClass.getMetadata(), ImportResource.class);
    if (importResource != null) {
    String[] resources = importResource.getStringArray("locations");
    Class<? extends BeanDefinitionReader> readerClass = importResource.getClass("reader");
    String[] var19 = resources;
    int var21 = resources.length;

    for(int var22 = 0; var22 < var21; ++var22) {
    String resource = var19[var22];
    String resolvedResource = this.environment.resolveRequiredPlaceholders(resource);
    configClass.addImportedResource(resolvedResource, readerClass);
    }
    }

    Set<MethodMetadata> beanMethods = this.retrieveBeanMethodMetadata(sourceClass);
    Iterator var17 = beanMethods.iterator();

    while(var17.hasNext()) {
    MethodMetadata methodMetadata = (MethodMetadata)var17.next();
    configClass.addBeanMethod(new BeanMethod(methodMetadata, configClass));
    }

    this.processInterfaces(configClass, sourceClass);
    if (sourceClass.getMetadata().hasSuperClass()) {
    String superclass = sourceClass.getMetadata().getSuperClassName();
    if (superclass != null && !superclass.startsWith("java") && !this.knownSuperclasses.containsKey(superclass)) {
    this.knownSuperclasses.put(superclass, configClass);
    return sourceClass.getSuperClass();
    }
    }

    return null;
    }

    方法,加粗方法进入ComponentScanAnnotationParser的parse方法,该方法创建了ClassPathBeanDefinitionScanner实例,进入其doScan方法:

    protected Set<BeanDefinitionHolder> doScan(String... basePackages) {
    Assert.notEmpty(basePackages, "At least one base package must be specified");
    Set<BeanDefinitionHolder> beanDefinitions = new LinkedHashSet();
    String[] var3 = basePackages;
    int var4 = basePackages.length;

    for(int var5 = 0; var5 < var4; ++var5) {
    String basePackage = var3[var5];
    Set<BeanDefinition> candidates = this.findCandidateComponents(basePackage);
    Iterator var8 = candidates.iterator();

    while(var8.hasNext()) {
    BeanDefinition candidate = (BeanDefinition)var8.next();
    ScopeMetadata scopeMetadata = this.scopeMetadataResolver.resolveScopeMetadata(candidate);
    candidate.setScope(scopeMetadata.getScopeName());
    String beanName = this.beanNameGenerator.generateBeanName(candidate, this.registry);
    if (candidate instanceof AbstractBeanDefinition) {
    this.postProcessBeanDefinition((AbstractBeanDefinition)candidate, beanName);
    }

    if (candidate instanceof AnnotatedBeanDefinition) {
    AnnotationConfigUtils.processCommonDefinitionAnnotations((AnnotatedBeanDefinition)candidate);
    }

    if (this.checkCandidate(beanName, candidate)) {
    BeanDefinitionHolder definitionHolder = new BeanDefinitionHolder(candidate, beanName);
    definitionHolder = AnnotationConfigUtils.applyScopedProxyMode(scopeMetadata, definitionHolder, this.registry);
    beanDefinitions.add(definitionHolder);
    this.registerBeanDefinition(definitionHolder, this.registry);
    }
    }
    }

    return beanDefinitions;
    }

    这里的basePackages是上层解析主类解析出来的该类包名,这个方法内部又经过ClassPathScanningCandidateComponentProvider的scanCandidateComponents方法:

    private Set<BeanDefinition> scanCandidateComponents(String basePackage) {
    LinkedHashSet candidates = new LinkedHashSet();

    try {
    String packageSearchPath = "classpath*:" + this.resolveBasePackage(basePackage) + '/' + this.resourcePattern;
    Resource[] resources = this.getResourcePatternResolver().getResources(packageSearchPath);
    boolean traceEnabled = this.logger.isTraceEnabled();
    boolean debugEnabled = this.logger.isDebugEnabled();
    Resource[] var7 = resources;
    int var8 = resources.length;

    for(int var9 = 0; var9 < var8; ++var9) {
    Resource resource = var7[var9];
    if (traceEnabled) {
    this.logger.trace("Scanning " + resource);
    }

    if (resource.isReadable()) {
    try {
    MetadataReader metadataReader = this.getMetadataReaderFactory().getMetadataReader(resource);
    if (this.isCandidateComponent(metadataReader)) {
    ScannedGenericBeanDefinition sbd = new ScannedGenericBeanDefinition(metadataReader);
    sbd.setResource(resource);
    sbd.setSource(resource);
    if (this.isCandidateComponent((AnnotatedBeanDefinition)sbd)) {
    if (debugEnabled) {
    this.logger.debug("Identified candidate component class: " + resource);
    }

    candidates.add(sbd);
    } else if (debugEnabled) {
    this.logger.debug("Ignored because not a concrete top-level class: " + resource);
    }
    } else if (traceEnabled) {
    this.logger.trace("Ignored because not matching any filter: " + resource);
    }
    } catch (Throwable var13) {
    throw new BeanDefinitionStoreException("Failed to read candidate component class: " + resource, var13);
    }
    } else if (traceEnabled) {
    this.logger.trace("Ignored because not readable: " + resource);
    }
    }

    return candidates;
    } catch (IOException var14) {
    throw new BeanDefinitionStoreException("I/O failure during classpath scanning", var14);
    }
    }

    这里扫描到了主类包下所有我们自定义的类:

    最终将要创建的Bean全部处理成BeanDefinition注册到registry,这里经过多次递归上面的几个主要类的处理过程,最终创建所有194个Bean:

    处理完所有的Bean后,PostProcessorRegistrationDelegate的方法继续执行,执行了其他几个后处理器,最后回到AbstractApplicationContext的refresh方法,最后回到SpringApplication的

    this.refreshContext(context);

    方法,最终完成所有方法,SpringBoot启动完成。

    一定要断点调试,直接看源码臆想过程会出错!!

    基础知识地址:

    https://www.cnblogs.com/xiaoxi/p/6392154.html

    https://blog.csdn.net/masterchiefcc/article/details/80358977

  • 相关阅读:
    Cousera课程Learning How to Learn学习报告
    C语言中当无符号数遇到符号数
    STC15 串口(工作方式1)使用小结
    取C语言头文件的文件名
    linux 的 shell 逻辑
    Win7 局域网内简单共享的设置
    写了一个批处理,可以实现文件备份,自动对比删除冗余文件。
    C语言 函数指针的应用
    自动控制原理 典型环节频率特性对比
    51单片机汇编的溢出标志位OV和进位标志位CY
  • 原文地址:https://www.cnblogs.com/free-wings/p/10005763.html
Copyright © 2011-2022 走看看