跳转至

Spring Bean 后置处理器

1. 介绍

  Bean后置处理器允许在调用初始化方法前后对 Bean 进行额外的处理。

  BeanPostProcessor 接口定义回调方法,你可以实现该方法来提供自己的实例化逻辑,依赖解析逻辑等。你也可以在 Spring 容器通过插入一个或多个 BeanPostProcessor 的实现来完成实例化,配置和初始化一个bean之后实现一些自定义逻辑回调方法。

  你可以配置多个 BeanPostProcessor 接口,通过设置 BeanPostProcessor 实现的 Ordered 接口提供的 order 属性来控制这些 BeanPostProcessor 接口的执行顺序。

  BeanPostProcessor 可以对 bean(或对象)实例进行操作,这意味着 Spring IoC 容器实例化一个 bean 实例,然后 BeanPostProcessor 接口进行它们的工作。

  ApplicationContext 会自动检测由 BeanPostProcessor 接口的实现定义的 bean,注册这些 bean 为后置处理器,然后通过在容器中创建 bean,在适当的时候调用它。

2. 操作步骤

  下面的例子显示如何在 ApplicationContext 的上下文中编写,注册和使用 BeanPostProcessor。

  我们在适当的位置使用 Eclipse IDE,然后按照下面的步骤来创建一个 Spring 应用程序

这是实现 BeanPostProcessor 的非常简单的例子,它在任何 bean 的初始化的之前和之后输入该 bean 的名称。你可以在初始化 bean 的之前和之后实现更复杂的逻辑,因为你有两个访问内置 bean 对象的后置处理程序的方法。

InitPerson.class

package com.cmz.bean;

import org.springframework.beans.BeansException;
import org.springframework.beans.factory.config.BeanPostProcessor;

/**
 * @author summer
 * @create 2020-02-28 22:24
 * bean 表示创建的具体对象
 * beanName 表示bean的属性
 */
public class InitPerson implements BeanPostProcessor {

    // 在每一个对象的初始化前面执行
    public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
        System.out.println("BeforeInitialization : " + beanName);
        return null;
    }
    // 在每一个对象的初始化后面执行
    public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
        System.out.println("AfterInitialization : " + beanName);
        return null;
    }
}

ioc2.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:p="http://www.springframework.org/schema/p"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">

    <!--<bean id="person" class="com.cmz.bean.Person" scope="prototype">-->
    <!--根据属性值设置的时候,name的名字取决于set方法后面的参数首字母小写的名称-->
    <!--
    name: 表示参数列表的名称
    value: 表示实际的具体指
    type: 表示值的类型
    index: 表示值的下标,从0开始
    -->

    <bean id="person" class="com.cmz.bean.Person" init-method="init" destroy-method="destroy">
        <property name="id" value="1"></property>
        <property name="name" value="张三"></property>
        <property name="age" value="20"></property>
        <property name="gender" value="男"></property>
        <property name="date" value="2020/02/28"></property>
    </bean>
    <bean class="com.cmz.bean.InitPerson"></bean>
</beans>

MyTest.class

import com.cmz.bean.Person;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

/**
 * @author summer
 * @create 2020-02-22 21:06
 */
public class MyTest {
    public static void main(String[] args) {
        ApplicationContext context = new ClassPathXmlApplicationContext("ioc2.xml");
        // 根据bean标签id来获取对象
        Person person = context.getBean("person", Person.class);
        System.out.println(person);
        ((ClassPathXmlApplicationContext) context).close();
    }
}

输出

BeforeInitialization : person
Bean is going through init.
AfterInitialization : person
Person{id=1, name='张三', age=20, gender='男', date=Fri Feb 28 00:00:00 CST 2020}
Bean will destroy now.