4

I have a Spring-based web application running in a tomcat container and I want to maintain two different configuration files:

  • src/main/resources/default.properties: contains defaults for development, integration tests and when no other properties are set
  • .../tomcat/conf/app.properties: has a different content on different environments and should override default.properties

I have a spring configuration that is working fine when the application runs in a tomcat

app-context.xml

<context:property-placeholder
    ignore-resource-not-found="true"
    ignore-unresolvable="true"
    system-properties-mode="OVERRIDE"
    location="classpath:default.properties,
              file:${catalina.home}/conf/app.properties"/>

But when I try to use this configuration in an integration test, outside of a tomcat container, loading the applicationContext fails:

java.lang.IllegalStateException: Failed to load ApplicationContext
    at org.springframework.test.context.TestContext.getApplicationContext(TestContext.java:308)
    ...
Caused by: org.springframework.beans.factory.BeanDefinitionStoreException: Invalid bean definition with name 'org.springframework.beans.factory.config.PropertyPlaceholderConfigurer#0' defined in null: Could not resolve placeholder 'catalina.home'
    at org.springframework.beans.factory.config.PropertyPlaceholderConfigurer.processProperties(PropertyPlaceholderConfigurer.java:287)

Is there any way to tell Spring to ignore the location file:${catalina.home}/conf/app.properties when the property catalina.home is not set in the current context?

Kim Hagedorn
  • 43
  • 1
  • 4

3 Answers3

0

you can set ignore-resource-not-found to solve this problem.

Try this:

<context:property-placeholder
    ignore-resource-not-found="true"
    ignore-unresolvable="true"
    system-properties-mode="OVERRIDE"
    location="classpath:default.properties,
              file:${catalina.home}/conf/app.properties"/>

Code snippet from spring-context.xsd:

<xsd:attribute name="ignore-resource-not-found" type="xsd:boolean" default="false">
            <xsd:annotation>
                <xsd:documentation><![CDATA[
    Specifies if failure to find the property resource location should be ignored.
    Default is "false", meaning that if there is no file in the location specified
    an exception will be raised at runtime.
                ]]></xsd:documentation>
            </xsd:annotation>
        </xsd:attribute>
Christophe Roussy
  • 16,299
  • 4
  • 85
  • 85
Jaiwo99
  • 9,687
  • 3
  • 36
  • 53
  • ignore-resource-not-found and ignore-unresolvable was set, but this doesn't seem to help when the missing property is part of a location. It turned out that an empty default value does help – Kim Hagedorn Jan 09 '15 at 13:48
0

Since you have a context, where some PP values may be unresolved you can try to use a default variant for the property:

file:${catalina.home:}/conf/app.properties

In this case the path prefix is resolved to the empty String if there is no catalina.home property, e.g. in the System.getProperties(), which is the case for Tomcat, I guess.

And after that the ignore-resource-not-found="true" does the stuff.

Artem Bilan
  • 113,505
  • 11
  • 91
  • 118
0

What I'd suggest is using spring profiles to enable/disable property files.

When running in tomcat swith on the "tomcat" or "web" profile and put the loading of the app.properties into that profile.

Michael Wiles
  • 20,902
  • 18
  • 71
  • 101