• Spring加载classpath与classpath*的过程剖析


    使用spring-boot 1.5.7 

    在resource目录下创建i18n文件夹

    使用spring的默认配置没有加载到文件

    # INTERNATIONALIZATION (MessageSourceAutoConfiguration)
    spring.messages.always-use-message-format=false # Set whether to always apply the MessageFormat rules, parsing even messages without arguments.
    spring.messages.basename=messages # Comma-separated list of basenames, each following the ResourceBundle convention.
    spring.messages.cache-seconds=-1 # Loaded resource bundle files cache expiration, in seconds. When set to -1, bundles are cached forever.
    spring.messages.encoding=UTF-8 # Message bundles encoding.
    spring.messages.fallback-to-system-locale=true # Set whether to fall back to the system Locale if no files for a specific Locale have been found.

    在 MessageSourceAutoConfiguration中看到如下代码:

    不是很明白classpath*是什么意思
    PathMatchingResourcePatternResolver中的方法实现
        @Override
        public Resource[] getResources(String locationPattern) throws IOException {
            Assert.notNull(locationPattern, "Location pattern must not be null");
            if (locationPattern.startsWith(CLASSPATH_ALL_URL_PREFIX)) {
                // a class path resource (multiple resources for same name possible)
           // CLASSPATH_ALL_URL_PERFIX = "classpath*";   
           //getPathMatcher().isPattern("messages.properties") 返回false
    if (getPathMatcher().isPattern(locationPattern.substring(CLASSPATH_ALL_URL_PREFIX.length()))) { // a class path resource pattern return findPathMatchingResources(locationPattern); } else { // all class path resources with the given name return findAllClassPathResources(locationPattern.substring(CLASSPATH_ALL_URL_PREFIX.length())); } } else { // Generally only look for a pattern after a prefix here, // and on Tomcat only after the "*/" separator for its "war:" protocol. int prefixEnd = (locationPattern.startsWith("war:") ? locationPattern.indexOf("*/") + 1 : locationPattern.indexOf(":") + 1); if (getPathMatcher().isPattern(locationPattern.substring(prefixEnd))) { // a file pattern return findPathMatchingResources(locationPattern); } else { // a single resource with the given name return new Resource[] {getResourceLoader().getResource(locationPattern)}; } } }

    解决方法:

        @Bean
        public MessageSource messageSource() {
            ReloadableResourceBundleMessageSource messageSource = new ReloadableResourceBundleMessageSource();
            messageSource.setBasename("classpath:i18n/messages");
            messageSource.setDefaultEncoding("UTF-8");
            return messageSource;
        }

    ResourceBundleMessageSource限制了我们只能将对应的资源文件放置在类路径下

    ReloadableResourceBundleMessageSource允许我们指定非类路径下的文件作为对应的资源文件

  • 相关阅读:
    使用Apworks开发基于CQRS架构的应用程序(六):创建.NET WCF服务
    Microsoft NLayerApp案例理论与实践 项目简介与环境搭建
    使用Apworks开发基于CQRS架构的应用程序(七):配置数据库
    测试一下亚马逊联盟
    Revit参数族之DMD系列静电水处理器
    Revit参数族之ZP系列消声器
    第一个Ruby程序:Hello world!
    百度文库下载器冰点下载
    sketchup ruby编程之绘制梯段
    加西亚马尔克斯枯枝败叶
  • 原文地址:https://www.cnblogs.com/yuyutianxia/p/8360324.html
Copyright © 2020-2023  润新知