手机手机端网站建设系统软件开发服务
手机手机端网站建设,系统软件开发服务,制作网线颜色顺序,专业生产车间设计图纸网站推荐阅读#xff1a;Spring全家桶笔记#xff1a;SpringSpring BootSpring CloudSpring MVC疫情期间“闭关修炼”#xff0c;吃透这本Java核心知识#xff0c;跳槽面试不心慌2020“闭关”跳槽季#xff0c;啃透分布式三大技术#xff1a;限流、缓存、通讯基本环境开发工具…推荐阅读Spring全家桶笔记SpringSpring BootSpring CloudSpring MVC疫情期间“闭关修炼”吃透这本Java核心知识跳槽面试不心慌2020“闭关”跳槽季啃透分布式三大技术限流、缓存、通讯基本环境开发工具:Intellij IDEA 2017(盗)版java版本1.8.0_151spring的github地址:spring-framework准备git clone或直接下载github上的spring源码导入idea中在项目路径下执行gradle build (如果本机没有gradle环境或者版本差很多就用gradlew代替)会build很久可以事先将阿里的maven仓库地址加到repositories中像这样:repositories { maven { url http://maven.aliyun.com/nexus/content/groups/public/ } maven { url https://repo.spring.io/plugins-release }}会用到的缩写:ApplicationContext - ACApplicationContextInitializer - ACIBeanFactory - BFApplicationListener - ALEnvironmentPostProcessor - EPPspring boot 应用的启动/*** author pk* date 2018/02/22*/SpringBootApplicationpublic class SpringBootTwoStudyApplication {public static void main(String[] args) {SpringApplication springApplication new SpringApplication(SpringBootTwoStudyApplication.class);//可以在run之前,对AC进行一些自定义的配置,添加点ApplicationListener,ApplicationContextInitializer啥的springApplication.run(args);}}一.SpringApplication的初始化代码如下public SpringApplication(ResourceLoader resourceLoader, Class... primarySources) { this.resourceLoader resourceLoader; Assert.notNull(primarySources, PrimarySources must not be null); this.primarySources new LinkedHashSet(Arrays.asList(primarySources));//1 this.webApplicationType deduceWebApplicationType();//2 setInitializers((Collection) getSpringFactoriesInstances( ApplicationContextInitializer.class));//3 setListeners((Collection) getSpringFactoriesInstances(ApplicationListener.class));//4 this.mainApplicationClass deduceMainApplicationClass();//5 }1.设置启动类primarySources到对应属性这个启动类就是在初始化SpringApplication时候的参数,可以有多个2.获取web应用类型根据当前classpath下存在的类来判断的:如果存在org.springframework.web.reactive.DispatcherHandler,就是REACTIVE如果不存在org.springframework.web.servlet.DispatcherServlet或者javax.servlet.Servlet,就是NONE否则,就是SERVLET3.设置ApplicationContextInitializer代码如下:private Collection getSpringFactoriesInstances(Class type, Class[] parameterTypes, Object... args) { ClassLoader classLoader Thread.currentThread().getContextClassLoader();//3.1 Set names new LinkedHashSet( SpringFactoriesLoader.loadFactoryNames(type, classLoader));//3.2 List instances createSpringFactoriesInstances(type, parameterTypes, classLoader, args, names);//3.3 AnnotationAwareOrderComparator.sort(instances);//3.4 return instances; }3.1 获取线程上下文ClassLoaderTODO(ClassLoader的相关解释)3.2 使用SpringFactoriesLoader加载出classpath下所有路径为META-INF/spring.factories的资源文件,并读取key为ApplicationContextInitializer的值会得到如些几个类(实际是全称类名)SharedMetadataReaderFactoryContextInitializerAutoConfigurationReportLoggingInitializerConfigurationWarningsACIContextIdACIDelegatingACIServerPortInfoACI3.3 利用反射创建出上述ACI的实例3.4 排序根据Ordered接口/PriorityOrder注解/Order注解去排 其他地方的排序基本也是按照这个规则来排的4.设置listener跟设置ACI的方法一样,也是读取spring.factories文件中的对应key项所对应的所有类名,然后实例化、排序. 得到如下几个ApplicationListener:BackgroundPreinitializerClearCachesALParentContextCloserALFileEncodingALAnsiOutputALConfigFileALDelegatingALClasspathLoggingALLoggingALLiquibaseServiceLocatorAL5.设置mainApplicationClass就是找到main方法所在的类.是唯一的,跟上面的primarySources不是一回事二.SpringApplication的run(String … args)方法代码如下:public ConfigurableApplicationContext run(String... args) { StopWatch stopWatch new StopWatch(); stopWatch.start();//1 ConfigurableApplicationContext context null; Collection exceptionReporters new ArrayList(); configureHeadlessProperty();//2 SpringApplicationRunListeners listeners getRunListeners(args);//3 listeners.starting();//4 try { ApplicationArguments applicationArguments new DefaultApplicationArguments( args);//5 ConfigurableEnvironment environment prepareEnvironment(listeners, applicationArguments);//6 configureIgnoreBeanInfo(environment);//7 Banner printedBanner printBanner(environment);//8 context createApplicationContext();//9 exceptionReporters getSpringFactoriesInstances( SpringBootExceptionReporter.class, new Class[] { ConfigurableApplicationContext.class }, context);//10 prepareContext(context, environment, listeners, applicationArguments, printedBanner);//11 refreshContext(context);//12 afterRefresh(context, applicationArguments);//13 listeners.finished(context, null);//14 stopWatch.stop(); //15 if (this.logStartupInfo) { new StartupInfoLogger(this.mainApplicationClass) .logStarted(getApplicationLog(), stopWatch); } callRunners(context, applicationArguments);//16 return context; } catch (Throwable ex) { handleRunFailure(context, listeners, exceptionReporters, ex); throw new IllegalStateException(ex); } }1. 创建一个StopWatch用于记录启动的时间2. 配置java.awt.headless属性,默认为true这个headless是一种模式,是指缺少显示屏、键盘或者鼠标时的系统配置 我找了spring和spring boot的源码,只有ImageBanner里面用到了3.从spring.factories中加载出SpringApplicationRunListener,并构建一个SpringApplicationRunListenersStringApplicationListeners就是对对个SpringApplicationRunListener的包装 现在看只有一个具体实现类EventPublishingRunListener虽然这个类叫做listener,但其实起的作用是传播事件,更像是一个ApplicationEventMulticaster。 spring boot启动过程中的事件,主要由这个类来传播4.发布一个ApplicationStartingEvent事件关于spring事件发布机制请看spring事件机制 响应的ALLoggingAL初始化日志系统 做法是按照logbacklog4jjul的顺序查找classpath下存在的相关类LiquibaseServiceLocatorAL实在是没有用过这个东西不知道这个LiquibaseService是个啥…5.根据启动时的命令行参数构建一个ApplicationArgumentsApplicationArguments的接口定义:public interface ApplicationArguments { String[] getSourceArgs(); //--开头的参数 Set getOptionNames(); boolean containsOption(String name); //--开头的参数是允许重复定义的不会覆盖 List getOptionValues(String name); List getNonOptionArgs();}这个类的作用就是解析所有的启动参数的6.prepareEnvironment():创建并配置environment代码如下private ConfigurableEnvironment prepareEnvironment( SpringApplicationRunListeners listeners, ApplicationArguments applicationArguments) { ConfigurableEnvironment environment getOrCreateEnvironment();//6.1 configureEnvironment(environment, applicationArguments.getSourceArgs());//6.2 listeners.environmentPrepared(environment);//6.3 bindToSpringApplication(environment);//6.4 if (this.webApplicationType WebApplicationType.NONE) { environment new EnvironmentConverter(getClassLoader()) .convertToStandardEnvironmentIfNecessary(environment); } ConfigurationPropertySources.attach(environment);//6.5 return environment; }6.1 根据WebApplicationType创建对应类型的environment关于spring中Environment/PropertySource的介绍:根据webApplicationTypeSERVLET - StandardServletEnvironmentNONE/REACTIVE - StandardEnvironment初始化的时候会在构造函数中调用customizePropertySources()方法其结果是会在environment的propertySources属性的propertySourcesList列表中加入以下PropertySource代表ServletConfig的构建参数的名为servletConfigInitParams的StubPropertySource(目前只是作为占位符存在)代表ServletContext的构建参数的名为servletContextInitParams的StubPropertySource(目前只是作为占位符存在)代表jvm属性参数的名为systemProperties的MapPropertySource(来源于System.getProperties()方法)代表环境变量的名为systemEnvironment的SystemEnvironmentPropertySource(来源于System.getEnv()方法)6.2 配置environment配置PropertySources 看看SpringApplication的defaultProperties属性是否为空如果不为空则加入一个MapPropertySource到propertySources中。这个defaultProperties属性可以在SpringApplication调用run方法之前通过setDefaultProperties()方法设置看看有没有命令号参数如果有则创建一个SimpleCommandLinePropertySource加入到propertySources中配置activeProfiles:就是将spring.profiles.active属性的值作为数组读入6.3 listeners发布一个ApplicationEnvironmentPreparedEvent这是一个很重要的事件响应的listener有很多ConfigFileApplicationListener 从spring.factories中读取所有的EnvironmentPostProcessor它自己也是个EPP。排序然后逐个调用 SystemEnvironmentPropertySourceEPP:替换systemEnvironment为其内部类OriginAwareSystemEnvironmentPropertySourceSpringApplicationJsonEPP解析spring.application.json属性作为JsonPropertySource加入propertySources中CloudFoundryVcapEPP:VCAP相关不懂略过ConfigFileAL(自己) 添加一个RandomValuePropertySource作用是设置所有random.int/long开头的属性为一个随机值从spring.factories中读取PropertySourceLoader PropertiesPropertySourceLoader读取.properties配置文件YamlPropertySourceLoader读取.yaml配置文件根据activeProfiles解析每个对应的配置文件成OriginTrackedMapPropertySource加入到propertySources中6.4 将environment绑定到SpringApplication中todo…6.5 往propertySources中加入一个ConfigurationPropertySourcesPropertySource7.配置一个spring.beaninfo.ignore属性,默认为true8.打印banner9.根据webApplicationType构建ApplicationContextSERVLET - AnnotationConfigServletWebServerACREACTIVE - ReactiveWebServerACNONE - AnnotationConfigAC 按照继承结构DefaultResourceLoader:ResourceLoader的默认实现作用就是加载Resource内部有个比较重要的ProtocolResolver集合属性具体使用请看ProtocolResolver解析AbstractAC配置了一个ResourcePatternResolver具体请看Resource相关GenericAC初始化了一个BeanFactory具体类型是DefaultListableBeanFactory作者pumpkin_pk原文链接https://blog.csdn.net/yuxiuzhiai/article/details/79074249
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/pingmian/89126.shtml
如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!