前沿:
在说spring之前,先提一下spring的基本原理,依赖注入,控制反转。我们在配置spring的时候有两种bean可以配置,
一种是普通bean:配置的class就是生成的bean的真正对象。
一种是工厂Bean,即FactoryBean:配置class不是生成bean的真正对象。
他们都被spring容器管理,工厂Bean其返回的对象不是指定类的一个实例,是该FactoryBean的getObject方法所返回的对象。
普通人可能只知道一种,在Spring内部,有很多地方用到FactoryBean实现功能,
应用:它们在很多应用如(Spring的AOP、ORM、事务管理)及与其它第三框架(ehCache)集成时都有体现,
实现:
1. FactoryBean接口
1 package org.springframework.beans.factory; 2 3 public interface FactoryBean<T> { 4 5 T getObject() throws Exception; 6 7 Class<?> getObjectType(); 8 9 boolean isSingleton(); 10 11 }
其中是java泛型机制实现,即T表示要生成的对象。也可以不使用,推荐使用。
getObject()方法返回欲生成对象。getObjectType()欲返回对象类型,isSingleton()获得对象的机制(singleton|prototype|request|session).
2. 例子:mybatis和spring集成实例
1 package com.debug.factory; 2 3 import java.io.InputStream; 4 5 import org.apache.ibatis.io.Resources; 6 import org.apache.ibatis.session.SqlSessionFactory; 7 import org.apache.ibatis.session.SqlSessionFactoryBuilder; 8 import org.springframework.beans.factory.FactoryBean; 9 10 public class SqlSessionFactoryBean implements FactoryBean<SqlSessionFactory> { 11 SqlSessionFactory sessionFactory; 12 13 @Override 14 public SqlSessionFactory getObject() throws Exception { 15 System.out.println("getObject"); 16 String resource = "mybatis-config1.xml"; 17 InputStream in = Resources.getResourceAsStream(resource); 18 sessionFactory = new SqlSessionFactoryBuilder().build(in); 19 return sessionFactory; 20 } 21 22 @Override 23 public Class<?> getObjectType() { 24 // TODO Auto-generated method stub 25 System.out.println("getObjectType"); 26 return SqlSessionFactory.class; 27 } 28 29 @Override 30 public boolean isSingleton() { 31 System.out.println("isSingleton"); 32 return true; 33 } 34 }
application.xml配置
1 <?xml version="1.0" encoding="UTF-8"?> 2 <beans xmlns="http://www.springframework.org/schema/beans" 3 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 4 xmlns:aop="http://www.springframework.org/schema/aop" 5 xmlns:context="http://www.springframework.org/schema/context" 6 xmlns:tx="http://www.springframework.org/schema/tx" 7 xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd 8 http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-3.2.xsd 9 http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.2.xsd 10 http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-3.2.xsd"> 11 12 <bean id="mysqlsessionfactory" class="com.debug.factory.SqlSessionFactoryBean" scope="prototype"> 13 14 </bean> 15 </beans>
调用测试代码
1 ApplicationContext app = new ClassPathXmlApplicationContext("application.xml"); 2 { 3 SqlSessionFactory sqlSessionFactory = (SqlSessionFactory) app.getBean("mysqlsessionfactory"); 4 System.out.println(sqlSessionFactory); 5 } 6 { 7 SqlSessionFactory sqlSessionFactory = (SqlSessionFactory) app.getBean("mysqlsessionfactory"); 8 System.out.println(sqlSessionFactory); 9 }
生成:
1 isSingleton 2 getObjectType 3 isSingleton 4 getObject 5 org.apache.ibatis.session.defaults.DefaultSqlSessionFactory@8458f04 6 org.apache.ibatis.session.defaults.DefaultSqlSessionFactory@8458f04
说明,容器通过getBean方法返回的不是SqlSessionFactory本身,而是FactoryBean实现类中getObject()方法返回的对象。
上面代码是自己集成的mybatis如果用官方的包可以使用spring mybatis项目提供的代码mybatis-spring-1.2.0.tar.gz中的org.mybatis.spring.SqlSessionFactoryBean。
spring配置如下:
1 <bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean"> 2 <property name="dataSource" ref="dataSource" /> 3 <property name="configLocation" value="classpath:mybatis-config.xml" /> 4 </bean>
3. FactoryBean的扩展应用之Spring集成 ehcache
1 <bean id="cacheManager" class="org.springframework.cache.ehcache.EhCacheManagerFactoryBean"> 2 <property name="configLocation"> 3 <value>classpath:ehcache.xml</value> 4 </property> 5 </bean> 6 <bean id="levelOneCache" class="org.springframework.cache.ehcache.EhCacheFactoryBean"> 7 <property name="cacheManager"> 8 <ref local="cacheManager" /> 9 </property> 10 <property name="cacheName"> 11 <value>levelOneCache</value> 12 </property> 13 </bean>
调用代码
1 public class MainTest { 2 public static void main(String[] args) { 3 Resource res = new ClassPathResource("bean.xml"); 4 BeanFactory factory = new XmlBeanFactory(res); 5 //取到CacheManager类的实例 6 CacheManager cacheManager = (CacheManager) factory .getBean("cacheManager"); 7 //取到Cache类的实例 8 Cache levelOneCache = cacheManager.getCache("levelOneCache"); 9 } 10 }
更过详细设置参考其他详细资料!