Spring Boot @PropertySource 加载指定yaml配置文件获取不到配置的解决方法

Spring Boot @PropertySource 加载指定yaml配置文件获取不到配置的解决方法

@PropertySource可用于加载指定的配置文件,可以是properties配置文件,也可以是yml、yaml配置文件。

加载properties配置文件:

@Component
@PropertySource(value = {"classpath:person.properties"})
@ConfigurationProperties(prefix = "person")
public class Person {
    // @Value("${person.last-name}")
    private String lastName;
    private Integer age;
    private Boolean boss;
    private Date birth;
}

打印结果:Person{lastName='Jerry', age=25, boss=true, birth=Sat Dec 12 00:00:00 CST 2020, maps={k1=haha, k2=hehe}, lists=[a, b, c, d], dog=Dog{name='狗子', age=12}}

测试之后,可以正常获取到properties配置文件中的内容。

但加载yml配置文件的时候,则会出现获取不到属性的问题:

@Component
@PropertySource(value = {"classpath:person.yaml"})
@ConfigurationProperties(prefix = "person")
public class Person {
    private String lastName;
    private Integer age;
    private Boolean boss;
    private Date birth;

打印结果:Person

所有属性值都为空,显然是没有读取到配置文件。

解决方法:

@PropertySource 的注解中,有一个factory属性,可指定一个自定义的PropertySourceFactory接口实现,用于解析指定的文件。默认的实现是DefaultPropertySourceFactory,继续跟进,使用了PropertiesLoaderUtils.loadProperties进行文件解析,所以默认就是使用Properties进行解析的。

可以写一个类继承DefaultPropertySourceFactory,然后重写createPropertySource()

public class YamlAndPropertySourceFactory extends DefaultPropertySourceFactory {
    @Override
    public PropertySource<?> createPropertySource(String name, EncodedResource resource) throws IOException {
        if (resource == null) {
            return super.createPropertySource(name, resource);
        }
        Resource resourceResource = resource.getResource();
        if (!resourceResource.exists()) {
            return new PropertiesPropertySource(null, new Properties());
        } else if (resourceResource.getFilename().endsWith(".yml") || resourceResource.getFilename().endsWith(".yaml")) {
            List<PropertySource<?>> sources = new YamlPropertySourceLoader().load(resourceResource.getFilename(), resourceResource);
            return sources.get(0);
        }
        return super.createPropertySource(name, resource);
    }
}

使用的时候加上factory属性,属性值为YamlAndPropertySourceFactory.class

@Component
@PropertySource(value = {"classpath:person.yaml"},factory = YamlAndPropertySourceFactory.class)
@ConfigurationProperties(prefix = "person")
public class Person {
    private String lastName;
    private Integer age;
    private Boolean boss;
    private Date birth;
}

再次测试:

打印结果:Person{lastName='法外狂徒张三', age=25, boss=true, birth=Sat Dec 12 00:00:00 CST 2020, maps={friend1=lisi, friend2=wangwu, friend3=zhaoliu}, lists=[haha, hehe, xixi, hiahia], dog=Dog{name='阿黄', age=12}}

发现可以正常获取到yml配置文件中的属性值了。

posted @ 2020-09-26 15:22  笑到不能自已  阅读(3672)  评论(0编辑  收藏  举报