001: /*
002: * Licensed to the Apache Software Foundation (ASF) under one or more
003: * contributor license agreements. See the NOTICE file distributed with
004: * this work for additional information regarding copyright ownership.
005: * The ASF licenses this file to You under the Apache License, Version 2.0
006: * (the "License"); you may not use this file except in compliance with
007: * the License. You may obtain a copy of the License at
008: *
009: * http://www.apache.org/licenses/LICENSE-2.0
010: *
011: * Unless required by applicable law or agreed to in writing, software
012: * distributed under the License is distributed on an "AS IS" BASIS,
013: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014: * See the License for the specific language governing permissions and
015: * limitations under the License.
016: */
017: package org.apache.commons.configuration.beanutils;
018:
019: import java.util.Map;
020:
021: import org.apache.commons.configuration.HierarchicalConfiguration;
022: import org.apache.commons.configuration.tree.ConfigurationNode;
023:
024: import junit.framework.TestCase;
025:
026: /**
027: * Test class for XMLBeanDeclaration.
028: *
029: * @since 1.3
030: * @author Oliver Heger
031: * @version $Id: TestXMLBeanDeclaration.java 439648 2006-09-02 20:42:10Z oheger $
032: */
033: public class TestXMLBeanDeclaration extends TestCase {
034: /** An array with some test properties. */
035: static final String[] TEST_PROPS = { "firstName", "lastName",
036: "department", "age", "hobby" };
037:
038: /** An array with the values for the test properties. */
039: static final String[] TEST_VALUES = { "John", "Smith",
040: "Engineering", "42", "TV" };
041:
042: /** An array with the names of nested (complex) properties. */
043: static final String[] COMPLEX_PROPS = { "address", "car" };
044:
045: /** An array with the names of the classes of the complex properties. */
046: static final String[] COMPLEX_CLASSES = {
047: "org.apache.commons.configuration.test.AddressTest",
048: "org.apache.commons.configuration.test.CarTest" };
049:
050: /** An array with the property names of the complex properties. */
051: static final String[][] COMPLEX_ATTRIBUTES = {
052: { "street", "zip", "city", "country" },
053: { "brand", "color" } };
054:
055: /** An array with the values of the complex properties. */
056: static final String[][] COMPLEX_VALUES = {
057: { "Baker Street", "12354", "London", "UK" },
058: { "Bentley", "silver" } };
059:
060: /** Constant for the key with the bean declaration. */
061: static final String KEY = "myBean";
062:
063: /** Constant for the section with the variables.*/
064: static final String VARS = "variables.";
065:
066: /** Stores the object to be tested. */
067: XMLBeanDeclaration decl;
068:
069: /**
070: * Tests creating a declaration from a null node. This should cause an
071: * exception.
072: */
073: public void testInitFromNullNode() {
074: try {
075: decl = new XMLBeanDeclaration(
076: new HierarchicalConfiguration()
077: .configurationAt(null),
078: (ConfigurationNode) null);
079: fail("Could init declaration with null node!");
080: } catch (IllegalArgumentException iex) {
081: // ok
082: }
083: }
084:
085: /**
086: * Tests creating a declaration from a null configuration. This should cause
087: * an exception.
088: */
089: public void testInitFromNullConfiguration() {
090: try {
091: decl = new XMLBeanDeclaration(
092: (HierarchicalConfiguration) null);
093: fail("Could init declaration with null configuration!");
094: } catch (IllegalArgumentException iex) {
095: // ok
096: }
097: }
098:
099: /**
100: * Tests creating a declaration from a null configuration with a key. This
101: * should cause an exception.
102: */
103: public void testInitFromNullConfigurationAndKey() {
104: try {
105: decl = new XMLBeanDeclaration(null, KEY);
106: fail("Could init declaration with null configuration and key!");
107: } catch (IllegalArgumentException iex) {
108: // ok
109: }
110: }
111:
112: /**
113: * Tests creating a declaration from a null configuration with a node. This
114: * should cause an exception.
115: */
116: public void testInitFromNullConfigurationAndNode() {
117: try {
118: decl = new XMLBeanDeclaration(null,
119: new HierarchicalConfiguration().getRoot());
120: fail("Could init declaration with null configuration and node!");
121: } catch (IllegalArgumentException iex) {
122: // ok
123: }
124: }
125:
126: /**
127: * Tests fetching the bean's class name.
128: */
129: public void testGetBeanClassName() {
130: HierarchicalConfiguration config = new HierarchicalConfiguration();
131: config.addProperty(KEY + "[@config-class]", getClass()
132: .getName());
133: decl = new XMLBeanDeclaration(config, KEY);
134: assertEquals("Wrong class name", getClass().getName(), decl
135: .getBeanClassName());
136: }
137:
138: /**
139: * Tests fetching the bean's class name if it is undefined.
140: */
141: public void testGetBeanClassNameUndefined() {
142: decl = new XMLBeanDeclaration(new HierarchicalConfiguration());
143: assertNull(decl.getBeanClassName());
144: }
145:
146: /**
147: * Tests fetching the name of the bean factory.
148: */
149: public void testGetBeanFactoryName() {
150: HierarchicalConfiguration config = new HierarchicalConfiguration();
151: config.addProperty(KEY + "[@config-factory]", "myFactory");
152: decl = new XMLBeanDeclaration(config, KEY);
153: assertEquals("Wrong factory name", "myFactory", decl
154: .getBeanFactoryName());
155: }
156:
157: /**
158: * Tests fetching the name of the bean factory if it is undefined.
159: */
160: public void testGetBeanFactoryNameUndefined() {
161: decl = new XMLBeanDeclaration(new HierarchicalConfiguration());
162: assertNull(decl.getBeanFactoryName());
163: }
164:
165: /**
166: * Tests fetching the paramter for the bean factory.
167: */
168: public void testGetBeanFactoryParameter() {
169: HierarchicalConfiguration config = new HierarchicalConfiguration();
170: config.addProperty(KEY + "[@config-factoryParam]",
171: "myFactoryParameter");
172: decl = new XMLBeanDeclaration(config, KEY);
173: assertEquals("Wrong factory parameter", "myFactoryParameter",
174: decl.getBeanFactoryParameter());
175: }
176:
177: /**
178: * Tests fetching the paramter for the bean factory if it is undefined.
179: */
180: public void testGetBeanFactoryParameterUndefined() {
181: decl = new XMLBeanDeclaration(new HierarchicalConfiguration());
182: assertNull(decl.getBeanFactoryParameter());
183: }
184:
185: /**
186: * Tests if the bean's properties are correctly extracted from the
187: * configuration object.
188: */
189: public void testGetBeanProperties() {
190: HierarchicalConfiguration config = new HierarchicalConfiguration();
191: setupBeanDeclaration(config, KEY, TEST_PROPS, TEST_VALUES);
192: decl = new XMLBeanDeclaration(config, KEY);
193: checkProperties(decl, TEST_PROPS, TEST_VALUES);
194: }
195:
196: /**
197: * Tests obtaining the bean's properties when reserved attributes are
198: * involved. These should be ignored.
199: */
200: public void testGetBeanPropertiesWithReservedAttributes() {
201: HierarchicalConfiguration config = new HierarchicalConfiguration();
202: setupBeanDeclaration(config, KEY, TEST_PROPS, TEST_VALUES);
203: config.addProperty(KEY + "[@config-testattr]", "yes");
204: config.addProperty(KEY + "[@config-anothertest]", "this, too");
205: decl = new XMLBeanDeclaration(config, KEY);
206: checkProperties(decl, TEST_PROPS, TEST_VALUES);
207: }
208:
209: /**
210: * Tests fetching properties if none are defined.
211: */
212: public void testGetBeanPropertiesEmpty() {
213: decl = new XMLBeanDeclaration(new HierarchicalConfiguration());
214: Map props = decl.getBeanProperties();
215: assertTrue("Properties found", props == null || props.isEmpty());
216: }
217:
218: /**
219: * Tests fetching nested bean declarations.
220: */
221: public void testGetNestedBeanDeclarations() {
222: HierarchicalConfiguration config = new HierarchicalConfiguration();
223: setupBeanDeclaration(config, KEY, TEST_PROPS, TEST_VALUES);
224: for (int i = 0; i < COMPLEX_PROPS.length; i++) {
225: setupBeanDeclaration(config, KEY + '.' + COMPLEX_PROPS[i],
226: COMPLEX_ATTRIBUTES[i], COMPLEX_VALUES[i]);
227: config.addProperty(KEY + '.' + COMPLEX_PROPS[i]
228: + "[@config-class]", COMPLEX_CLASSES[i]);
229: }
230:
231: decl = new XMLBeanDeclaration(config, KEY);
232: checkProperties(decl, TEST_PROPS, TEST_VALUES);
233:
234: Map nested = decl.getNestedBeanDeclarations();
235: assertEquals("Wrong number of nested declarations",
236: COMPLEX_PROPS.length, nested.size());
237: for (int i = 0; i < COMPLEX_PROPS.length; i++) {
238: XMLBeanDeclaration d = (XMLBeanDeclaration) nested
239: .get(COMPLEX_PROPS[i]);
240: assertNotNull("No declaration found for "
241: + COMPLEX_PROPS[i], d);
242: checkProperties(d, COMPLEX_ATTRIBUTES[i], COMPLEX_VALUES[i]);
243: assertEquals("Wrong bean class", COMPLEX_CLASSES[i], d
244: .getBeanClassName());
245: }
246: }
247:
248: /**
249: * Tests fetching nested bean declarations if none are defined.
250: */
251: public void testGetNestedBeanDeclarationsEmpty() {
252: HierarchicalConfiguration config = new HierarchicalConfiguration();
253: setupBeanDeclaration(config, KEY, TEST_PROPS, TEST_VALUES);
254: decl = new XMLBeanDeclaration(config, KEY);
255: Map nested = decl.getNestedBeanDeclarations();
256: assertTrue("Found nested declarations", nested == null
257: || nested.isEmpty());
258: }
259:
260: /**
261: * Tests whether interpolation of bean properties works.
262: */
263: public void testGetInterpolatedBeanProperties() {
264: HierarchicalConfiguration config = new HierarchicalConfiguration();
265: String[] varValues = new String[TEST_PROPS.length];
266: for (int i = 0; i < TEST_PROPS.length; i++) {
267: varValues[i] = "${" + VARS + TEST_PROPS[i] + "}";
268: config.addProperty(VARS + TEST_PROPS[i], TEST_VALUES[i]);
269: }
270: setupBeanDeclaration(config, KEY, TEST_PROPS, varValues);
271: decl = new XMLBeanDeclaration(config, KEY);
272: checkProperties(decl, TEST_PROPS, TEST_VALUES);
273: }
274:
275: /**
276: * Tests constructing a bean declaration from an undefined key. This should
277: * cause an exception.
278: */
279: public void testInitFromUndefinedKey() {
280: HierarchicalConfiguration config = new HierarchicalConfiguration();
281: setupBeanDeclaration(config, KEY, TEST_PROPS, TEST_VALUES);
282: try {
283: decl = new XMLBeanDeclaration(config, "undefined_key");
284: fail("Could create declaration from an undefined key!");
285: } catch (IllegalArgumentException iex) {
286: // ok
287: }
288: }
289:
290: /**
291: * Tests constructing a bean declaration from a key, which is undefined when
292: * the optional flag is set. In this case an empty declaration should be
293: * created, which can be used for creating beans as long as a default class
294: * is provided.
295: */
296: public void testInitFromUndefinedKeyOptional() {
297: HierarchicalConfiguration config = new HierarchicalConfiguration();
298: setupBeanDeclaration(config, KEY, TEST_PROPS, TEST_VALUES);
299: decl = new XMLBeanDeclaration(config, "undefined_key", true);
300: assertNull("Found a bean class", decl.getBeanClassName());
301: }
302:
303: /**
304: * Tests constructing a bean declaration from a key with multiple values.
305: * This should cause an exception because keys must be unique.
306: */
307: public void testInitFromMultiValueKey() {
308: HierarchicalConfiguration config = new HierarchicalConfiguration();
309: config.addProperty(KEY, "myFirstKey");
310: config.addProperty(KEY, "mySecondKey");
311: try {
312: decl = new XMLBeanDeclaration(config, KEY);
313: fail("Could create declaration from multi-valued property!");
314: } catch (IllegalArgumentException iex) {
315: // ok
316: }
317: }
318:
319: /**
320: * Initializes a configuration object with a bean declaration. Under the
321: * specified key the given properties will be added.
322: *
323: * @param config the configuration to initialize
324: * @param key the key of the bean declaration
325: * @param names an array with the names of the properties
326: * @param values an array with the corresponding values
327: */
328: private void setupBeanDeclaration(HierarchicalConfiguration config,
329: String key, String[] names, String[] values) {
330: for (int i = 0; i < names.length; i++) {
331: config.addProperty(key + "[@" + names[i] + "]", values[i]);
332: }
333: }
334:
335: /**
336: * Checks the properties returned by a bean declaration.
337: *
338: * @param beanDecl the bean declaration
339: * @param names an array with the expected property names
340: * @param values an array with the expected property values
341: */
342: private void checkProperties(BeanDeclaration beanDecl,
343: String[] names, String[] values) {
344: Map props = beanDecl.getBeanProperties();
345: assertEquals("Wrong number of properties", names.length, props
346: .size());
347: for (int i = 0; i < names.length; i++) {
348: assertTrue("Property " + names[i] + " not contained", props
349: .containsKey(names[i]));
350: assertEquals("Wrong value for property " + names[i],
351: values[i], props.get(names[i]));
352: }
353: }
354: }
|