在Java中从yaml读取地图获取null

时间:2016-01-09 18:57:22

标签: java spring dictionary yaml

我在使用spring阅读我的yaml时遇到了问题。让我先显示代码

@Component
@EnableConfigurationProperties
@ConfigurationProperties(prefix = "countries")
public class UserLimitReader {

    private HashMap<String, Integer> orders;

    private HashMap<String, Integer> requests;

    public HashMap<String, Integer> getOrders() {
        return orders;
    }

    public void setOrderRedeemableLimit(HashMap<String, Integer>         orders) 
{
        this.orders= orders;
}

public HashMap<String, Integer> getRequests() {
    return requests;
}

public void setMonthlyRedeemableLimit(HashMap<String, Integer> requests) {
    this.requests= requests;
}
}

我的yaml文件:

cassandra:
    hosts: localhost:9142, 127.0.0.1:9142
    keyspace: test
countries:
    orders:
      JPY: 1000
      USD: 1000
    requests:
      JPY: 100000
      USD: 100000

spring context xml也有:

<bean id="yamlProperties"
    class="org.springframework.beans.factory.config.YamlPropertiesFactoryBean">
    <property name="resources">
        <value>classpath:config/application.yaml</value>
    </property>
</bean>

<context:property-placeholder
    properties-ref="yamlProperties" />

现在,我有(期待)的期望是,在我的spring-test应用程序的运行时(上下文xml来自我的测试资源,yaml也在我的测试中),这些订单和请求的值已设置,但它们为空。另外,请注意,除了我使用@Value($ {...})进行注射外,我的yaml中还有其他值,它们注入绝对正常!

我看了这个:Spring Boot - inject map from application.yml

我做的几乎一样,但是,我的价值观没有设定。请帮助。

我正在浏览谷歌,发现此链接: http://docs.spring.io/spring/docs/current/javadoc-api/org/springframework/beans/factory/config/YamlPropertiesFactoryBean.html

在这里,它说,一切都被读作字符串而不是地图。有没有其他类支持读取Yaml文件,就像他们在这里一样:Spring Boot - inject map from application.yml

或者我对YamlPropertiesFactoryBean的理解是错误的吗?

compile 'org.springframework:spring-core:4.2.+'
compile 'org.springframework:spring-beans:4.2.+'
compile 'org.springframework:spring-context:4.2.+'
compile 'org.springframework.boot:spring-boot:1.3.1.RELEASE'
compile 'org.springframework.boot:spring-boot-configuration-processor:1.3.1.RELEASE'

这些是gradle中的依赖项。你可能想知道为什么我有spring-core和spring-boot,本质上,我不想要spring-boot,但是没有spring-boot,我不会添加@EnableConfigurationProperties和@ConfigurationProperties,老实说我不知道我是否可以在没有它们的情况下将yaml内容读入地图。因此添加了这两个依赖项,但是如果有一种方法可以删除它们,我会非常乐意删除这两个依赖项。

热烈的问候, 帕

1 个答案:

答案 0 :(得分:5)

我对不同的泛型类型有同样的问题,我通过初始化map成员并删除setter方法来解决它,例如:

@Component
@EnableConfigurationProperties
@ConfigurationProperties(prefix = "countries")
public class UserLimitReader{
    private Map<String, Integer> orders = new HashMap<>();

    private Map<String, Integer> requests = new HashMap<>();

    public Map<String, Integer> getOrders() {
        return orders;
    }
    ...
}

请注意我使用了java 7菱形运算符,并将成员类型更改为Map而不是HashMap。

重要:在我的代码中,我使用Spring的配置类而不是XML,并将EnableConfigurationProperties移动到配置类。在你的情况下,它应该是这样的:

@Configuration
@EnableConfigurationProperties(value = {UserLimitReader.class})
public class SpringConfiguration {
    ...
}

@ConfigurationProperties(prefix = "countries", locations: "classpath:config/application.yaml")
public class UserLimitReader {
    ...
}

不知道如何使用XML配置它,但是正如我在评论中写的那样,我仍然认为你应该确保Spring使用组件扫描或类似的东西找到你的类。

@Value正常工作,因为Spring使用您的上下文文件加载YAML文件没有任何问题,但这并不意味着Spring加载和配置了UserLimitReader文件。