Spring
文章平均质量分 81
Spring 框架使用和源码分析
魔道不误砍柴功
我亦无它,唯手熟尔!
展开
-
Spring 之 DispatcherServlet 和 @EnableWebMvc 源码分析及一些问题
分析到这里,可以知道getHandler() 方法最终会返回两个类型值,一个是(使用 @RequestMapping 注解的返回这个类型)、一个是类的本身(实现 Controller、HttpRequestHandler 接口返回类本身实例侧面说明通过 request 请求找到了一个可以处理当前请求的方法,接下来就是看怎么调用该方法,那就要看() 方法怎么去适配调用,因为每种类型的 Controller 里的方法形式都不一样,所以需要一层适配器封装调用。} }发现里面维护了一个urlMap。原创 2023-02-08 17:31:28 · 527 阅读 · 0 评论 -
Spring 之 @Cacheable 源码解析(上)
当要使用 @Cacheable 注解时需要引入 @EnableCaching 注解开启缓存功能。为什么呢?现在就来看看为什么要加入 @EnableCaching 注解才能开启缓存切面呢?可以看出是通过 @Import 注解来导入一个类 CachingConfigurationSelector,猜测下,这个类肯定是一个入口类,也可以说是个触发类。注意此处 mode() 默认是。类、类。那么接下来就重点分析这两个类是用来干啥的?原创 2023-01-18 23:25:03 · 2509 阅读 · 0 评论 -
Spring 之 @Cacheable 源码解析(下)
在 loadCaches() 方法中可以返回非常多 Cache 实例,那么这么多实例要怎么存呢,肯定需要有映射关系,那么必然采用 Map,那么 key 就是对应的 cacheName,value 就是对应的 Cache,Spring 就是这样设计的。:先去查对应缓存(Redis、LocalMap 等缓存),缓存命中直接返回,未命中,先创建 CachePutRequest 请求头,在去调用目标方法获取数据(可能从数据库中查询数据等),然后将查到的数据保存到对应缓存中,最后返回获取到的数据。原创 2023-01-18 23:24:48 · 2297 阅读 · 0 评论 -
Spring 之 @Cacheable 缓存使用教程
该抽象类提供 loadCaches() 方法,可以获取到所有 Cache 接口实现类。所以这里能够获取到所有缓存。那么肯定是可以使用双缓存。/*** 直接实现 AbstractCacheManager 抽象类的钩子方法,该类已经写好模版方法* 当执行的时候,如果 MyGuavaCacheManager 管理类 @Bean 的话,就会勾到这个方法逻辑* @return} }} }最终通过注入一个缓存管理类 MySimpleCacheManager 就可以使用到三个缓存。原创 2023-01-18 13:20:22 · 4339 阅读 · 0 评论 -
Spring 之 @Transactional 注解简单使用及源码分析
但是这段逻辑是一个模版模式,也就是一段公共逻辑,所以是在抽象类中写的。因为类是一个抽象类,不可能被实例化的,那么如何会调用到这段逻辑呢?肯定需要去找这个抽象类的子类,所以类就去实现类。所以可以看出注解只是引入一个入口类,在这里入口类中并没有做什么逻辑,有用逻辑都是在它父类中完成。/** 合适的通知不为空 */ if(specificInterceptors!方法会去收集当前 bean 有哪些 Advisor 可以对其增强。如果找到有 Advisor 可以对其增强,就会调用方法为其创建代理对象。原创 2023-01-10 15:03:30 · 1338 阅读 · 1 评论 -
Spring 之编程式事务的简单使用
声明式事务控制粒度比较大,所以连接对象需要经过比较长的时间才能够回收到连接池中,如果请求很多,同事方法执行比较久,有可能会导致连接池连接对象不足,请求来不及处理。此时如果又想要有事务,并且粒度不能太大,就可以使用编程式事务,而且编程式事务对分布式事务也是可以支持的。原创 2023-01-09 20:28:33 · 499 阅读 · 0 评论 -
Spring 之 @Async 的简单使用与源码解析
有时候需我们需要让一个方法异步执行,但是又不想自己去写异步代码,毕竟和业务不相关。所以 Spring 就非常友好,提供 @Async 注解让方法异步执行。想要让 @Async 注解生效,必须通过注解来激活这个功能。从打印结果中可看出两个 show() 方法时被在 SimpleAsyncTaskExecutor-1 线程中执行的,并不是在 main() 线程中。说明 @Async 已经生效。原创 2023-01-09 19:46:44 · 985 阅读 · 0 评论 -
SpringMVC 定义 Controller 的几种简单方式
所以用的最多的都是通过 @RequestMapping 注解来再一个类中定义多个方法,每个方法对应处理一个 url 请求。这样就不用写过多的 Controller 类。以上两种写法更多出现在源码中,因为在源码中内置的 Handler 和 url 都会建立好映射关系。在开发中比较少用,不够灵活,一个 url 需要对应一个类,有点大题小做的感觉。原创 2023-01-06 18:06:06 · 1042 阅读 · 1 评论 -
Spring 中常用的几个工具类
获取某个类的某个方法上是否有标注注解,并可以通过其他 API 获取到这个类注解上的属性值,该工具类其他 API 下面截图可以查看。原创 2023-01-04 16:27:13 · 1044 阅读 · 0 评论 -
Spring 提前生成代理 Give BeanPostProcessors a chance to return a proxy instead of the target bean instance
因为没有执行 doCreateBean() 方法,会认为还没有创建好目标对象,就生成代理对象,有点扯淡,从而就会质疑 Spring 在源码中那个地方注释这样一句话就很离谱。从上述源码中可以看出,如果想要返回目标对象,就需要让 customTargetSourceCreators 集合有值,才有机会返回对象,并且还要重写 getTargetSource() 方法,返回一个自定义的目标对象,这样才能保证有在此处有提前生成好的目标对象返回,这样就能够在 doCreateBean() 方法之前就提前生成代理对象。原创 2023-01-03 20:12:50 · 550 阅读 · 0 评论 -
Spring 之 @EnableAspectJAutoProxy 简单使用和源码分析
注意这个类又什么特点呢?可以看出这个类是 Spring BeanPostProcessor 接口的应用。BeanPostProcessor 接口设计非常灵活。这里主要关注#postProcessAfterInstantiation() 方法,因为主要逻辑在这个方法里面。这个抽象类把公共的核心逻辑写好,子类只需要重写其中的一些方法即可,这其实是模版设计模式的一种体现。if(bean!= null) {原创 2022-12-31 19:39:55 · 4537 阅读 · 0 评论 -
Spring 之 @Aspect 切面的几种简单方式
如果不用 @Aspect 注解的话,也可以通过自定义Advisor} }/*** @desc:System . out . println("我是 MyMethodAdvice 增强逻辑....");} }} /*** 控制更细粒度的开关} /*** 可以对参数进行判断做到了更新粒度的切面控制} }在执行时,Spring 就会收集到你自定义的 Advisor 来做切面逻辑。/**原创 2022-12-30 17:13:49 · 2724 阅读 · 0 评论 -
SpringBoot 之自动装配简单使用
其实归根结底还是Spring 的 SpringFactoriesLoader 工厂加载机制 + @Import(DeferredImportSelector)实现的,之前说配置文件必须写死 META-INF/spring.factories 规范也就是 Spring 的 SpringFactoriesLoader 规范。上升到 SpringBoot 就完美利用这两点功能实现了自动装配。然后 SpringBoot 将 @EnableXxx 各式各类注解统一命名成 @简单明了!这也就是为什么。原创 2022-12-28 14:45:39 · 1771 阅读 · 0 评论 -
Spring 之 @Import 注解使用与源码浅析
再说 @Import 之前先回忆下 @Component 的作用,在类上标注该注解,该类就能够被 Spring 扫描封装成 BeanDefinition 并注册到容器中。但现在需要将第三方 jar 包、或者其他路径下面的包中的类也要被扫描注册呢?原创 2022-12-27 16:12:02 · 856 阅读 · 0 评论 -
Spring 中 ConfigurationClassPostProcessor 类扫描解析之 @ComponentScan 解析
读取所有资源文件判断哪些有 @Component 修饰,封装成 BeanDefinition,然后注册到 Spring 容器中完事。原创 2022-12-20 22:27:33 · 969 阅读 · 7 评论 -
Spring 之 @Component 和 @Configuration 两者区别以及源码分析
之前一直搞不清 @Component 和 @Configuration 这两个注解到底有啥区别,一直认为被这两修饰的类可以被 Spring 实例化嘛,不,还是见识太短,直到今天才发现这两玩意有这么大区别。很幸运能够及时发现,后面可以少走点坑,下面就直接通过最简单的案例来说明它两的区别,颠覆你的认知。原创 2022-12-20 18:03:41 · 3405 阅读 · 1 评论 -
Spring 之 MutablePropertyValues 和 ConstructorArgumentValues 的简单理解
其实在绝大多情况下,MutablePropertyValues 这个类很少用,但是涉及到框架改造扩展可能就要使用到这个类。并且这个类在 BeanDefinition 模板中也是一个非常重要的角色。:Bean 唯一标识名称。:类全限定名(包名+类名)。:定义 Bean 初始化方法,Bean 组装之后调用,必须是一个无参数方法。:定义 Bean 销毁方法,在 BeanFactory 关闭时触发,同样也必须是一个无参构造方法,只能应用于 SingletonBean 单例 Bean。原创 2022-12-19 23:08:35 · 1480 阅读 · 0 评论 -
Spring 中 @Value 注解使用和源码分析
先配置本地可以看到最终在 Apple 中可以获取到配置文件中的值,那么 Spring 是怎样解析获取到该值的呢?下面开始分析下。原创 2022-12-18 19:37:17 · 2559 阅读 · 1 评论 -
将对象交给 Spring 管理的几种方式
该接口其实是 BeanFactoryPostProcessor 接口的一个衍生子类,除了父类提供的 postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) 获取 BeanFactory 对象的方法,子类还扩充了一个可以获取 postProcessBeanDefinitionRegistry(BeanDefinitionRegistry registry) 注册器的方法。原创 2022-12-17 17:48:34 · 2634 阅读 · 1 评论 -
Spring 之类元数据封装—MetadataReader
在 Spring 中最喜欢干的事情就是将多个参数封装到一个对象,这里就挑选一个例子讲讲——MetadataReader,这个对象是将一个类封装成了三部分:File 文件本身,类元数据,注解元数据。原创 2022-12-16 20:25:26 · 956 阅读 · 0 评论 -
Spring 通过 @Lazy 注解解决构造方法循环依赖问题
像这种在 Apple 里面有一个属性 Orange、Orange 中有一个属性 Apple,你中有我,我中有你,这样可以称之为循环依赖。循环依赖问题不止在 Spring 中有,在 Mybatis 中也有,解决思想基本一样,都需要借助额外的缓存进行实现。Spring 对于这种属性注入的循环依赖是支持的,不会有任何问题,今天这里探讨一下 Spring 中构造方法的循环依赖问题,Spring 默认是不支持的,但是也提供了方法解决。原创 2022-12-11 15:51:10 · 8329 阅读 · 2 评论 -
Spring 中 @Autowired 修饰构造方法时注意事项
1、当有且仅有1个构造方法时,Spring 都只会使用这个构造方法创建实例。2、Spring 优先选择 被 @Autowired 标注的构造方法3、当有多个构造方法同时存在时,Spring 默认选择空构造方法,若此时没有空构造方法,就会报错。4、当有多个方法同时存在时,想指定 Spring 具体用哪个构造方法,可以加上 @Autowired 注解来标识,如果此时有多个 @Autowired 同时存在,需要将所有的 required 修改成 false ,Spring 默认使用参数最多的构造方法。原创 2022-12-09 18:28:56 · 1059 阅读 · 0 评论 -
Spring 中 @Bean 注解流程分析
2、beanName 确定好,在 Spring 实例化完成之后,容器中就可以根据 beanName 去找到对应的实例 bean,在这里可以根据 beanName = blue 找到 Blue 的实例 bean,根据 beanName = apple2 找到 Apple 的实例化 bean,但是你想根据 beanName = apple3 去找到 Apple 的实例,绝对不可能的,因为容器中就没有 beanName = apple3 的实例 bean。那么这段逻辑就显得格外重要了,现在进入内部逻辑。原创 2022-12-09 14:39:25 · 1388 阅读 · 1 评论 -
Spring 中发布了哪些事件?
Spring 发布的 5 种事件原创 2022-12-08 14:19:44 · 88 阅读 · 0 评论 -
Spring 中 ClassPathBeanDefinitionScanner 包扫描器的应用
先定义两个实体类,不用 @Component 修饰,但是最终需要被 Spring 管理,代码如下:然后定义注解 @BeansScanner 模拟 @ComponentScan 注解功能,代码如下:这里通过 @Import 注解将 BeansScannerRegistrar 类导入进来,BeansScannerRegistrar 类如下所示:最后编写测试类:测试结果:可以发现这里还是借助了 ClassPathBeanDefinitionScanner 包扫描器,只是添加的过滤条件我们重写了,我们这里原创 2022-12-07 23:23:06 · 418 阅读 · 0 评论 -
Spring 中 BeanFactoryPostProcessor 接口的作用
BeanFactoryPostProcessor 和该子类 BeanDefinitionRegistryPostProcessor 作用于 BeanDefinition 解析之后,Bean 实例化之前,所以我们可以在 BeanDefinition 定义好了之后做一些修改,从而影响 Bean 的实例化。源码如下BeanFactoryPostProcessor 类定义的方法中我们可以获取到 BeanFactory,有了这个工厂自然而然就可以干很多事情啦,比如去修改它的默认配置:比如我们去修改 BeanFact原创 2022-12-07 19:42:48 · 1533 阅读 · 0 评论 -
在 Spring 中 BeanDefinition 的几个重要的属性
MultablePropertyValues:用于封装原创 2022-12-06 18:16:34 · 311 阅读 · 0 评论 -
Spring 配置 @Scope(value = “prototype“,proxyMode = ScopedProxyMode.TARGET_CLASS) 执行过程分析
总结一下 createScopedProxy() 方法把原始的 BeanDefinition 的 **autowireCandidate 属性修改成了 false**,因为改了这个值,所以在 @Autowired 属性注入的时候,就不会考虑到这个原生的 BeanDefinition 定义了这里自己给造了一份新的这个 bean 的 BeanDefinition,可以理解为这个 bean 的代理 BeanDefinition,此时容器中已经存在两份 bean 的 BeanDefinition,只是原生的 .原创 2022-08-26 12:01:34 · 3067 阅读 · 2 评论 -
Spring 代理对象提前生成 (还未调用构造方法实例化 bean)
然后调用 getBean() 方法,直接实例化 ScopeProxyBean,至此我们提前在创建 bean 实例之前完成了 bean 创建。通过这种方式创建的 bean,在真正去调用的时候才会触发去调用 getBean() 流程创建真实的实例,并且 BeanFactory 是深拷贝出来的,会把 @Aspect 切面踢除了的,就算你配置了 @Aspect 功能也无效。还要注意一点就通过这种方式提前创建的 bean 默认都是 prototype 多例的,Spring 内部将其修改成 protot....原创 2022-08-26 00:00:09 · 777 阅读 · 1 评论 -
Spring 中通过自定义 Scope 理解 Scope 的作用
为什么还要自定义 Scope,其实就是不想让 Spring 来管理创建好的 bean,而是自己控制,比如我们可以把 bean 保存到自己定义的 Map 中。1、实现 Scope 接口System . out . println("MyMapScope 执行自定义 Scope get() 方法逻辑....");if(!System . out . println("MyMapScope 执行自定义 Scope remove() 方法逻辑....");} }原创 2022-08-25 12:00:45 · 704 阅读 · 0 评论 -
Spring 事务传播机制源码浅析——PROPAGATION_PROPAGATION_NESTED 事务嵌套
举个例子:下面有三条执行语句,先后对 age 字段做了相应的修改,但是有时候我希望保留第一次的修改值,第二、三次修改给我回滚,这个时候就需要使用到保存点 savepoint 了。创建 savepoint 保存点,用来标志回滚到什么位置,回滚操作,只需要 rollback b,这样就只保留了第一次修改,其他两次修改都不会成功,这就是 savepoint 的作用进入源码如下:获取到 Connection 连接对象,调用 JDBC API 创建保存点。原创 2022-08-24 19:02:38 · 935 阅读 · 1 评论 -
Spring 事务传播机制源码浅析——PROPAGATION_REQUIRES_NEW
两个方法都使用 PROPAGATION_REQUIRES_NEW 传播机制进行演示,并分析源码:示例如下:还是要进入 TransactionInterceptor 类,这各类是入口,这里截取出核心源码如下:进入 createTransactionIfNecessary() 方法,可以分成六个核心步骤,源码如下:源码如下:可以发现第一步骤有两行非常重要的代码,第一行代码主要是从 ThreadLocal 类型的变量中去获取值,源码如下:第一次也就是现在过来的 add() 方法,现在从这个 ThreadLoc原创 2022-08-24 15:57:39 · 2577 阅读 · 0 评论 -
Spring 事务传播机制源码浅析——PROPAGATION_REQUIRED 默认传播机制
事务传播是 Spring 中提出来的概念,很多人使用事务都是在方法上标注注解,然而,如果每个方法上面都标注着注解,那么你应该执行哪个注解的功能呢?所以这里就需要一个机制或者规范来解决这个问题,能够保证所有方法上面的事务能够正常执行(或者说是让事务生效),这个就是事务的传播机制。你觉得有发生事务传播嘛?原创 2022-08-24 00:46:02 · 6361 阅读 · 0 评论 -
Spring 事务处理流程源码浅析
(AOP 切面功能抽象类,AOP 中王者级别的类),发现终于找到了后置处理器中定义的规范 API 方法,源码如下:首先看到 getEarlyBeanReference() 方法,源码如下:发现第一行是把当前过来的原生包成品 bean 保存到了一个缓存中,为什么要保存呢?原创 2022-08-23 18:29:37 · 233 阅读 · 0 评论 -
Spring 是怎么解决循环依赖问题的呢?
有两个业务代码分别是 A、B,并且还存在在相互引用,这样就形成了经典的循环依赖,而且这种循环依赖 Spring 不会出现问题,那么 Spring 是怎么解决的呢?让我们追溯下源码(目前分析的是单实例场景)原创 2022-08-23 13:44:38 · 178 阅读 · 0 评论 -
Spring 注解配置实例化 bean 流程源码分析
Spring 注解配置实例化 bean 流程源码分析原创 2022-08-23 11:12:14 · 400 阅读 · 0 评论 -
Spring 中自定义注解 @DBMasterAnno 和 @Async 注解在循环依赖场景下使用出现问题
下面开始追溯一下原因到底是哪里导致出错的呢?使用示例,先制造出一个单例的循环依赖环境,直接使用 @Autowired 注入自己即可,按理这个循环依赖是没问题的,Spring 是支持循环依赖问题的,但是由于这里加了两个切面 @DBMasterAnno 和 @Async 进来,这里就直接报错了。原创 2022-08-22 21:27:10 · 273 阅读 · 0 评论 -
Spring 的 @Aspect 注解使用之—AopUtils.getMostSpecificMethod 工具类的使用
Spring 的 @Aspect 注解使用之—AopUtils.getMostSpecificMethod 工具类的使用原创 2022-08-22 14:38:07 · 615 阅读 · 0 评论 -
自己定义 Advisor 实现自定义注解修饰的方法增强
自己定义 Advisor 实现自定义注解修饰的方法增强原创 2022-08-22 14:31:25 · 501 阅读 · 0 评论 -
Spring 整合嵌入式 Tomcat 容器
Tomcat SPI 机制中暴露了一个接口 ServletContainerInitializer,在 Tomcat 启动生命周期过程中会去加载加载该接口的所有实现类,并且还会解析 @HandlersTypes 注解,解析到的结果存放到一个 Set原创 2022-08-16 17:13:46 · 502 阅读 · 0 评论