SpringBoot
- 自动配置
- 起步依赖 starter
- actuator 监控
- 命令行
自动配置
使用
@EnableAutoConfiguration注解 ,@SpringBootApplication已经包含此注解
启动自动配置,可以通过exclude进行排除,手动配置
spring.factories配置文件进行自动配置
自动配置的原理
根据条件判断是否需要某些自动配置
例如依赖了H2的jar,包含H2的对象,又没有配置类,就自动加载默认配置
注解举例:
@Conditional,@ConditionalOnClass, @ConditionalOnBean, @ConditionalOnPropertiy(enable = true ),@onMissingBean(xx.class)
注解原理:BeanFactoryPostProcessor查找bean的定义信息
判断类是否存在,ClassUtils.isPresent()
判断Bean是否存在,ListableBeanFactory列出Bean信息
判断存在某些bean,不存在bean进行自动配置
如何查看是否使用了自动配置
--debug打印包含,不包含的一些自动配置
Positive matches:
Negative matches:
Exclusion matches:
uncondition matches:
起步依赖
解决问题:
对于一个服务的依赖,例如mybatis,不知道具体有多少具体依赖包的问题
面向功能,根据功能解析对应需要的依赖
自动配置 + 依赖管理
配置的优先级
DevTools
@TestPropertySource注解
Java命令参数
System.getProperties()
操作系统环境变量
Actuator监控
监控并管理应用程序
两种方法:http,jmx
功能
显示bean,缓存,配置项,环境信息,日志级别,heapdump
Spring-boot-admin监控
提供可视化管理界面,提供通知机制
启动原理
1.启动类上添加注解,执行启动类
@SpringBootApplication包含几个子注解**@SpringBootConfiguration,@EnableAutoConfiguration**和@ComponentScan
@EnableAutoConfiguration开启自动配置:原理是ImportSelector接口+@Conditional注解实现,导入并使用指定配置
2.调用SpringApplication的run方法
SpringApplication.run(SpringDemosApplication.class, args);这个方法创建SpringApplication对象
使用SpringFactoriesLoader加载工厂类
原理:读取META-INF/spring.factories 找到并加载了很多工厂类,例如listener,通过反射实例化为各个配置类
3.初始化一堆Listener,这里是观察者模式
具体执行了这些操作:
- 创建一个StopWatch实例,用来记录SpringBoot的启动时间
- 通过SpringFactoriesLoader加载listeners:比如EventPublishingRunListener
- 发布SprintBoot开始启动事件(EventPublishingRunListener#starting())
- 创建和配置environment(environmentPrepared())
- 打印SpringBoot的banner和版本
- 创建对应的ApplicationContext:Web类型,Reactive类型,普通的类型(非Web)
- prepareContext
- 准备ApplicationContext,Initializers设置到ApplicationContext(contextPrepared())
- 打印启动日志,打印profile信息(如dev, test, prod)
- 最终会调用到AbstractApplicationContext#refresh方法,实际上就是Spring IOC容器的创建过程,并且会进行自动装配的操作,以及发布ApplicationContext已经refresh事件,标志着ApplicationContext初始化完成(contextLoaded())
- afterRefresh hook方法
- stopWatch停止计时,日志打印总共启动的时间
- 发布SpringBoot程序已启动事件(started())
- 调用ApplicationRunner和CommandLineRunner
- 最后发布就绪事件ApplicationReadyEvent,标志着SpringBoot可以处理就收的请求了(running())
SpringIOC 容器初始化过程
由于现在大都是用SpringBoot开发,所以呢,Spring IOC 初始化的源码,就是AnnotationConfigApplicationContext中的源码,IOC的初始化就是该类实例创建的过程。
创建的过程(AnnotationConfigApplicationContext的构造方法)
- 给我们的Bean,创建与之对应的BeanDefinition,然后把他们放入ConcurrentHashMap(key:beanName和value:beanDefinition)中;BeanDefinition实际上包括一些Bean的信息,比如BeanName, Scope, 是否被**@Primary注解修饰,是否是@Lazy**,以及**@Description**等注解
- 入口是**refresh()**方法: 创建IOC需要的资源
- 初始化BeanFactory, set一些属性,如BeanClassLoader,systemEnvironment
- 如果是SpringBoot程序,会调用方法进行自动装配:AutoConfigurationImportSelector.AutoConfigurationGroup#process,见:@EnableAutoConfiguration的总结
- 注册MessageSource,国际化相关的资源,到ApplicationContext
- 注册ApplicationListener到ApplicationContext
- 实例化化lazy-init的Bean
- 最后,publish相关的事件,ApplicationContext 就初始化完成,整个IOC容器初始化完成(IOC容器的本质就是初始化BeanFactory和ApplicationContext),就可以从IOC容器中获取Bean自动注入了
Bean的初始化
PostPostProcessor前置 - 检查是否是InitializingBean - init方法 - PostProcessor后置
初始化顺序
Constructor > @PostConstruct > InitializingBean > init-method
初始化区别
spring为bean提供了两种初始化bean的方式,实现InitializingBean接口,实现afterPropertiesSet方法,或者在配置文件中同过init-method指定
实现InitializingBean接口是直接调用afterPropertiesSet方法,比通过反射调用init-method指定的方法效率相对来说要高点;
init-method方式消除了对spring的依赖;
BeanFactory和ApplicationContext的区别
他俩都是接口,Application继承了Beanfactory
Beanfactory提供了实例化对象和获取对象的功能
Application提供了国际化,资源加载等功能,在启动之初创建所有bean
MVC处理请求的流程
1.用户发送请求,DispatcherServlet收到请求
2.DispatcherServlet调用HandlerMapping处理器映射器,查询对应的handler,返回执行链
3.Handler根据请求url匹配找到具体的Controller,生成处理对象的Controller以及Filter,返回给DispatcherServlet
4.DispatcherServlet通过handlerAdapter适配器找到并调用Controller中具体的的方法
5.执行处理器具体方法,Controller调用service,dao等执行具体方法
6.Controller处理完成,返回Model和view给HandlerAdapter
7.Handler将model and view 返回给dispatcherServlet
8.Dispatcher将mode and view交给viewResolver视图解析
9.viewResolver解析后返回具体view
10.DispatcherServlet对view进行渲染视图,
11.DispatcherServlet响应请求,返回结果
名词解析
- DispatcherServlet:前端控制器,也称为中央控制器,它是整个请求响应的控制中心,组件的调用由它统一调度。
- HandlerMapping:处理器映射器,它根据用户访问的 URL 映射到对应的后端处理器 Handler。也就是说它知道处理用户请求的后端处理器,但是它并不执行后端处理器,而是将处理器告诉给中央处理器。
- HandlerAdapter:处理器适配器,它调用后端处理器中的方法,返回逻辑视图 ModelAndView 对象。
- ViewResolver:视图解析器,将 ModelAndView 逻辑视图解析为具体的视图(如 JSP)。
- Handler:后端处理器,对用户具体请求进行处理,也就是我们编写的 Controller 类。
BEANFACTORY和FACTORYBEAN的区别与联系
-
两者都是接口;
-
BeanFactory主要是用来创建Bean和获得Bean的;
-
FactoryBean跟普通Bean不同,其返回的对象不是指定类的一个实例,而是该FactoryBean的getObject方法所返回的对象;
自己是个bean对象,并提供getObject方法生产bean对象,getobject,getType,isSingleton
-
通过BeanFactory和beanName获取bean时,如果beanName不加&则获取到对应bean的实例;如果beanName加上&,则获取到FactoryBean本身的实例
-
FactoryBean 通常是用来创建比较复杂的bean(如创建mybatis的SqlSessionFactory很复杂),一般的bean 直接用xml配置即可,但如果创建一个bean的创建过程中涉及到很多其他的bean 和复杂的逻辑,用xml配置比较困难,这时可以考虑用FactoryBean。
-
SqlSessionFactory包含mybatis-config,Mapper等