Author: oheger
Date: Thu Aug 11 06:22:49 2011
New Revision: 1156501
URL: http://svn.apache.org/viewvc?rev=1156501&view=rev
Log:
[CONFIGURATION-459] Merged documentation of ConfigurationFactory into the
DefaultConfigurationBuilder document.
Modified:
commons/proper/configuration/trunk/src/site/xdoc/userguide/howto_configurationbuilder.xml
Modified:
commons/proper/configuration/trunk/src/site/xdoc/userguide/howto_configurationbuilder.xml
URL:
http://svn.apache.org/viewvc/commons/proper/configuration/trunk/src/site/xdoc/userguide/howto_configurationbuilder.xml?rev=1156501&r1=1156500&r2=1156501&view=diff
==============================================================================
---
commons/proper/configuration/trunk/src/site/xdoc/userguide/howto_configurationbuilder.xml
(original)
+++
commons/proper/configuration/trunk/src/site/xdoc/userguide/howto_configurationbuilder.xml
Thu Aug 11 06:22:49 2011
@@ -15,80 +15,367 @@
See the License for the specific language governing permissions and
limitations under the License.
-->
+<!-- $Id$ -->
<document>
<properties>
<title>Configuration Builder Howto</title>
- <author email="[email protected]">Oliver Heger</author>
</properties>
<body>
<section name="Using DefaultConfigurationBuilder">
<p>
- The <code>ConfigurationFactory</code> class that was introduced in the
- <a
href="howto_configurationfactory.html#Using_a_Configuration_Factory">last
- section</a> is a powerful tool for dealing with multiple different
- configuration sources, but it also has some shortcomings:
+ This section explains how a
+ <code><a
href="../apidocs/org/apache/commons/configuration/DefaultConfigurationBuilder.html">
+ DefaultConfigurationBuilder</a></code>object is setup that provides
+ access to a collection of different configuration sources.
+ <code>DefaultConfigurationBuilder</code> is the option of choice for
+ applications that have to deal with multiple configuration sources. It
+ provides the following features:
<ul>
- <li>The format for configuration definition files is not
extensible.</li>
- <li>Complex initializations of the declared configuration sources (e.g.
- for assigning a reloading strategy) are not supported.</li>
- <li>The returned configuration object is not hierarchical, which limits
- the query facilities somewhat.</li>
- <li>Declared configuration sources can only be accessed by index from
the
- returned composite configuration, which means that code using a
- <code>ConfigurationFactory</code> depends on the order of declarations
- in a configuration definition file.</li>
+ <li>Various configuration sources can be combined to a single
+ <a href="howto_combinedconfiguration.html#Combined Configuration">
+ CombinedConfiguration</a> object. This is a truly hierarchical
+ configuration supporting enhanced query facilities.</li>
+ <li>As configuration sources the most relevant
<code>Configuration</code>
+ implementations provided by this library are supported. Sources are
+ defined as <a href="howto_beans.html#Declaring and Creating Beans">bean
+ declarations</a>, so complex initializations are possible.</li>
+ <li>Meta data can be provided to fine-tune the constructed
+ configuration.</li>
+ <li><code>DefaultConfigurationBuilder</code> is extensible. Custom
+ configuration sources can be added.</li>
</ul>
</p>
<p>
- To work around these limitations the class
- <code><a
href="../apidocs/org/apache/commons/configuration/DefaultConfigurationBuilder.html">
- DefaultConfigurationBuilder</a></code> was introduced.
+ This document starts with some explanations of
+ <code>DefaultConfigurationBuilder</code> basics. Then the
<em>configuration
+ definition files</em> processed by
<code>DefaultConfigurationBuilder</code>
+ are discussed in detail. Finally an advanced example is presented.
</p>
- <subsection name="ConfigurationFactory Differences">
- <p>
- From its basic usage scenarios <code>DefaultConfigurationBuilder</code>
is
- very similar to <code>ConfigurationFactory</code>. It is able to process
- the same configuration definition files as can be read by
- <code>ConfigurationFactory</code>, but supports more options. The
following
- list identifies the main differences between these classes:
- </p>
+ <subsection name="The configuration definition file">
<p>
- <ul>
- <li><code>DefaultConfigurationBuilder</code> extends
<code>XMLConfiguration</code>.
- This means that it is a <a href="howto_filebased.html#File-based
Configurations">
- file-based configuration</a>, and thus supports multiple ways of
- specifying the location of the configuration definition file (e.g.
- as <code>java.io.File</code> object, as URL, etc.).</li>
- <li>The configuration object returned by a
<code>DefaultConfigurationBuilder</code>
- is an instance of the <a
href="howto_combinedconfiguration.html#Combined Configuration">
- CombinedConfiguration</a> class, i.e. a truely hierarchical
- configuration supporting enhanced query facilities.</li>
- <li>Each declaration of a configuration source in the configuration
- definition file is interpreted as a
- <a href="howto_beans.html#Declaring and Creating Beans">bean
- declaration</a>, so complex initializations are supported.</li>
- <li><code>DefaultConfigurationBuilder</code> supports custom tags in
its
- configuration definition file. For this purpose a so-called
- <em>configuration provider</em> has to be registered, which will be
- called when a corresponding tag is encountered.</li>
- </ul>
+ In previous chapters we have already seen how specific configuration
+ classes like <code>PropertiesConfiguration</code> or
+ <code>XMLConfiguration</code> can be used to load configuration data from
+ a single source. This may be sufficient for small applications, but if
+ requirements for configuration become more complex, additional support
+ for managing a set of different configuration sources is desired. This is
+ the domain of <code>DefaultConfigurationBuilder</code> which allows
+ combining multiple configuration sources. The properties defined in these
+ sources can then be accessed as if they were defined in a single
+ configuration file. The sources to be loaded have to be defined in a
+ XML document with a specific structure, a so-called <em>configuration
+ definition file</em>. The following listing shows a simple example of
such
+ a definition file:
+ </p>
+ <source><![CDATA[
+<?xml version="1.0" encoding="ISO-8859-1" ?>
+
+<configuration>
+ <properties fileName="usergui.properties"/>
+</configuration>
+]]></source>
+ <p>
+ A configuration definition file can contain an arbitrary number of
+ elements declaring the configuration sources to load. The
+ <code><properties></code> element is one of these; it is used to
+ include properties files. For this example we store the definition file
+ in the same directory as the properties file and call it
+ <code>config.xml</code>. The properties file used in this example is the
+ same as in the section about <a href="howto_properties.html">properties
+ files</a>.
</p>
</subsection>
- <subsection name="Enhancements to the configuration definition file">
+ <subsection name="Setting up a DefaultConfigurationBuilder">
<p>
- As was already pointed out, <code>DefaultConfigurationBuilder</code>
- maintains compatibility with <code>ConfigurationFactory</code> in that it
- understands the same configuration definition files. In addition to the
- elements that are allowed in a configuration definition file for
- <code>ConfigurationFactory</code> the data files for
- <code>DefaultConfigurationBuilder</code> support some additional options
- providing greater flexibility. This section explains these enhanced
- features.
+ Now we have to create a <code>DefaultConfigurationBuilder</code> object
+ and let it read this definition file. This is quite simple: Just create a
+ new instance and set the name of the definition file
+ (<code>DefaultConfigurationBuilder</code> is derived from
+ <code>XMLConfiguration</code>, so all options for specifying the document
+ to load are available here, too). The combined configuration collecting
+ all sources defined in the configuration definition file can then be
+ obtained by calling the <code>getConfiguration()</code> method:
+ </p>
+ <source><![CDATA[
+DefaultConfigurationBuilder builder = new DefaultConfigurationBuilder();
+builder.setFile(new File("config.xml"));
+Configuration config = builder.getConfiguration(true);
+]]></source>
+ <p>
+ Now the <em>config</em> object can be accessed in the usual way to query
+ configuration properties, e.g. by using methods like
<code>getString()</code>,
+ or <code>getInt()</code>. We will see in a moment how properties defined
+ in different configuration sources are accessed.
+ </p>
+ </subsection>
+
+ <subsection name="Overriding properties">
+ <p>
+ Using <code>DefaultConfigurationBuilder</code> to collect configuration
+ sources does not make much sense if there is only a single source to be
+ loaded. So let's add another one! This time we will embedd a XML file:
+ <em>gui.xml</em> which is shown in the next listing:
+ </p>
+ <source><![CDATA[
+<?xml version="1.0" encoding="ISO-8859-1" ?>
+<gui-definition>
+ <colors>
+ <background>#808080</background>
+ <text>#000000</text>
+ <header>#008000</header>
+ <link normal="#000080" visited="#800080"/>
+ </colors>
+ <rowsPerPage>15</rowsPerPage>
+</gui-definition>
+]]></source>
+ <p>
+ To make this XML document part of our global configuration we have to
+ modify our configuration definition file to also include the new file.
For
+ XML documents the element <code><xml></code> can be used so that we
+ ave now:
+ </p>
+ <source><![CDATA[
+<?xml version="1.0" encoding="ISO-8859-1" ?>
+
+<configuration>
+ <properties fileName="usergui.properties"/>
+ <xml fileName="gui.xml"/>
+</configuration>
+]]></source>
+ <p>
+ The code for setting up the <code>DefaultConfigurationBuilder</code>
+ object remains the same. From the <code>Configuration</code> object
+ returned by the factory the new properties can be accessed in the usual
+ way.
+ </p>
+ <p>
+ There is one problem with this example configuration setup: The
+ <code>color.background</code> property is defined in both the properties
+ and the XML file, and - to make things worse - with different values.
+ Which value will be returned by a call to <code>getString()</code>?
+ </p>
+ <p>
+ The answer is that the configuration sources are searched in the order
+ they are defined in the configuration definition file. Here the
properties
+ file is included first, then comes the XML file. Because the
+ <code>color.background</code> property can be found in the properties
file
+ the value specified there will be returned (which happens to be
+ <code>#FFFFFF</code>).
+ </p>
+ <p>
+ It might not be obvious why it makes sense to define the value of one and
+ the same property in multiple configuration sources. But consider the
+ following scenario: An application comes with a set of default properties
+ and allows the user to override some or all of them. This can now easily
+ be realized by saving the user's settings in one file and the default
+ settings in another. Then in the configuration definition file the file
+ with the user settings is included first and after that the file with the
+ default values. The application code that queries these settings needs no
+ be aware whether a property was overriden by the user.
<code>DefaultConfigurationBuilder</code>
+ takes care that properties defined in the first file (the user file) are
+ found; other properties which the user has not changed will still be
+ returned from the second file (the defaults file).
+ </p>
+ </subsection>
+
+ <subsection name="Optional configuration sources">
+ <p>
+ The example above with two configuration sources - one for user settings
+ and one with default values - raises an interesting question: What
happens
+ if the user has not defined specific properties yet? Or what if a new
user
+ starts our application for the first time and thus no user specific
+ properties exist?
+ </p>
+ <p>
+ The default behavior of <code>DefaultConfigurationBuilder</code> is to
+ throw a <code>ConfigurationException</code> exception if one of the
sources
+ defined in the configuration definition file cannot be loaded. For our
+ example this behavior is not desired: the properties file with specific
user
+ settings is not required. If it cannot be loaded, the example application
+ should still work because a complete set of configuration properties is
+ defined in the second file.
+ </p>
+ <p>
+ <code>DefaultConfigurationBuilder</code> supports such optional
configuration
+ sources. For this purpose in the definition of a configuration source the
+ <code>config-optional</code> attribute can be placed. An example of this
+ is shown below:
+ </p>
+ <source><![CDATA[
+<?xml version="1.0" encoding="ISO-8859-1" ?>
+
+<configuration>
+ <properties fileName="usersettings.properties" config-optional="true"/>
+ <properties fileName="default.properties"/>
+</configuration>
+]]></source>
+ <p>
+ In this configuration definition file the first properties file with user
+ specific settings is marked as optional. This means that if it cannot be
+ loaded, <code>DefaultConfigurationBuilder</code> will not throw an
exception,
+ but only write a warning message to its logger. Note that the
+ <code>config-optional</code> attribute is absent for the second
properties
+ file. Thus it is mandatory, and the <code>getConfiguration()</code>
method
+ of <code>DefaultConfigurationBuilder</code> would throw an exception if
it
+ could not be found.
+ </p>
+ </subsection>
+
+ <subsection name="Union configuration">
+ <p>
+ In an earlier section about the configuration definition file for
+ <code>DefaultConfigurationBuilder</code> it was stated that configuration
+ files included first can override properties in configuraton files
+ included later, and an example use case for this behaviour was given.
There
+ may be cases when there are other requirements.
+ </p>
+ <p>
+ Let's continue the example with the application that somehow process
+ database tables and that reads the definitions of the affected tables
from
+ its configuration. This example and the corresponding XML configuration
+ files were introduced in the section about <a
href="howto_xml.html">XMLConfiguration</a>.
+ Now consider that this application grows larger and must be maintained by
+ a team of developers. Each developer works on a separated set of tables.
+ In such a scenario it would be problematic if the definitions for all
+ tables would be kept in a single file. It can be expected that this file
+ needs to be changed very often and thus can be a bottleneck for team
+ development when it is nearly steadily checked out. It would be much
better
+ if each developer had an associated file with table definitions and all
+ these information could be linked together at the end.
+ </p>
+ <p>
+ <code>DefaultConfigurationBuilder</code> provides support for such a use
case,
+ too. It is possible to specify in the configuration definition file that
+ from a set of configuration sources a logic union configuration is to be
+ constructed. Then all properties defined in the provided sources are
+ collected and can be accessed as if they had been defined in a single
source.
+ To demonstrate this feature let us assume that a developer of the
database
+ application has defined a specific XML file with a table definition named
+ <code>tasktables.xml</code>:
+ </p>
+ <source><![CDATA[
+<?xml version="1.0" encoding="ISO-8859-1" ?>
+
+<config>
+ <table tableType="application">
+ <name>tasks</name>
+ <fields>
+ <field>
+ <name>taskid</name>
+ <type>long</type>
+ </field>
+ <field>
+ <name>name</name>
+ <type>java.lang.String</type>
+ </field>
+ <field>
+ <name>description</name>
+ <type>java.lang.String</type>
+ </field>
+ <field>
+ <name>responsibleID</name>
+ <type>long</type>
+ </field>
+ <field>
+ <name>creatorID</name>
+ <type>long</type>
+ </field>
+ <field>
+ <name>startDate</name>
+ <type>java.util.Date</type>
+ </field>
+ <field>
+ <name>endDate</name>
+ <type>java.util.Date</type>
+ </field>
+ </fields>
+ </table>
+</config>
+]]></source>
+ <p>
+ This file defines the structure of an additional table, which should be
+ added to the so far existing table definitions. To achieve this the
+ configuration definition file has to be changed: A new section is added
+ that contains the include elements of all configuration sources which
+ are to be combined.
+ </p>
+ <source><![CDATA[
+<?xml version="1.0" encoding="ISO-8859-1" ?>
+<!-- Configuration definition file that demonstrates the
+ override and additional sections -->
+
+<configuration>
+ <override>
+ <properties fileName="usergui.properties"/>
+ <xml fileName="gui.xml"/>
+ </override>
+
+ <additional>
+ <xml fileName="tables.xml"/>
+ <xml fileName="tasktables.xml" config-at="tables"/>
+ </additional>
+</configuration>
+]]></source>
+ <p>
+ Compared to the older versions of this file some changes have been done.
+ One major difference is that the elements for including configuration
+ sources are no longer direct children of the root element, but are now
+ contained in either an <code><override></code> or
<code><additional></code>
+ section. The names of these sections already imply their purpose.
+ </p>
+ <p>
+ The <code>override</code> section is not strictly necessary. Elements in
+ this section are treated as if they were children of the root element,
i.e.
+ properties in the included configuration sources override properties in
+ sources included later. So the <code><override></code> tags could
have
+ been ommitted, but for the sake of clearity it is recommended to use them
+ if there is also an <code><additional></code> section.
+ </p>
+ <p>
+ It is the <code><additonal></code> section that introduces a new
behaviour.
+ All configuration sources listed here are combined to a union
configuration.
+ In our example we have put two <code>xml</code> elements in this area
+ that load the available files with database table definitions. The syntax
+ of elements in the <code>additional</code> section is analogous to the
+ syntax described so far. In this example the <code>config-at</code>
+ attribute is introduced. It specifies the position in the logic union
+ configuration where the included properties are to be added. Here it is
set
+ for the second element to the value <em>tables</em>. This is because the
+ file starts with a <code><table></code> element, but to be
compatible
+ with the other table definition file it should be accessable under the
key
+ <code>tables.table</code>.
+ </p>
+ <p>
+ After these modifications have been performed, the configuration obtained
+ from <code>DefaultConfigurationBuilder</code> allows access to three
database
+ tables. A call of <code>config.getString("tables.table(2).name");</code>
+ results in a value of <em>tasks</em>. In an analogous way it is possible
+ to retrieve the fields of the third table.
+ </p>
+ <p>
+ Note that it is also possible to override properties defined in an
+ <code>additonal</code> section. This can be done by placing a
configuration
+ source in the <code>override</code> section that defines properties that
+ are also defined in one of the sources listed in the
<code>additional</code>
+ section. The example does not make use of that. Note also that the order
of
+ the <code>override</code> and <code>additional</code> sections in a
+ configuration definition file does not matter. Sources in an
<code>override</code>
+ section are always treated with higher priority (otherwise they could not
+ override the values of other sources).
+ </p>
+ </subsection>
+
+ <subsection name="Configuration definition file reference">
+ <p>
+ Configuration definition files are XML documents telling
+ <code>DefaultConfigurationBuilder</code> which configuration sources to
+ load and how to process them in order to create the resulting combined
+ configuration.
</p>
<p>
<strong>Overall structure of a configuration definition file</strong>
@@ -117,27 +404,60 @@
<strong>Declaring configuration sources</strong>
</p>
<p>
- The <code>override</code> and <code>additional</code> sections should
look
- familar to users that have already worked with
- <code>ConfigurationFactory</code>. They have the exact same purpose here,
- i.e. they contain declarations for the configuration sources to be
- embedded. For compatibility reasons it is also allowed to declare
+ The <code>override</code> and <code>additional</code> sections have
already
+ been introduced when the basics of
<code>DefaultConfigurationBuilder</code>
+ were discussed. They contain declarations for the configuration sources
to be
+ embedded. For convenience reasons it is also possible to declare
configuration sources outside these sections; they are then treated as if
they were placed inside the <code>override</code> section.
</p>
<p>
Each declaration of a configuration source is represented by an XML
- element whose name determines the type of the configuration source (e.g.
- <code>properties</code> for properties files, or <code>xml</code> for
- XML documents). Per default all configuration types are supported that
- are also allowed for <code>ConfigurationFactory</code>. A list of all
- supported tags can be found
- <a href="howto_configurationfactory.html#Configuration definition file
reference">here</a>.
- In addition to the default tags provided by
<code>ConfigurationFactory</code>
- <code>DefaultConfigurationBuilder</code> knows the following tags:
+ element whose name determines the type of the configuration source.
+ Attributes or nested elements can be used to provide additional
+ configuration options for the sources to be included (e.g. a name of a
+ file to be loaded or a reloading strategy). Below is a list of all
+ tags which can be used out of the box:
</p>
<p>
<dl>
+ <dt>properties</dt>
+ <dd>With this element properties files can be included. The name of
+ the file to load is specified using the <code>fileName</code>
+ attribute. Which configuration class is created by this tag
+ depends on the extension of the file to load: If the extension
+ is ".xml", a <code>XMLPropertiesConfiguration</code> object is
+ created, which is able to process the XML properties format
+ introduced in Java 5.0. Otherwise a
<code>PropertiesConfiguration</code>
+ object is created, the default reader for properties files.</dd>
+ <dt>xml</dt>
+ <dd>The <code>xml</code> element can be used to load XML configuration
+ files. It also uses the <code>fileName</code> attribute to
+ determine the name of the file to load and creates an instance
+ of <code>XMLConfiguration</code>.</dd>
+ <dt>jndi</dt>
+ <dd>As the name implies, with this element JNDI resources can be
+ included in the resulting configuration. Under the hood this is
+ done by an instance of the <code>JNDIConfiguration</code>
+ class. The <code>prefix</code> attribute can be used to
+ select a subset of the JNDI tree.</dd>
+ <dt>plist</dt>
+ <dd>The <code>plist</code> element allows to embedd configuration
+ files in the NeXT / OpenStep or Mac OS X format. Again the
+ name of the file to load is specified through the
+ <code>fileName</code> attribute. If a XML file is specified,
+ a <code>XMLPropertyListConfiguration</code> object is created
+ to process the file. Otherwise this task is delegated to a
+ <code>PropertyListConfiguration</code> instance.</dd>
+ <dt>system</dt>
+ <dd>With this element an instance of <code>SystemConfiguration</code>
+ is added to the resulting configuration allowing access to
+ system properties. <em>Note:</em> Using this element system properties
+ are directly made available. Alternatively the
+ interpolation features introduced in version 1.4 (see
+ <a href="howto_basicfeatures.html#Variable_Interpolation">
+ Variable Interpolation</a> for more details) can be used for
referencing
+ system properties.</dd>
<dt>configuration</dt>
<dd>The <code>configuration</code> tag allows other configuration
definition files to be included. This makes it possible to nest these
@@ -176,7 +496,7 @@
declarations are indeed
<a href="howto_beans.html#Declaring and Creating Beans">Bean
declarations</a>. That means they can have attributes matching simple
- properties of the configuration object to create and sub elements
+ properties of the configuration object to create, and sub elements
matching complex properties. The following example fragment shows how
complex initialization can be performed in a configuration declaration:
</p>
@@ -267,14 +587,12 @@
</table>
</p>
<p>
- The <code>config-at</code> and <code>config-optional</code> attributes
- have the same meaning as the <code>at</code> and <code>optional</code>
- attributes for <code>ConfigurationFactory</code>. For compatibility
- reasons the old attributes without the <code>config-</code> prefix are
- still supported. Note that the <code>config-at</code> is now allowed for
- override configurations, too (<code>ConfigurationFactory</code> evaluated
- the <code>at</code> attribute only for configuration declarations in the
- <code>additional</code> section).
+ <em>Note:</em> In older versions of Commons Configuration the attributes
+ <code>config-at</code> and <code>config-optional</code> were named
+ <code>at</code> and <code>optional</code> respective. They have been
+ renamed in order to avoid possible name clashes with property names for
+ configuration sources. However, for reasons of backwards compatibility,
+ the old attribute names can still be used.
</p>
<p>
Another useful feature is the built-in support for interpolation (i.e.
@@ -308,9 +626,11 @@
</configuration>
]]></source>
<p>
- This example differs from the previous one by allowing CONFIG_FILE, and
other
- properties, to be defined in a properties file and added to the system
- properties before the configuration is constructed.
+ This example differs from the previous one by the
<code>systemProperties</code>
+ attribute added to the root element. It causes the specified to be read
+ and all properties defined therein to be added to the system properties.
+ So properties like <em>CONFIG_FILE</em> can be defined in a properties
+ file and are then treated as if they were system properties.
</p>
<p>
<strong>The header section</strong>
@@ -349,7 +669,7 @@
The <code>result</code> element points to the bean declaration for the
resulting combined configuration. In this example we set some attributes
and initialize the node combiner (which is not necessary because the
- default override combiner is specified) and the expression engine to be
+ default override combiner is specified), and the expression engine to be
used. Note that the <code>config-class</code> attribute makes it
possible to inject custom classes for the resulting configuration or the
node combiner.
@@ -360,12 +680,20 @@
correctly. More information can be found in the section about
<a href="howto_combinedconfiguration.html#Node combiners">Node
combiners</a>.
</p>
+ <p>
+ <em>Note:</em> From time to time the question is raised whether there is
a
+ document type definition or a schema defining exactly the structure of a
+ configuration definition file. Frankly, the answer is no. This is due to
+ the fact that the format is extensible. As will be shown below, it is
+ possible to register yout own tags in order to embedd custom
configuration
+ sources.
+ </p>
</subsection>
-
+
<subsection name="An example">
<p>
- After all that theory let's go through an example! We start with the
- configuration definition file that looks like the following:
+ After all that theory let's go through a more complex example! We start
+ with the configuration definition file that looks like the following:
</p>
<source><![CDATA[
<?xml version="1.0" encoding="ISO-8859-1" ?>