Spring源码分析之依赖注入(一)2

简介: Spring源码分析之依赖注入(一)

static不进行注入

如图所示, 需要注意的是, 如果当前的属性是 static的, 那么直接return掉, 不进行属性的注入

网络异常,图片无法展示
|

为什么一个字段是static的, 不将其当做注入点

如果我们的 Bean对象不是单例的, 而是多例或者其他类型的, 那么获取一次Bean都会将其重新创建一遍, 这不符合我们对 static静态资源的预期

如果获取到相关的注解

如果获取到相关的注解了, 那么继续往下走,会先执行一个方法, 然后把当前这个字段设置为一个注入点

网络异常,图片无法展示
|

在我们的 @Autowired注解中, 可以进行配置 required, 这个值默认是true的, 他的含义是: 如果在依赖注入的时候, 没有找到这个 Bean是会报错的, 如果设置为 false之后, 在依赖注入期间没有找到这个 Bean就不会报错了

网络异常,图片无法展示
|

下面的代码, 就是对 @Autowired注解属性配置的单独处理

boolean required = determineRequiredStatus(ann);
复制代码

遍历当前 Bean所有的方法

接着往下走, 就是遍历当前 Bean所有的方法了

网络异常,图片无法展示
|

还是一样的, 简单流程如下:

  • 过滤掉桥接方法
  • 去找方法上面有没有加注解
  • 是不是静态方法
  • 某个方法的参数等于0, 则打印日志
  • 解析 required值
  • 封装成AutowiredMethodElement类
  • 当成注入点加入 currElements集合中

桥接方法, 是专门用来处理一些特殊的情况的

如下图所示, 如果是用以下这种方式编写代码, 那么在字节码文件中就会发现两个 setOrderService方法, 这个时候就需要桥接方法帮助我们找到原方法

网络异常,图片无法展示
|

遍历父类, 去循环上面的操作

注意, 我们这个方法是一个 do while循环, 先执行当前 Bean再去遍历 父Bean

网络异常,图片无法展示
|

return

将当前类和父类的注入点都找出来, 封装成一个对象, 把这个对象返回并且缓存, 存到外面的方法

网络异常,图片无法展示
|
返回到上一个方法, 可以看到, 已经将返回值缓存到了 injectionMetadataCache中

网络异常,图片无法展示
|

注入点进行注入

根据我们之前进行 Bean生命周期的分析, 接下来会执行 postProcessProperties方法

网络异常,图片无法展示
|

取出注入点

在这个方法的第一行代码, 就是取出注入点, 具体代码如下所示, 之前已经全部注入完了, 这里就不详细讲了

网络异常,图片无法展示
|

给注入点进行注入

如下图所示, 接下来获取到所有的注入点, 然后对其进行遍历

网络异常,图片无法展示
|
遍历的 InjectedElement类, 是一个父类, 他的具体实现, 通过下图可以看到, 分别是方法和字段

网络异常,图片无法展示
|

注意, 这里查看具体处理方法的时候, 不要直接点进 element.inject(target, beanName, pvs);方法, 因为我们是子类继承父类去实现的, 所以要去找子类的实现方法

网络异常,图片无法展示
|

字段的注入实现

流程简单说明:

  • 找出注入点封装的字段
  • 获取字段的对象
  • 获取缓存, 我们没有, 直接进入else
  • 调用方法 resolveFieldValue
  • 根据字段的类型, 名字去找具体的值(下一篇文章详细讲解)
  • 找到之后通过反射为字段复制

字段的注入实现代码如下图所示:

网络异常,图片无法展示
|

方法的注入实现

流程简单说明:

  • 如果pvs中已经有当前注入点的值了,则跳过注入
  • 找出方法对象
  • 获取缓存, 我们没有, 直接进入else
  • 根据 @Autowired注解的参数返回对象数组
  • 执行 method.invoke(bean, arguments);

方法的注入实现代码如下图所示:

网络异常,图片无法展示
|

五、属性注入方法的执行

回到我们本标题的最开始, 看这个for遍历, 如下图所示

网络异常,图片无法展示
|
在这个遍历过程中, 我们可以看到它执行了一个我们所熟悉的方法, 属性的注入

网络异常,图片无法展示
|

六、属性赋值

可以看到, 在上面的代码分析过程中, 并没有实际的做属性赋值操作, 那么具体的属性赋值实际上是在该方法的最后一行

网络异常,图片无法展示
|

这个方法实际上就是将 BeanDefinition中的属性和值设置到 Bean对象中, 感兴趣的可以去看一下


目录
相关文章
|
3月前
|
XML Java 测试技术
Spring Boot中的依赖注入和控制反转
Spring Boot中的依赖注入和控制反转
|
5月前
|
XML Java 程序员
Spring6框架中依赖注入的多种方式(推荐构造器注入)
依赖注入(DI)是一种过程,对象通过构造函数参数、工厂方法的参数或在对象实例构建后设置的属性来定义它们的依赖关系(即与其一起工作的其他对象)。
78 3
|
5月前
|
Java 测试技术 开发者
Spring IoC容器通过依赖注入机制实现控制反转
【4月更文挑战第30天】Spring IoC容器通过依赖注入机制实现控制反转
50 0
|
2月前
|
Java Spring 容器
彻底改变你的编程人生!揭秘 Spring 框架依赖注入的神奇魔力,让你的代码瞬间焕然一新!
【8月更文挑战第31天】本文介绍 Spring 框架中的依赖注入(DI),一种降低代码耦合度的设计模式。通过 Spring 的 DI 容器,开发者可专注业务逻辑而非依赖管理。文中详细解释了 DI 的基本概念及其实现方式,如构造器注入、字段注入与 setter 方法注入,并提供示例说明如何在实际项目中应用这些技术。通过 Spring 的 @Configuration 和 @Bean 注解,可轻松定义与管理应用中的组件及其依赖关系,实现更简洁、易维护的代码结构。
35 0
|
2月前
|
设计模式 自然语言处理 Java
简单了解下Spring中的各种Aware接口实现依赖注入
在Spring框架中,Aware接口是一组用于提供特定资源或环境信息的回调接口。这些接口被设计用来允许Bean获取对Spring容器或其他相关资源的引用,并在需要时进行适当的处理。
24 2
|
2月前
|
自然语言处理 Java 开发者
简单了解下Spring中的各种Aware接口实现依赖注入
【8月更文挑战第21天】在Spring框架中,Aware接口系列是一种特殊的机制,它允许Bean在初始化过程中获取到Spring容器或容器中的特定资源,从而实现了更加灵活和强大的依赖注入方式。本文将围绕Spring中的各种Aware接口,详细探讨它们如何帮助开发者在工作和学习中更好地实现依赖注入。
56 0
|
3月前
|
缓存 Java Spring
Spring循环依赖问题之Spring不支持构造器内的强依赖注入如何解决
Spring循环依赖问题之Spring不支持构造器内的强依赖注入如何解决
|
4月前
|
存储 安全 Java
Spring Security 6.x OAuth2登录认证源码分析
上一篇介绍了Spring Security框架中身份认证的架构设计,本篇就OAuth2客户端登录认证的实现源码做一些分析。
172 2
Spring Security 6.x OAuth2登录认证源码分析
|
4月前
|
设计模式 Java 测试技术
Spring Boot中的依赖注入详解
Spring Boot中的依赖注入详解
|
4月前
|
缓存 Java 测试技术
Spring 框架,不只是依赖注入和面向切面那么简单!
【6月更文挑战第25天】Spring框架超越DI和AOP,涵盖事务管理、数据访问抽象如`JdbcTemplate`、消息驱动支持如`@JmsListener`、缓存管理和测试工具。示例代码展示了其简化复杂性的能力,如自动事务处理、数据库操作及消息队列监听。Spring是构建高效企业级应用的全面解决方案。
32 4
下一篇
无影云桌面