- 浏览: 865230 次
- 性别:
- 来自: 北京
文章分类
- 全部博客 (687)
- java (127)
- servlet (38)
- struts (16)
- spring (22)
- hibernate (40)
- javascript (58)
- jquery (18)
- tomcat (51)
- 设计模式 (6)
- EJB (13)
- jsp (3)
- oracle (29)
- RUP (2)
- ajax (3)
- java内存管理 (4)
- java线程 (12)
- socket (13)
- path (5)
- XML (10)
- swing (2)
- UML (1)
- JBPM (2)
- 开发笔记 (45)
- Note参考 (15)
- JAXB (4)
- Quartz (2)
- 乱码 (2)
- CSS (2)
- Exception (4)
- Tools (7)
- sqlserver (3)
- DWR (7)
- Struts2 (47)
- WebService (2)
- 问题解决收藏 (7)
- JBOSS (7)
- cache (10)
- easyUI (19)
- jQuery Plugin (11)
- FreeMarker (6)
- Eclipse (2)
- Compass (2)
- JPA (1)
- WebLogic (1)
- powerdesigner (1)
- mybatis (1)
最新评论
-
bugyun:
受教了,谢谢
java 正则表达式 过滤html标签 -
xiongxingxing_123:
学习了,感谢了
java 正则表达式 过滤html标签 -
wanmeinange:
那如果无状态的。对同一个任务并发控制怎么做?比如继承Quart ...
quartz中参数misfireThreshold的详解 -
fanjieshanghai:
...
XPath 元素及属性查找 -
tianhandigeng:
还是没明白
quartz中参数misfireThreshold的详解
在Spring BeanFactory容器中管理两种bean
- 博客分类:
- spring
在Spring BeanFactory容器中管理两种bean
1.标准Java Bean
2,另一种是工厂Bean, 即实现了FactoryBean接口的bean 它不是一个简单的Bean 而是一个生产或修饰对象生成的工厂Bean
在向Spring容器获得bean时 对于标准的java Bean 返回的是类自身的实例
而FactoryBean 其返回的对象不一定是自身类的一个实例,返回的是该工厂Bean的getObject方法所返回的对象
一个简单的例子
- public class SayHelloFactoryBeanImpl implements FactoryBean {
- /**
- * 返回该工厂生成的bean
- */
- public Object getObject() throws Exception {
- return new ChinaSayHelloServiceImpl();
- }
- /**
- * getObject返回对象对应的Class
- */
- public Class getObjectType() {
- return ChinaSayHelloServiceImpl.class;
- }
- /**
- * getObject返回的对象 是否是一个单例
- */
- public boolean isSingleton() {
- return false;
- }
- }
- 配置文件
- <bean id="sayHelloFactoryBean" class="com.xx.service.impl.SayHelloFactoryBeanImpl" />
- ApplicationContext context = new ClassPathXmlApplicationContext(new String[]{"classpath:applicationContext-server.xml"}, true);
- //bean的 getObject方法 返回的对象
- Object object = context.getBean("sayHelloFactoryBean");
- System.out.println(object);
控制台输出
com.xx.service.impl.ChinaSayHelloServiceImpl@1f66cff
容器返回的是 bean getObject方法返回对象 而不是SayHelloFactoryBeanImpl自身的实例 当然可以用“&”符号转义 获得FactoryBean的自身实例
- ApplicationContext context = new ClassPathXmlApplicationContext(new String[]{"classpath:applicationContext-server.xml"}, true);
- //可以用转义符"&"来获得FactoryBean本身实例
- System.out.println(context.getBean("&sayHelloFactoryBean"));
控制台输出
com.xx.service.impl.SayHelloFactoryBeanImpl@75e4fc
下面看看FactoryBean是怎么实现的
Spring FactoryBean接口定义
- public interface FactoryBean {
- Object getObject() throws Exception;
- Class getObjectType();
- boolean isSingleton();
- }
bean的实例化 是在AbstractBeanFactory getBean方法发生的
- public Object getBean(String name, Class requiredType, Object[] args) throws BeansException {
- return doGetBean(name, requiredType, args, false);
- }
- protected Object doGetBean(final String name, final Class requiredType, final Object[] args, boolean typeCheckOnly) throws BeansException {
- // bean name处理 如果是以"&"开头 截取掉
- final String beanName = transformedBeanName(name);
- Object bean = null;
- //单例的bean 只实例化一次 第一次实例化后会放到一个Map中 即singletonObjects map集合中 下次使用的时候直接拿
- Object sharedInstance = getSingleton(beanName);
- if (sharedInstance != null && args == null) {
- // FactoryBean 相关处理 在此方法发生
- //name 调用getBean时传入的参数
- //beanName 截取"&"后的name
- bean = getObjectForBeanInstance(sharedInstance, name, beanName, null);
- }
- else {
- ...略
- }
- return bean;
- }
- protected Object getObjectForBeanInstance(
- Object beanInstance, String name, String beanName, RootBeanDefinition mbd) {
- // 如果不是FactoryBean的相关调用 结束处理
- //isFactoryDereference 方法判断name 是不是以"&"开始 如果以"&"开始 返回true
- if (BeanFactoryUtils.isFactoryDereference(name) && !(beanInstance instanceof FactoryBean)) {
- throw new BeanIsNotAFactoryException(transformedBeanName(name), beanInstance.getClass());
- }
- if (!(beanInstance instanceof FactoryBean) || BeanFactoryUtils.isFactoryDereference(name)) {
- return beanInstance;
- }
- Object object = null;
- //bean的定义为null
- if (mbd == null) {
- //缓存集合factoryBeanObjectCache中包含 当前bean getObject方法返回的实例 不需要在调用 直接返回
- object = getCachedObjectForFactoryBean(beanName);
- }
- if (object == null) {
- FactoryBean factory = (FactoryBean) beanInstance;
- //containsBeanDefinition方法-> bean的定义map beanDefinitionMap集合中 是否包含该bean的定义
- if (mbd == null && containsBeanDefinition(beanName)) {
- mbd = getMergedLocalBeanDefinition(beanName);
- }
- boolean synthetic = (mbd != null && mbd.isSynthetic());
- // FactoryBean getObject触发 并缓存到factoryBeanObjectCache集合中
- object = getObjectFromFactoryBean(factory, beanName, !synthetic);
- }
- return object;
- }
- protected Object getObjectFromFactoryBean(FactoryBean factory, String beanName, boolean shouldPostProcess) {
- //当前的factoryBean是否单例 并且 缓存singletonObjects‘Map中包含FactoryBean的自身实例
- if (factory.isSingleton() && containsSingleton(beanName)) {
- synchronized (getSingletonMutex()) {
- // factoryBeanObjectCache 缓存的是 getObject返回的对象
- Object object = this.factoryBeanObjectCache.get(beanName);
- if (object == null) {
- //getObject方法调用
- object = doGetObjectFromFactoryBean(factory, beanName, shouldPostProcess);
- //缓存 getObject方法返回的实例对象
- this.factoryBeanObjectCache.put(beanName, (object != null ? object : NULL_OBJECT));
- }
- return (object != NULL_OBJECT ? object : null);
- }
- }
- else {
- //getObject方法调用
- return doGetObjectFromFactoryBean(factory, beanName, shouldPostProcess);
- }
- }
- private Object doGetObjectFromFactoryBean(
- final FactoryBean factory, final String beanName, final boolean shouldPostProcess)
- throws BeanCreationException {
- AccessControlContext acc = AccessController.getContext();
- return AccessController.doPrivileged(new PrivilegedAction() {
- public Object run() {
- Object object;
- try {
- // getObject方法调用
- object = factory.getObject();
- }
- catch (FactoryBeanNotInitializedException ex) {
- throw new BeanCurrentlyInCreationException(beanName, ex.toString());
- }
- catch (Throwable ex) {
- throw new BeanCreationException(beanName, "FactoryBean threw exception on object creation", ex);
- }
- if (object == null && isSingletonCurrentlyInCreation(beanName)) {
- throw new BeanCurrentlyInCreationException(
- beanName, "FactoryBean which is currently in creation returned null from getObject");
- }
- if (object != null && shouldPostProcess) {
- try {
- object = postProcessObjectFromFactoryBean(object, beanName);
- }
- catch (Throwable ex) {
- throw new BeanCreationException(beanName, "Post-processing of the FactoryBean's object failed", ex);
- }
- }
- return object;
- }
- }, acc);
- }
当一个受Spring容器管理的bean 如果实现了FactoryBean接口 在bean实例化(getBean)阶段 Spring会调用该bean的getObejct方法 返回的不一定是自身的实例
Spring 框架中有很多FactoryBean 例如RmiProxyFactoryBean, SqlMapClientFactoryBean. LocalSessionFactoryBean等都是通过FactoryBean getObject方法驱动起来的.对bean的生产 修饰做了很好的封装。
发表评论
-
spring 2.5 注释驱动的 IoC 功能
2012-06-15 23:35 895概述 注释配置相对于 XML 配置具有很多的优势: 它可 ... -
Spring-security 1
2011-05-15 20:20 1624有没有发现一个问题 ... -
容器背后的秘密
2011-04-28 00:26 871核心提示:4.4 容器背 ... -
spring 监听器 IntrospectorCleanupListener简介
2011-04-27 15:49 1248其中JavaBeans Introspector是一个类,位置 ... -
通过ApplicationContextAware获取bean
2011-04-25 17:30 1618通过ApplicationContextAware获取bean ... -
详解 Spring 3.0 基于 Annotation 的依赖注入实现
2011-03-14 17:18 1055简介: Spring 的依赖配置方式与 Spring 框架的内 ... -
spring+hibernate操控LOB对象
2011-03-12 00:27 945spring为hibernate提供了对LOB对像的支持, ... -
Spring AOP
2011-03-11 10:32 823AOP是Aspect Oriented Programming ... -
Spring AOP配置选项
2011-03-11 08:59 1556Spring实现动态代理配置是有两种配置文件:1、 xml ... -
spring 事务传播属性和隔离级别
2011-02-13 14:53 1033一、Propagation (事务的 ... -
spring学习,实例化bean的方式及Bean的作用域
2010-10-26 10:09 1119今天继续学习Spring,黎老师对Spring中比较重要的部分 ... -
Spring学习 xml配置依赖注入
2010-10-26 09:39 953最近项目中也配了几遍ssh框架了,不过老出问题,还是Sprin ... -
IOC控制反转和DI依赖注入区别
2010-10-12 15:20 1142IOC控制反转:说的是创建对象实例的控制权从代码控制剥离到IO ... -
Quartz cron表达式详解
2010-09-27 15:13 915字段 允许 ... -
Spring Bean的作用域
2010-09-27 15:12 908XML代码 <bean id="role ... -
spring配置中调用properties文件
2010-09-27 14:59 1543system.propertiesdatabase.url=j ... -
DataSourceUtils.getConnection()要与其对称方法配合使用
2010-09-15 16:56 1305DataSourceUtils.getConnection() ... -
使用BeanNameAutoProxyCreator实现spring的自动代理
2010-09-06 15:05 981提到代理,我们可以使用ProxyBeanFactory,并配置 ... -
Spring源代码解析(一):IOC容器
2010-08-17 13:33 773在认真学习Rod.Johnson的三部曲之一:< < ... -
Spring源代码分析之(二):IOC容器在web容器中的启动[转]
2010-08-17 13:32 935以下引用自博客:http://jiwenke-spring.b ...
相关推荐
管理 Bean 从第一个 Spring 应用程式开始,逐步了解何谓依赖注入,以及如何使用 Spring 的容器功能来管理 Bean,了解 Bean 在 Spring 容器中的生命周期。 第一个 Spring 程式 BeanFactory、 ...
spring 三种注入(就是从spring容器中将bean放入对象属性值中) Spring下描述依赖关系@Resource, @Autowired和@Inject的区别与联系 Spring中BeanFactory和ApplicationContext的区别 谈谈Spring IOC的理解,原理与...
spring以动态灵活的方式来管理对象 , 注入的两种方式,设置注入和构造注入。 设置注入的优点:直观,自然 构造注入的优点:可以在构造器中决定依赖关系的顺序。 什么是AOP? 面向切面编程(AOP)完善spring的...
Spring提供了两种类型的IOC容器实现 BeanFactory:IOC容器的基本实现,在调用getBean()方法时才会实例化对象 ApplicationContext:提供了更多的高级特性,在加载配置文件后就会实例化对象。是BeanFactory的子接口 ...
Spring配置管理SessionFactory与数据库的连接,在实际的应用中,数据源会采用依赖注入的方式,传递给SessionFactory。 见beans-config_sh.xml 24.3 Spring对Hibernate的简化 24.3.1 概述 Hibernate的持久层访问步骤...
Spring IoC容器的两个接口 依赖注入的类型 Bean的配置 …IOC:控制反转依赖注入。它使程序组件或类之间尽量形成一种松耦合的结构,开发者在使用类的实列之前,需要先创建对象的实列。而IoC是将创建实列的任务交给了...
247 14.6 小结 248 第15章 Spring框架 249 15.1 Spring 2.0的体系结构 249 15.2 Ioc容器 250 15.2.1 BeanFactory 250 15.2.2 ApplicationContext 252 15.2.3 Beans的生命周期过程 253 15.2.4 Beans的进阶管理 ...
1. 目录 1. 2. 目录 .........................................................................................................................................................1 JVM ........................