BeanFactory与ApplicationContext的区别

概述

BeanFactory:
是Spring里面最低层的接口,提供了最简单的容器的功能,只提供了实例化对象和拿对象的功能。

ApplicationContext:
public interface ApplicationContext extends EnvironmentCapable, ListableBeanFactory, HierarchicalBeanFactory, MessageSource, ApplicationEventPublisher, ResourcePatternResolver
应用上下文,继承BeanFactory接口,所以ApplicationContext包含BeanFactory的所有功能以及更多功能。

  • MessageSource:国际化
  • ResourceLoader:资源访问
  • 载入多个上下文
  • ApplicationEvent、ApplicationListener:事件机制(监听器)
  • AOP(拦截器)

两者装载bean的区别

  1. BeanFactory:延迟实例化。BeanFactory在启动的时候不会去实例化Bean,中有从容器中拿Bean的时候才会去实例化。
  2. 延迟实例化的优点:
    • 应用启动的时候占用资源很少;对资源要求较高的应用,比较有优势;
  3. ApplicationContext:不延迟实例化。ApplicationContext在启动的时候就把所有的Bean全部实例化了。它还可以为Bean配置lazy-init=true来让Bean延迟实例化。
  4. 不延迟实例化的优点:
    • 所有的Bean在启动的时候都加载,系统真正运行时的速度快
    • 在启动的时候所有的Bean都加载了,我们就能在系统启动的时候,尽早的发现系统中的配置问题;

MessageSource:国际化

spring中对国际化支持挺好的,比较简单,只需要按照语言配置几个properties文件;然后注册一个国际化的相关的bean,bean内需指定一下配置文件的位置,基本上就可以了。

spring中国际化是通过MessageSource这个接口来支持的,常见3个实现类:

  • ResourceBundleMessageSource:这个是基于Java的ResourceBundle基础类实现,允许仅通过资源名加载国际化资源
  • ReloadableResourceBundleMessageSource:这个功能和第一个类的功能类似,多了定时刷新功能,允许在不重启系统的情况下,更新资源的信息
  • StaticMessageSource:它允许通过编程的方式提供国际化信息,一会我们可以通过这个来实现db中存储国际化信息的功能。

通常我们在ApplicationContext类型的容器中使用国际化3个步骤:

  1. 步骤一:创建国际化文件,国际化文件命名格式:名称_语言_地区.properties
  2. 步骤二:向容器中注册一个MessageSource类型的bean,bean名称必须为:messageSource,指定国际化文件路径
  3. 步骤三:调用AbstractApplicationContext中的getMessage来获取国际化信息,其内部将交给第二步中注册的messageSource名称的bean进行处理。

ResourceBundleMessageSource

步骤一:创建国际化文件

创建3个文件,文件目录ApplicationContextDemo/
message.properties:

name=您的姓名
personal_introduction=默认个人介绍:{0},{1}

当系统找不到的时候会使用这个默认的。

message_zh_CN.properties:中文【中国】:

name=姓名
personal_introduction=个人介绍:{0},{1},{0}

message_en_GB.properties:英文【英国】:

name=Full name
personal_introduction=personal_introduction:{0},{1},{0}

注册一个MessageSource类型的bean

注意必须是MessageSource类型的,bean名称必须为messageSource
配置类MainConfig1 :

package ApplicationContextDemo;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.support.ResourceBundleMessageSource;

@Configuration
public class MainConfig1 {
    @Bean
    public ResourceBundleMessageSource messageSource() {
        ResourceBundleMessageSource result = new ResourceBundleMessageSource();
        //可以指定国际化化配置文件的位置,格式:路径/文件名称,注意不包含【语言_国家.properties】含这部分
        result.setBasenames(new String[]{"ApplicationContextDemo/message"}); //@1
        return result;
    }
}

@1:这个地方的写法需要注意,可以指定国际化化配置文件的位置,格式:路径/文件名称,注意不包含【语言_国家.properties】含这部分。

容器调用getMessage来获取国际化信息

程序调用MessageSourceTest:

package ApplicationContextDemo;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
import java.util.Locale;

public class MessageSourceTest {
    public static void main(String[] args) {
        AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(MainConfig1.class);
        //未指定Locale,此时系统会取默认的locale对象,本地默认的值中文【中国】,即:zh_CN
        System.out.println(context.getMessage("name", null, null));
        System.out.println(context.getMessage("name", null, Locale.CHINA)); //CHINA对应:zh_CN
        System.out.println(context.getMessage("name", null, Locale.UK)); //UK对应en_GB
    }

    System.out.println(context.getMessage("personal_introduction", new String[]{"spring高手", "java高手"}, Locale.CHINA)); //CHINA对应:zh_CN
    System.out.println(context.getMessage("personal_introduction", new String[]{"spring", "java"}, Locale.UK)); //UK对应en_GB
}

运行结果:
您的姓名
您的姓名
Full name
默认个人介绍:spring高手,java高手
personal_introduction:spring,java,spring

ReloadableResourceBundleMessageSource

ReloadableResourceBundleMessageSource这个类,功能和上面案例中的ResourceBundleMessageSource类似,不过多了个可以监控国际化资源文件变化的功能,有个方法用来设置缓存时间:

public void setCacheMillis(long cacheMillis)

StaticMessageSource

这个类它允许通过编程的方式提供国际化信息,这个类中有2个方法比较重要:

public void addMessage(String code, Locale locale, String msg);
public void addMessages(Map<String, String> messages, Locale locale);

通过这两个方法来添加国际化配置信息。

详见:https://www.cnblogs.com/konglxblog/p/15488207.html 《spring成神之路第二十六篇:国际化详解》

ResourceLoader:资源访问

这是spring对资源文件(如:properties)进行存取操作的功能。

步骤一:获取spring容器

ApplicationContext acxt =new ClassPathXmlApplicationContext("/applicationContext.xml");

步骤二:访问资源

1.通过虚拟路径来存取。当资源位于CLASSPATH路径下时,可以采用这种方式来存取。
Resource resource = acxt.getResource(“classpath:messages_en_CN.properties”);

2.通过绝对路径存取资源文件。
Resource resource = acxt.getResource(“file:F:/testwork/MySpring/src/messages_en_CN.properties”);

3.相对路径读取资源文件。
Resource resource = acxt.getResource("/messages_en_CN.properties");

Resource常用的方法:

  • getFilename():获得文件名称
  • contentLength():获得文件大小
  • createRelative(path):在资源的相对地址上创建新文件
  • exists():是否存在
  • getFile():获得Java提供的File 对象
  • getInputStream():获得文件的流

其实通过ApplicationContext上下文访问外部配置文件,还可以通过applicationContext.xml中配置<context:property-placeholder location="…" />指定外部属性文件,进而获取参数。详见 《Spring-IOC》-外部属性文件。

spring载入多个上下文

不同项目使用不同分模块策略,spring配置文件分为:
applicationContext.xml(主文件,包括JDBC配置,hibernate.cfg.xml,与所有的Service与DAO基类)
applicationContext-cache.xml(cache策略,包括hibernate的配置)
applicationContext-transaction.xml(事务)
moduleName-Service.xml
moduleName-dao.xml

配置方式

1、加载方式中可以加载多个配置文件,获取到ApplicationContext 对象中

String[] configs = {"applicationContext.xml","user_spring.xml"};
ApplicationContext ctx = new ClassPathXmlApplicationContext(configs);

AbstractDao myUserDAO =  (AbstractDao) ctx.getBean("userDao");

2、web.xml文件中引用
web.xml里面可以定义两种参数:
1、application范围内的参数,存放在servletcontext中。中的参数(可以指定多个文件)
2、servlet范围内的参数,只能在servlet的init()方法中取得, 中的参数,在init方法中用this.getInitParameter(“param1”)获取

监听器、拦截器后续文章学习。

参考:https://www.iteye.com/blog/youyu4-2346183

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

不会叫的狼

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值