您的位置:首页 > 编程语言 > Java开发

浅析Spring IoC源码(四)分析BeanPostProcessor(1)

2016-11-28 09:57 906 查看


BeanPostProcessor是什么呢,有什么作用呢,打开源代码先看看



这个接口的注释中原作者说明了该接口的作用:

“工厂钩子允许用户自定义修改创建的bean实例,应用上下文可以在ben的定义中自动检测beanPostProecessor,并且将其应用于随后创建的任意bean中,并且可以通过factory给其他的类进行注册然后使用”

说白了,就是我们可以自定义的去修改spring给我们创建的类,给了我们一个二次修改bean的机会,这种设计思路与spring的“开闭原则”相符合,没有过度分装,举例来说,我们根据beanDefinition去查找一个Teacher,找到之后spring给我们实例化这个Teacher,但是我们用这个teacher的时候,发现这个teacher会抽烟,我们可以修改这个老师会抽烟的属性,这样就得到了一个完美的老师,这个完美的老师授课结束后,我们再告诉他你可以接着抽烟了,所以spring给我们想的还是很周到的~

再看这个接口定义的2个方法



BeanPostProcessor这个接口就2个方法,根据这2个方法的名称,我们就大概知道这2个方法的做什么的了

postProcessBeforeInitialization在“初始化之前处理”

postProcessAfterInitialization在“初始化之后处理”

废话不多说,我们就实现一个上面讲述的例子,大家更加深入的理解一下BeanPostProcessor这个作用

Teacher.Java

[java] view
plain copy

package org.study.spring.beanpostprocessor.demo;

public class Teacher {

/**

* 老师的姓名

*/

private String name;

/**

* 年龄

*/

private int age;

/**

* 是否抽烟

*/

private boolean smoking;

/**

* 老师教授的课程

*/

private String language;

/**

* 临时变量,默认抽烟

*/

private boolean tempSmoking = true;

public Teacher() {

}

public boolean isTempSmoking() {

return tempSmoking;

}

public void setTempSmoking(boolean tempSmoking) {

this.tempSmoking = tempSmoking;

}

public String getName() {

return name;

}

public void setName(String name) {

this.name = name;

}

public int getAge() {

return age;

}

public void setAge(int age) {

this.age = age;

}

public boolean isSmoking() {

return smoking;

}

public void setSmoking(boolean smoking) {

this.smoking = smoking;

}

public String getLanguage() {

return language;

}

public void setLanguage(String language) {

this.language = language;

}

public void teach(){

System.out.println("I am :"+name+" and I will teach you :"+language + " and I "+(tempSmoking?"will":"will not")+" smoking");

}

}

ChangeTeacherSmokingBeanPostProcessor.java

[java] view
plain copy

package org.study.spring.beanpostprocessor.demo;

import org.springframework.beans.BeansException;

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

public class ChangeTeacherSmokingBeanPostProcessor implements BeanPostProcessor{

/**

* 初始化之前处理

*/

public Object postProcessBeforeInitialization(Object bean, String beanName)

throws BeansException {

/**

* 只处理该bean的类型是Teacher的

*/

if(bean instanceof Teacher){

Teacher teacher = (Teacher)bean;

/**

* 实例化之前,要吧所有抽烟的都改成不抽烟的

*/

if(teacher.isSmoking()){

((Teacher)bean).setTempSmoking(false);

}

}

return bean;

}

public Object postProcessAfterInitialization(Object bean, String beanName)

throws BeansException {

return bean;

}

}

bean-post-processor-teacher.xml

[html] view
plain copy

<?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:context="http://www.springframework.org/schema/context"

xmlns:mybatis-spring="http://mybatis.org/schema/mybatis-spring"

xmlns:tx="http://www.springframework.org/schema/tx" xmlns:jee="http://www.springframework.org/schema/jee"

xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.2.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.2.xsd
http://www.springframework.org/schema/jee http://www.springframework.org/schema/jee/spring-jee-3.2.xsd
http://mybatis.org/schema/mybatis-spring http://mybatis.org/schema/mybatis-spring-1.2.xsd
http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-3.2.xsd">

<bean id="teacher" class="org.study.spring.beanpostprocessor.demo.Teacher">

<property name="name" value="孔浩"/>

<property name="age" value="32"/>

<property name="smoking" value="true"/>

<property name="language" value="java"/>

</bean>

<bean id="changeTeacher" class="org.study.spring.beanpostprocessor.demo.ChangeTeacherSmokingBeanPostProcessor"/>

</beans>

ChangeTeacherSmokingBeanPostProcessorTest.java

[java] view
plain copy

package org.study.spring.beanpostprocessor.demo;

import org.junit.Test;

import org.springframework.context.ApplicationContext;

import org.springframework.context.support.ClassPathXmlApplicationContext;

public class ChangeTeacherSmokingBeanPostProcessorTest{

@Test

public void test2() throws Exception{

ApplicationContext applicationContext = new ClassPathXmlApplicationContext("bean-post-processor-teacher.xml");

Teacher teacher = applicationContext.getBean("teacher",Teacher.class);

teacher.teach();

}

}

运行结果



上面的例子只是说明,spring在初始化之前,给了我们开发者二次修改的机会,beanPostProcessor这个类是“spring”开闭原则的典型实现,下一节详细讲述它在项目中的具体运用~
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐