bmcdonald
bmcdonald

Reputation: 401

Overriding a few properties for junit test using spring or camel property placeholder in a maven layout

I want to specify only the properties I want to override in a test properties file of the same name in the src/test/resources folder.

A little more detail...

In a maven layout I have a properties file that contains the deployed value to use (eg. input.uri).

src/main/resources/app.properties: 
input.uri=jms:topic:in
app.name=foo_bar

This file's properties are loaded into the context.xml file by the property-placeholder:

src/main/resources/META-INF/spring/context.xml:
<context:property-placeholder properties-ref="springProperties"/>
<util:properties id="springProperties" local-override="true" location="classpath:app.properties" />

I have the test properties file with the same name, app.properties, in src/test/resources folder and override the input.uri definition to one that my junit test will use. (note, app.name doesn't change).

src/test/resources/app.properties: 
input.uri=seda:in

How would you write the junit test and/or a test context.xml file so that properties are loaded from the src/main/resources/app.properties file, but any properties defined in the src/test/resources/app.properties file override the ones in the src/main/resources/app.properties file? Without it being obvious that you're loading two different files either in the src/main files or src/test junit test files - I want the property placeholder to search the classpath and pick the right values.

Upvotes: 6

Views: 5294

Answers (2)

р&#252;ффп
р&#252;ффп

Reputation: 5448

This answer assume your tests uses Apache Camel.

To easily test a Camel route, you have to extends your jUnit test from CamelTestSupport and then overrides the method createCamelContext like this:

@Override
protected CamelContext createCamelContext() throws Exception {
    CamelContext camelContext = super.createCamelContext();
    // overrides properties
    camelContext.addComponent("properties", new PropertiesComponent(
            "classpath:app.properties"));
    
    return camelContext;
}

Like this all properties in the file src/test/resources/app.properties will be taken in account for the whole test.

But since I am developing with Apache Camel since a long time, my preference is to directly use the method useOverridePropertiesWithPropertiesComponent() which is part of the CamelTestSupport class.

Exemple:

@Override
protected Properties useOverridePropertiesWithPropertiesComponent() {
    Properties props = new Properties();
    props.put("input.uri", "direct:testInput");
    props.put("destination.uri", "mock:TEST.FLOW.QUEUE");
    return props;
}

After you can also map your property values like this:

@EndpointInject(uri = "direct:testInput")
protected Endpoint testInput;

@EndpointInject(uri = "mock:TEST.FLOW.QUEUE")
private MockEndpoint mockDestination;   

and you can use them in your tests.

Here is also an example with Junit5 (recommended).

Upvotes: 0

Biju Kunjummen
Biju Kunjummen

Reputation: 49915

You will have to provide a different name though - if both the properties in the main and the test have the same name, the entire properties in one or the other will take effect.

Instead an approach like this has worked for me:

In your src/main/resources/META-INF/spring/context.xml do this:

<context:property-placeholder location="classpath:app.properties" local-override="true" properties-ref="springProperties"/>
<util:properties id="springProperties">
</util:properties>

In a test-context.xml file:

<import resource="classpath:/META-INF/spring/context.xml">
<util:properties id="springProperties"> <!-- or refer to a overriding file -->
    <prop key="input.uri">seda.in</prop>
</util:properties>

This will override the properties for you, while maintaining the not overridden values from the original file.

Upvotes: 5

Related Questions