IOC DI机制
IOC的意思是控制反转,控制的意思啊由Spring 工厂控制对象,反转是从我们主动创建好对象反转为等待Spring 工厂的注入
DI是依赖注入,组件需要的依赖对象由容器注入,主要通过setter 构造器 接口三种注入方式注入.
AOP 面向切面编程
AOP思想是做无侵入式的功能增强,即在不改变其原有方法代码的情况下,增加一定的功能.AOP是通过代理实现的.
Spring中AOP的核心是动态代理,jdk动态代理或CGLIB代理.
AOP分为:
- 前置通知
- 后置通知
- 后置返回值通知
- 异常通知
- 环绕通知
AOP的实现步骤
- 首先定义一个切面,创建一个类,在类上添加注解Aspect
- 生命一个方法,定一个那些方法需要被织入,使用Pointcut注解
- 定义增强操作,如前置通知 @Befare 后置通知@After 等等.
- 建立切面与切点之间的关联
@Aspect
@Component
public class LogAspect {
private final Logger logger = LoggerFactory.getLogger(this.getClass());
// 定义切点,对所有 public 方法进行拦截
@Pointcut("execution(public * com.example..*.*(..))")
public void logPointcut() {}
// 定义前置通知,在目标方法执行前执行
@Before("logPointcut()")
public void beforeAdvice(JoinPoint joinPoint) {
logger.info("beforeAdvice: " + joinPoint.getSignature().getName());
}
// 定义后置通知,在目标方法执行后执行
@AfterReturning("logPointcut()")
public void afterAdvice(JoinPoint joinPoint) {
logger.info("afterAdvice: " + joinPoint.getSignature().getName());
}
// 定义异常通知,在目标方法抛出异常时执行
@AfterThrowing(pointcut = "logPointcut()", throwing = "ex")
public void throwingAdvice(JoinPoint joinPoint, Exception ex) {
logger.error("throwingAdvice: " + joinPoint.getSignature().getName() + " occurs an exception, exception message is: " + ex.getMessage());
}
}
Spring Boot自动装配原理
从启动类上的注解一步步推吧
Spring Boot 的启动类上需要添加@SpringBootApplication注解,看一下它的源码
这里可以看到有两个注解,@SpringBootConfiguration 和 @EnableAutoConfiguration ,先看一下@SpringBootConfiguration
@SpringBootConfiguration
查看它的源码,可以看到它上面包含了注解@Configuration,其中又包含了@Component
也就是说添加了注解@Configuration或者SprigBootConfiguration的类都会成为SpringBoot的配置类,交给容器同一管理.
@EnableAutoConfiguration
这个注解的作用在于开启自动配置的功能,其中包含了两个注解@AutoConfigurationPackage,和@Import(AutoConfigurationImportSelector.class)
@AutoConfigurationPackage
这个注解的作用在于将主配置类,即添加了SpringBootApplication注解的启动类所在的包及包下包含的所有中间扫描并加载到spring工厂中.
@Import(AutoConfigurationImportSelector.class)
这个注解的作用是将需要自动装配的类以全类名的方式返回.在类AutoConfigurationImportSelector中存在一个方法selectImports,其中调用了getAutoConfigurationEntry方法
又依次调用了getCandidateConfigurations方法,loadFactoryNames方法,loadSpringFactories方法.
loadSpringFactories方法会扫描所有在META-INF路径下的spring.factories文件