Your application calls for a multilayered configuration where a set of default properties can be selectively overridden by local or user configuration preferences.
Create a configuration.xml
file that contains references to multiple properties files, and pass
this file to a ConfigurationFactory.
A ConfigurationFactory will then
return a Configuration implementation
that obtains configuration parameters from multiple properties
file.
Table 7-1 lists configuration properties for an application. A global configuration layer defines default values for configuration parameters. A local configuration layer allows you to customize the behavior of a system at a particular site, and the user configuration layer refines configuration parameters for a specific user. When an application retrieves the value of "name," the user layer's value of "Sean" overrides the global layer's value of "Default User."
Table 7-1. Three layers of configuration
|
Property |
Global |
Local |
User |
|---|---|---|---|
|
threads.max |
50 |
30 |
|
|
threads.min |
20 |
1 |
|
|
timeout |
15.52 |
||
|
interactive |
TRUE |
||
|
color |
red |
black |
|
|
speed |
50 |
55 |
75 |
|
name |
Default User |
Sean |
Properties are stored in three separate files shown in Examples
Example 7-2 (global.properties), Example 7-3 (local.properties), and Example 7-4 (user.properties).
A configuration.xml file
provides a configuration for the ConfigurationFactory. This file is stored as a
resource in the classpath, and the URL for this resource is passed to
the setConfigurationURL( ) method of
ConfigurationFactory. The following
configuration.xml will create a
Configuration object, which locates
properties from properties files using the override order defined in the
XML document. user.properties
overrides local.properties, which
overrides global.properties:
<?xml version="1.0" encoding="ISO-8859-1" ?>
<configuration>
<properties fileName="user.properties"/>
<properties fileName="local.properties"/>
<properties fileName="global.properties"/>
</configuration>The following code passes the URL of the configuration.xml resource to a ConfigurationFactory, and a Configuration instance is returned, which
resolves application configuration parameters according to the rules
outlined above:
import org.apache.commons.configuration.Configuration;
import org.apache.commons.configuration.ConfigurationFactory;
// Configure Factory
ConfigurationFactory factory = new ConfigurationFactory( );
URL configURL = this.getClass( ).getResource("configuration.xml");
factory.setConfigurationURL( configURL );
Configuration config = factory.getConfiguration( );
// Print out properties
System.out.println( "Timeout: " + config.getFloat("timeout"));
System.out.println( "Max Threads: " + config.getString("threads.max"));
System.out.println( "Name: " + config.getString("name"));
System.out.println( "Speed: " + config.getInt("speed"));This code executes and prints the value of four properties to the
console. The timeout property is
retrieved from global.properties,
the threads.max property is retrieved
from local.properties, and both
speed and name are retrieved from user.properties:
Timeout: 15.52 Max Threads: 30 Name: Sean Speed: 75
The configuration.xml
file instructs the ConfigurationFactory to create a Configuration implementation based on multiple
properties files. In the previous example, when the application
retrieves a property, there is no parameter signifying the source of the
property. There is no mechanism for obtaining the source of a
configuration property; in other words, there is no way for our
application to see which properties file a particular value was obtained
from, and there is no mechanism for enumerating the properties in a
single properties file. The configuration.xml file "configures" the
ConfigurationFactory to create a
Configuration—complexity is hidden
from the application and the source of configuration can be changed with
no effect to this example.
A configuration.xml file can
also instruct a ConfigurationFactory
to use a mixture of properties files and XML documents.
The following configuration.xml
instructs the ConfigurationFactory to
create a Configuration instance that
looks for properties from a properties file and an XML document:
<?xml version="1.0" encoding="ISO-8859-1" ?>
<configuration>
<properties fileName="test.properties"/>
<dom4j fileName="test.xml"/>
</configuration>With this configuration, a Configuration instance will attempt to locate
a property with a matching key in test.properties before it attempts to locate
the matching property in test.xml.
See Recipe 7.7 for more
information about retrieving configuration from XML documents.
In addition to properties files and XML documents, Commons
Configuration can also be instructed to resolve configuration properties
from a JNDI tree using org.apache.commons.configuration.JNDIConfiguration.
For more information on accessing properties in a JNDI tree using
Commons Configuration, see the "Configuration Overview" page on the
Commons Configuration project site (http://commons.apache.org/configuration/overview.html).
