【Spring】Spring容器获取Bean

      Spring容器是生产并管理Bean实例的工厂。Spring有两个核心的接口:BeanFactoryApplicationContext

BeanFactorySpring中最底层的接口,提供了最简单的容器的功能,只提供了实例化对象和获取对象的功能。

ApplicationContext为应用上下文,它是Spring的一种更高级的容器,其实是BeanFactory的子接口,对BeanFactory进行了扩展,提供了更多的功能。

BeanFactory

      创建BeanFactory实例时,必须使用Spring容器管理的Bean详细配置信息,在Spring中有几种BeanFactory的实现。其中最常使用的是org.springframework.beans.factory.xml.XmlBeanFactory,它根据XML文件中的定义装在Bean。XML配置文件通常使用Resource对象传入。

 Spring提供了以下多种Resource的实现:

    1.org.springframework.core.io.ByteArrayResource:定义内容由一组字节给定的资源

    2.org.springframework.core.io.ClassPathResource:定义可从classpath提起的资源

    3.org.springframework.core.io.DescripiveResource:定义包含资源描述符,但实际没有可读资源的资源

    4.org.springframework.core.io.FileSyatemResource:定义可从文件系统提取的资源

    5.org.springframework.core.io.InputStreamResource:定义可从输入流提取的资源

    6.org.springframework.core.io.UrlResource:定义可从给定URL提取的资源

    7.org.springframework.web.portlet.context.PortletContextResource:定义可用在portlet上下文中的资源

    8.org.springframework.web.context.support.ServletContextResource:定义可用在servlet上下文中的资源

示例1

 //搜索类加载路径,以类加载路径下的applicationContext.xml文件创建Resource对象
 ClassPathResource resource = newClassPathResource("applicationContext.xml");
 //以Resource对象为参数,创建BeanFactory实例
 BeanFactory factory = newXmlBeanFactory(resource);

      Bean工厂会立即把Bean定义信息载入,但是Bean只有在被需要时才被实例化;只要简单调用getBean()方法,把需要的Bean的名字传入即可。

BeanFactory的源码学习:

package org.springframework.beans.factory;

import org.springframework.beans.BeansException;


public interface BeanFactory {

	 //使用转义符&来得到FactoryBean本身,用来区分通过容器获得FactoryBean本身和其产生的对象
	String FACTORY_BEAN_PREFIX = "&";

	//根据Bean的名字取得IOC容器管理的Bean
	Object getBean(String name) throws BeansException;

	//根据bean的名字和Class类型来得到bean实例,增加了类型安全验证机制
	Object getBean(String name, Class requiredType) throws BeansException;

	 //判断容器是否含有指定名字的bean
	boolean containsBean(String name);

	//查询指定名字的Bean是不是单例的Bean
	boolean isSingleton(String name) throws NoSuchBeanDefinitionException;

	 //判断Bean是不是prototype类型的bean
	boolean isPrototype(String name) throws NoSuchBeanDefinitionException;

	//查询指定了名字的Bean的Class类型是否与指定类型匹配
	boolean isTypeMatch(String name, Class targetType) throws NoSuchBeanDefinitionException;

	  //获取指定名字bean的Class类型
	Class getType(String name) throws NoSuchBeanDefinitionException;

	//查询指定了名字的bean的所有别名,这些别名都是在BeanDefinition中定义的
	String[] getAliases(String name);

}

ApplicationContext

      ApplicationContextBeanFactory进行的扩展,提供了更多的功能,例如:

   ①国际化的功能。②消息发送和相应机制。③统一加载资源。④AOP的功能。

ApplicationContext经常用到的三个实现如下:

   1.ClassPathXmlApplicationContext:从类路径中的XML文件载入上下文定义信息。把上下文定义文件当成类路径资源。

   2.FileSystemXmlApplicationContext:从文件系统中的XML文件载入上下文定义信息。

   3.XmlWebApplicationContext:从Web系统中的XML文件载入上下文定义信息。

示例1ClassPathXMLApplicationContext方式

ApplicationContextfactory=newClassPathXmlApplicationContext("classpath:applicationContext.xml"); 
// src目录下的单个配置文件加载
ApplicationContextfactory=newClassPathXmlApplicationContext("applicationContext.xml"); 
// src目录下的多个配置文件加载
ApplicationContextfactory=new ClassPathXmlApplicationContext(new String[]{"applicationContext-beans.xml","applicationContext.xml"}); 
// src目录下的多个配置文件加载(使用通配符)
ApplicationContextfactory = newClassPathXmlApplicationContext("applicationContext-*.xml");
// src/conf目录下的 配置文件加载
ApplicationContextfactory=newClassPathXmlApplicationContext("conf/applicationContext.xml"); 

示例2:FileSystemXmlApplicationContext方式

ApplicationContextfactory=newFileSystemXmlApplicationContext("src/applicationContext.xml"); 
//使用classpath下的相对路径 
ApplicationContextfactory=newFileSystemXmlApplicationContext("classpath:applicationContext.xml"); 

ApplicationContext源码学习:

package org.springframework.context;

import org.springframework.beans.factory.HierarchicalBeanFactory;
import org.springframework.beans.factory.ListableBeanFactory;
import org.springframework.beans.factory.config.AutowireCapableBeanFactory;
import org.springframework.core.io.support.ResourcePatternResolver;

public interface ApplicationContext extends ListableBeanFactory,
		HierarchicalBeanFactory, MessageSource, ApplicationEventPublisher,
		ResourcePatternResolver {

	// 获取父上下文,如果没有则返回null
	ApplicationContext getParent();

	// 返回AutoCapableBeanFactory,为这个上下文提供AutowireCapableBeanFactory功能
	AutowireCapableBeanFactory getAutowireCapableBeanFactory()
			throws IllegalStateException;

	// 获取应用上下文显示的名称
	String getDisplayName();

	// 返回应用上下文第一次加载的时间毫秒值
	long getStartupDate();

}

ApplicationContext接口中最重要的方法就是getAutowireCapableBeanFactory方法了,因为是通过该方法获取的实例,源码如下:

package org.springframework.beans.factory.config;

import org.springframework.beans.BeansException;
import org.springframework.beans.factory.BeanFactory;

public interface AutowireCapableBeanFactory extends BeanFactory {

	//这个常量表明工厂没有自动装配的Bean
	int AUTOWIRE_NO = 0;

	//根据名称自动装配
	int AUTOWIRE_BY_NAME = 1;

	//根据类型自动装配
	int AUTOWIRE_BY_TYPE = 2;

	//根据构造方法装配
	int AUTOWIRE_CONSTRUCTOR = 3;


	int AUTOWIRE_AUTODETECT = 4;


//根据给定的类型,指定的装配策略,创建新的Bean实例
	Object createBean(Class beanClass, int autowireMode, boolean dependencyCheck)
			throws BeansException;

	//根据给定的策略,类型,装配Bean属性
	Object autowire(Class beanClass, int autowireMode, boolean dependencyCheck)
			throws BeansException;


	void autowireBeanProperties(Object existingBean, int autowireMode, boolean dependencyCheck)
			throws BeansException;


	void applyBeanPropertyValues(Object existingBean, String beanName) throws BeansException;


	Object configureBean(Object existingBean, String beanName) throws BeansException;


	Object initializeBean(Object existingBean, String beanName) throws BeansException;


	Object applyBeanPostProcessorsBeforeInitialization(Object existingBean, String beanName)
			throws BeansException;


	Object applyBeanPostProcessorsAfterInitialization(Object existingBean, String beanName)
			throws BeansException;

}

      小编在深入追踪源码流程时发现了一篇非常漂亮的博客,推荐给大家:http://www.cnblogs.com/ITtangtang/p/3978349.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 11
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 11
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值