I am getting a problem in reading my yaml through java, using spring. Let me show the code first
@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;
}
}
My yaml file:
cassandra:
hosts: localhost:9142, 127.0.0.1:9142
keyspace: test
countries:
orders:
JPY: 1000
USD: 1000
requests:
JPY: 100000
USD: 100000
The spring context xml also has this:
<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" />
Now, the expectation that I have(had) is that, during the runtime of my spring-test application(the context xml is from my test resources, the yaml is also in my test), these values of orders and requests are set, but they are null. Also, note, there are other values in my yaml besides this that I am injecting using @Value(${...}), they are injected absolutely fine!
I looked at this: Spring Boot - inject map from application.yml
I have done virtually the same, but yet, my values are not set. Kindly help.
I was going through google, found this link: http://docs.spring.io/spring/docs/current/javadoc-api/org/springframework/beans/factory/config/YamlPropertiesFactoryBean.html
In this, it says, everything is read as a string and not a map. Is there any other class that supports reading of Yaml file the way they did it here: Spring Boot - inject map from application.yml
Or is my understanding of YamlPropertiesFactoryBean wrong?
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'
These are the dependencies in gradle. You might be wondering why I have spring-core and spring-boot, essentially, I don't want spring-boot, but without spring-boot, I don't get to add @EnableConfigurationProperties and @ConfigurationProperties, I honestly don't know if I can read the yaml content into a map without them. Hence those two dependencies are added, but if there's a way to remove them, I would be more than happy to remove those two dependencies.
Warm regards, Pavan
I had the same problem with different generic types and I solved it by initializing the map member and remove the setter method, e.g.:
@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;
}
...
}
Please note I used java 7 diamond operator and change the member type to Map instead of HashMap.
IMPORTANT: In my code, I use Spring's configuration class instead of XML and moved the EnableConfigurationProperties
to the configuration class. In your case it should be something like:
@Configuration
@EnableConfigurationProperties(value = {UserLimitReader.class})
public class SpringConfiguration {
...
}
@ConfigurationProperties(prefix = "countries", locations: "classpath:config/application.yaml")
public class UserLimitReader {
...
}
Don't know how you configure it using XML, however as I wrote in my comments I still think you should make sure Spring's finds your class using component scan or something alike.
@Value
work as Spring loads the YAML file without any problem using your context file, however it does not mean UserLimitReader
file is loaded and configured by Spring.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With