##### Coverage Report - org.apache.commons.configuration.SubnodeConfiguration

Classes in this File | Line Coverage | Branch Coverage | Complexity
SubnodeConfiguration |
100% | 18/18
100% | 2/2
| 1.6666666666666667;1,667

1 |  |
     /*
2 |  |
      * Licensed to the Apache Software Foundation (ASF) under one or more
3 |  |
      * contributor license agreements.  See the NOTICE file distributed with
4 |  |
      * this work for additional information regarding copyright ownership.
5 |  |
      * The ASF licenses this file to You under the Apache License, Version 2.0
6 |  |
      * (the "License"); you may not use this file except in compliance with
7 |  |
      * the License.  You may obtain a copy of the License at
8 |  |
      *
9 |  |
      *     http://www.apache.org/licenses/LICENSE-2.0
10 |  |
      *
11 |  |
      * Unless required by applicable law or agreed to in writing, software
12 |  |
      * distributed under the License is distributed on an "AS IS" BASIS,
13 |  |
      * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 |  |
      * See the License for the specific language governing permissions and
15 |  |
      * limitations under the License.
16 |  |
      */
17 |  |
     package org.apache.commons.configuration;
18 |  |
19 |  |
     import org.apache.commons.configuration.tree.ConfigurationNode;
20 |  |
21 |  |
     /**
22 |  |
      * <p>
23 |  |
      * A specialized hierarchical configuration class that wraps a single node of
24 |  |
      * its parent configuration.
25 |  |
      * </p>
26 |  |
      * <p>
27 |  |
      * Configurations of this type are initialized with a parent configuration and a
28 |  |
      * configuration node of this configuration. This node becomes the root node of
29 |  |
      * the subnode configuration. All property accessor methods are evaluated
30 |  |
      * relative to this root node. A good use case for a
31 |  |
      * <code>SubnodeConfiguration</code> is when multiple properties from a
32 |  |
      * specific sub tree of the whole configuration need to be accessed. Then a
33 |  |
      * <code>SubnodeConfiguration</code> can be created with the parent node of
34 |  |
      * the affected sub tree as root node. This allows for simpler property keys and
35 |  |
      * is also more efficient.
36 |  |
      * </p>
37 |  |
      * <p>
38 |  |
      * A subnode configuration and its parent configuration operate on the same
39 |  |
      * hierarchy of configuration nodes. So if modifications are performed at the
40 |  |
      * subnode configuration, these changes are immideately visible in the parent
41 |  |
      * configuration. Analogously will updates of the parent configuration affect
42 |  |
      * the subnode configuration if the sub tree spanned by the subnode
43 |  |
      * configuration's root node is involved.
44 |  |
      * </p>
45 |  |
      * <p>
46 |  |
      * When a subnode configuration is created, it inherits the settings of its
47 |  |
      * parent configuration, e.g. some flags like the
48 |  |
      * <code>throwExceptionOnMissing</code> flag or the settings for handling list
49 |  |
      * delimiters) or the expression engine. If these settings are changed later in
50 |  |
      * either the subnode or the parent configuration, the changes are not visible
51 |  |
      * for each other. So you could create a subnode configuration, change its
52 |  |
      * expression engine without affecting the parent configuration.
53 |  |
      * </p>
54 |  |
      * <p>
55 |  |
      * From its purpose this class is quite similar to
56 |  |
      * <code>{@link SubsetConfiguration}</code>. The difference is that a subset
57 |  |
      * configuration of a hierarchical configuration may combine multiple
58 |  |
      * configuration nodes from different sub trees of the configuration, while all
59 |  |
      * nodes in a subnode configuration belong to the same sub tree. If an
60 |  |
      * application can live with this limitation, it is recommended to use this
61 |  |
      * class instead of <code>SubsetConfiguration</code> because creating a subset
62 |  |
      * configuration is more expensive than creating a subnode configuration.
63 |  |
      * </p>
64 |  |
      *
65 |  |
      * @since 1.3
66 |  |
      * @author Oliver Heger
67 |  |
      * @version $Id: SubnodeConfiguration.java 439648 2006-09-02 20:42:10Z oheger $
68 |  |
      */
69 |  |
     public class SubnodeConfiguration extends HierarchicalConfiguration
70 |  |
     {
71 |  |
         /**
72 |  |
          * The serial version UID.
73 |  |
          */
74 |  |
         private static final long serialVersionUID = 3105734147019386480L;
75 |  |
76 |  |
         /** Stores the parent configuration. */
77 |  |
         private HierarchicalConfiguration parent;
78 |  |
79 |  |
         /**
80 |  |
          * Creates a new instance of <code>SubnodeConfiguration</code> and
81 |  |
          * initializes it with the parent configuration and the new root node.
82 |  |
          *
83 |  |
          * @param parent the parent configuration
84 |  |
          * @param root the root node of this subnode configuration
85 |  |
          */
86 |  |
         public SubnodeConfiguration(HierarchicalConfiguration parent, ConfigurationNode root)
87 | 190 |
         {
88 | 190 |
             if (parent == null)
89 |  |
             {
90 | 1 |
                 throw new IllegalArgumentException(
91 |  |
                         "Parent configuration must not be null!");
92 |  |
             }
93 | 189 |
             if (root == null)
94 |  |
             {
95 | 1 |
                 throw new IllegalArgumentException("Root node must not be null!");
96 |  |
             }
97 |  |
98 | 188 |
             setRootNode(root);
99 | 188 |
             this.parent = parent;
100 | 188 |
             initFromParent(parent);
101 | 188 |
         }
102 |  |
103 |  |
         /**
104 |  |
          * Returns the parent configuration of this subnode configuration.
105 |  |
          *
106 |  |
          * @return the parent configuration
107 |  |
          */
108 |  |
         public HierarchicalConfiguration getParent()
109 |  |
         {
110 | 411 |
             return parent;
111 |  |
         }
112 |  |
113 |  |
         /**
114 |  |
          * Returns a hierarchical configuration object for the given sub node.
115 |  |
          * This implementation will ensure that the returned
116 |  |
          * <code>SubnodeConfiguration</code> object will have the same parent than
117 |  |
          * this object.
118 |  |
          *
119 |  |
          * @param node the sub node, for which the configuration is to be created
120 |  |
          * @return a hierarchical configuration for this sub node
121 |  |
          */
122 |  |
         protected SubnodeConfiguration createSubnodeConfiguration(ConfigurationNode node)
123 |  |
         {
124 | 75 |
             return new SubnodeConfiguration(getParent(), node);
125 |  |
         }
126 |  |
127 |  |
         /**
128 |  |
          * Creates a new node. This task is delegated to the parent.
129 |  |
          *
130 |  |
          * @param name the node's name
131 |  |
          * @return the new node
132 |  |
          */
133 |  |
         protected Node createNode(String name)
134 |  |
         {
135 | 4 |
             return getParent().createNode(name);
136 |  |
         }
137 |  |
138 |  |
         /**
139 |  |
          * Initializes this subnode configuration from the given parent
140 |  |
          * configuration. This method is called by the constructor. It will copy
141 |  |
          * many settings from the parent.
142 |  |
          *
143 |  |
          * @param parentConfig the parent configuration
144 |  |
          */
145 |  |
         protected void initFromParent(HierarchicalConfiguration parentConfig)
146 |  |
         {
147 | 188 |
             setExpressionEngine(parentConfig.getExpressionEngine());
148 | 188 |
             setListDelimiter(parentConfig.getListDelimiter());
149 | 188 |
             setDelimiterParsingDisabled(parentConfig.isDelimiterParsingDisabled());
150 | 188 |
             setThrowExceptionOnMissing(parentConfig.isThrowExceptionOnMissing());
151 | 188 |
         }
152 |  |
153 |  |
         /**
154 |  |
          * Performs interpolation. This implementation will ask the parent
155 |  |
          * configuration to perform the interpolation so that variables can be
156 |  |
          * evaluated in the global context.
157 |  |
          *
158 |  |
          * @param value the value to be interpolated
159 |  |
          */
160 |  |
         protected Object interpolate(Object value)
161 |  |
         {
162 | 288 |
             return getParent().interpolate(value);
163 |  |
         }
164 |  |
     }