Spring 5.2.5 官方文档解读,仅记录一些不知道的点(持续更新)

解读一下 Spring 的官网文档,查漏补缺。认识一些骚操作,平时都没有注意到或使用到的点。

文章目录

      • BeanPostProcessor
      • @Autowired
        • @Autowired 多实例
        • @Autowired required = false

BeanPostProcessor

通过 ConfigurableBeanFactoryaddBeanPostProcessor 可以手动将 BeanPostProcessor 注册到容器中。

但需要注意的是,这种注册方式不遵守 order 接口的顺序,仅仅和注册顺序有关。先注册的先执行。

其次,手动注册的顺序一定早于自动注册的,无关于order。

BeanPostProcessor 和其引用的 Bean 是无法通过 AOP 增强的。因为AOP 增强本身就是通过 BeanPostProcessor 处理的,是在常规 Bean 的生命周期-初始化之后进行的。
而 BeanPostProcessor 及其引用 Bean,由于 BeanPostProcessor 是容器上下文启动的一个环节,并不遵守 Bean 生命周期过程。因此也无法被应用到 BeanPostProcessor。

官方文档原文: Classes that implement the BeanPostProcessor interface are special and are treated differently by the container. All BeanPostProcessor instances and beans that they directly reference are instantiated on startup, as part of the special startup phase of the ApplicationContext. Next, all BeanPostProcessor instances are registered in a sorted fashion and applied to all further beans in the container. Because AOP auto-proxying is implemented as a BeanPostProcessor itself, neither BeanPostProcessor instances nor the beans they directly reference are eligible for auto-proxying and, thus, do not have aspects woven into them.

@Autowired

@Autowired 用于 Bean 的属性注入,一般放在构造器上,或者属性上,或Setter 方法上,或者自定义初始化方法上。

@Service
public class UserService {
    // 属性
    @Autowired
    private UserDao userDao;
    
    // 构造器
    @Autowired
    public UserService(UserDao userDao) {
    }
    
    // setter
    @Autowired
    public void setUserDao(UserDao userDao) {
    }
    
    // 自定义初始化方法
    @Autowired
    public void init(UserDao userDao) {
    }
}

从 Spring 4.3 版本开始,如果 Bean 只有一个构造器,则可以忽略 @Autowired 注解,容器可以根据构造器自动注入。

但是如果存在多个构造器,则必须指定某个构造器 标注 @Autowired,来确保容器正确选择构造器,来注入。

上面所列举的 @Autowired 的使用方式,可以混合使用。

@Autowired 多实例

@Autowired 允许注入同一个接口实现的多个 Bean,到 数组、Set、甚至Map类型(key 为 BeanName)的属性上。
但是,如果注入到上述类型中,容器中必须存在至少一个满足类型的 Bean,否则就会报错。


public class MovieRecommender {

    @Autowired
    private MovieCatalog[] movieCatalogs;

    // ...
}

public class MovieRecommender {

    private Set<MovieCatalog> movieCatalogs;

    @Autowired
    public void setMovieCatalogs(Set<MovieCatalog> movieCatalogs) {
        this.movieCatalogs = movieCatalogs;
    }

    // ...
}

public class MovieRecommender {

    private Map<String, MovieCatalog> movieCatalogs;

    @Autowired
    public void setMovieCatalogs(Map<String, MovieCatalog> movieCatalogs) {
        this.movieCatalogs = movieCatalogs;
    }

    // ...
}

默认注入到数组、集合中的顺序,是各个 Bean 在容器中的初始化顺序。
可以通过 @Order 或 Order 接口,来自定义注入的顺序。(注意:不会影响Bean的初始化顺序)

@Autowired required = false

允许 @Autowired 的 required 设置为 false,来标识当容器中无法匹配到指定类型的 Bean,可以不用注入。

如果多个构造函数声明了注释,则它们都必须声明required = false才能被视为自动装配的候选对象(类似于XML中的autowire = constructor)。
Bean 初始化时,将选择通过匹配容器中的bean可以满足的依赖项数量最多的构造函数。如果都无法满足,将默认使用主或默认构造函数。
如果 Bean 只有一个构造函数,无论是否使用注释,都将被使用。

@Autowired 支持 Java 8 的 Optional 或 JSR-305 的 @Nullable(Spring 5 开始支持), 来实现与 required = false 相同的语义。

public class SimpleMovieLister {

    @Autowired
    public void setMovieFinder(Optional<MovieFinder> movieFinder) {
        ...
    }
}

public class SimpleMovieLister {

    @Autowired
    public void setMovieFinder(@Nullable MovieFinder movieFinder) {
        ...
    }
}

官方文档Spring Framework 5

你可能感兴趣的:(spring)