kmosley
kmosley

Reputation: 366

How do I load a bean value from a file with job parameter substitution?

In my spring batch project I can do something like this:

<bean id="exampleTasklet" class="my.custom.Tasklet">
    <property name="message" value="job parameter value: #{jobParameters['arg1']}"/>
</bean>

and the message property will have a value taken from the spring batch job parameters. However, the value that I actually want to assign is very large and I don't want to put it in the xml file. I know this syntax doesn't work, but I would like to do something like:

<bean id="exampleTasklet" class="my.custom.Tasklet">
    <property name="message" read-value-from-file="/path/to/file.txt"/>
</bean>

and that file would contain the line "job parameter value: #{jobParameters['arg1']}" which spring will parse as if the file content was in a value="" attribute.

Is there a nice way to do this?

Upvotes: 0

Views: 2030

Answers (3)

Devon_C_Miller
Devon_C_Miller

Reputation: 16528

I think what you are looking for is a PropertyPlaceholderConfigurer.

<bean  class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">  
    <property name="location" value="/path/to/file.properties" /> 
    <property name="placeholderPrefix" value="#{" /> 
    <property name="placeholderSuffix" value="}" /> 
</bean>

This is run by Spring as a bean processor and will attempt to resolve placeholder tokens. There is a default instance that will resolve against system properties, using this notation: ${propertyname}. For your notation, you would need to specify the placeholderPrefix/Suffix. When there are multiple bean processors, the order is determined by the order property. By default, if a processor fails to resolve a placeholder, execution fails, but this can be altered by setting ignoreUnresolvablePlaceholders. Since the mechanism is property driven, you probably want to consider a notation like:

<property name="message" value="job parameter value: #{jobParameters.arg1}"/>

Or, if what you're trying to convey is that arg1 is also a parameter, you might try:

<property name="message" value="job parameter value: #{jobParameters.${arg1}}"/>

Spring loops over the bean processors until no replacements are performed, or an exception is raised. So defining a property as ${something.${orOther}} is valid.

Upvotes: 1

Peter Wippermann
Peter Wippermann

Reputation: 4579

If anybody came here to do something like this from a properties-file:

If you want a property from a .properties-file to appear in the JobParameters, you won't find ready-to-use solution. You can do the following:

  1. Wrap a bean around your properties file.
  2. Pass this bean to another one which has access to the JobParameters and can pump the properties from the file into that class.
  3. Then you should be able to access your properties with Spring's Expression Language and do something like: <bean id="myBean" class="my.custom.Bean"> <property name="prop" value="#{jobParameters['arg1']}"/> </bean>

Alternatively, I think the solution proposed by Devon_C_Miller is much easier. You don't have the properties in your JobParameters then. But if the replacement in the XML configuration is the only thing you want, you only have to change your placeholders to:

${myPropFromFile}

Happy batching, everyone ;-)

Upvotes: 0

Matin Kh
Matin Kh

Reputation: 5178

I would suggest you to use a String as file name and in your bean open that file.
I'm not sure if I get your problem right. I'm just suggesting something like Spring MessageBundle

Something like this:

<bean id="exampleTasklet" class="my.custom.Tasklet">
    <property name="messagePath" location="/path/to/file.txt"/>
</bean>


And in your exampleTasklet read the file and do your thing (I'm not sure what it is)

Upvotes: 0

Related Questions