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  
18  package org.apache.commons.configuration.plist;
19  
20  import java.io.File;
21  import java.util.*;
22  
23  import junit.framework.TestCase;
24  import junitx.framework.ObjectAssert;
25  import junitx.framework.ArrayAssert;
26  import junitx.framework.ListAssert;
27  import org.apache.commons.configuration.FileConfiguration;
28  import org.apache.commons.configuration.Configuration;
29  import org.apache.commons.configuration.HierarchicalConfiguration;
30  import org.apache.commons.configuration.StrictConfigurationComparator;
31  import org.apache.commons.configuration.ConfigurationComparator;
32  
33  /***
34   * @author Emmanuel Bourg
35   * @version $Revision: 645568 $, $Date: 2008-04-07 17:37:45 +0200 (Mo, 07 Apr 2008) $
36   */
37  public class TestXMLPropertyListConfiguration extends TestCase
38  {
39      private FileConfiguration config;
40  
41      protected void setUp() throws Exception
42      {
43          config = new XMLPropertyListConfiguration();
44          config.setFileName("conf/test.plist.xml");
45          config.load();
46      }
47  
48      public void testString() throws Exception
49      {
50          assertEquals("'string' property", "value1", config.getString("string"));
51      }
52  
53      public void testInteger() throws Exception
54      {
55          assertEquals("'integer' property", 12345678900L, config.getLong("integer"));
56      }
57  
58      public void testReal() throws Exception
59      {
60          assertEquals("'real' property", -12.345, config.getDouble("real"), 0);
61      }
62  
63      public void testBoolean() throws Exception
64      {
65          assertEquals("'boolean1' property", true, config.getBoolean("boolean1"));
66          assertEquals("'boolean2' property", false, config.getBoolean("boolean2"));
67      }
68  
69      public void testDictionary()
70      {
71          assertEquals("1st element", "value1", config.getProperty("dictionary.key1"));
72          assertEquals("2nd element", "value2", config.getProperty("dictionary.key2"));
73          assertEquals("3rd element", "value3", config.getProperty("dictionary.key3"));
74      }
75  
76      public void testDate() throws Exception
77      {
78          Calendar calendar = Calendar.getInstance();
79          calendar.clear();
80          calendar.setTimeZone(TimeZone.getTimeZone("UTC"));
81          calendar.set(2005, Calendar.JANUARY, 1, 12, 0, 0);
82  
83          assertEquals("'date' property", calendar.getTime(), config.getProperty("date"));
84  
85          calendar.setTimeZone(TimeZone.getTimeZone("CET"));
86          calendar.set(2002, Calendar.MARCH, 22, 11, 30, 0);
87  
88          assertEquals("'date-gnustep' property", calendar.getTime(), config.getProperty("date-gnustep"));
89      }
90  
91      public void testSubset()
92      {
93          Configuration subset = config.subset("dictionary");
94          Iterator keys = subset.getKeys();
95  
96          String key = (String) keys.next();
97          assertEquals("1st key", "key1", key);
98          assertEquals("1st value", "value1", subset.getString(key));
99  
100         key = (String) keys.next();
101         assertEquals("2nd key", "key2", key);
102         assertEquals("2nd value", "value2", subset.getString(key));
103 
104         key = (String) keys.next();
105         assertEquals("3rd key", "key3", key);
106         assertEquals("3rd value", "value3", subset.getString(key));
107 
108         assertFalse("more than 3 properties founds", keys.hasNext());
109     }
110 
111     public void testArray()
112     {
113         Object array = config.getProperty("array");
114 
115         assertNotNull("array not found", array);
116         ObjectAssert.assertInstanceOf("the array element is not parsed as a List", List.class, array);
117         List list = config.getList("array");
118 
119         assertFalse("empty array", list.isEmpty());
120         assertEquals("size", 3, list.size());
121         assertEquals("1st element", "value1", list.get(0));
122         assertEquals("2nd element", "value2", list.get(1));
123         assertEquals("3rd element", "value3", list.get(2));
124     }
125 
126     public void testNestedArray()
127     {
128         String key = "nested-array";
129 
130         Object array = config.getProperty(key);
131 
132         // root array
133         assertNotNull("array not found", array);
134         ObjectAssert.assertInstanceOf("the array element is not parsed as a List", List.class, array);
135         List list = config.getList(key);
136 
137         assertFalse("empty array", list.isEmpty());
138         assertEquals("size", 2, list.size());
139 
140         // 1st array
141         ObjectAssert.assertInstanceOf("the array element is not parsed as a List", List.class, list.get(0));
142         List list1 = (List) list.get(0);
143         assertFalse("nested array 1 is empty", list1.isEmpty());
144         assertEquals("size", 2, list1.size());
145         assertEquals("1st element", "a", list1.get(0));
146         assertEquals("2nd element", "b", list1.get(1));
147 
148         // 2nd array
149         ObjectAssert.assertInstanceOf("the array element is not parsed as a List", List.class, list.get(1));
150         List list2 = (List) list.get(1);
151         assertFalse("nested array 2 is empty", list2.isEmpty());
152         assertEquals("size", 2, list2.size());
153         assertEquals("1st element", "c", list2.get(0));
154         assertEquals("2nd element", "d", list2.get(1));
155     }
156 
157     public void testDictionaryArray()
158     {
159         String key = "dictionary-array";
160 
161         Object array = config.getProperty(key);
162 
163         // root array
164         assertNotNull("array not found", array);
165         ObjectAssert.assertInstanceOf("the array element is not parsed as a List", List.class, array);
166         List list = config.getList(key);
167 
168         assertFalse("empty array", list.isEmpty());
169         assertEquals("size", 2, list.size());
170 
171         // 1st dictionary
172         ObjectAssert.assertInstanceOf("the dict element is not parsed as a Configuration", Configuration.class, list.get(0));
173         Configuration conf1 = (Configuration) list.get(0);
174         assertFalse("configuration 1 is empty", conf1.isEmpty());
175         assertEquals("configuration element", "bar", conf1.getProperty("foo"));
176 
177         // 2nd dictionary
178         ObjectAssert.assertInstanceOf("the dict element is not parsed as a Configuration", Configuration.class, list.get(1));
179         Configuration conf2 = (Configuration) list.get(1);
180         assertFalse("configuration 2 is empty", conf2.isEmpty());
181         assertEquals("configuration element", "value", conf2.getProperty("key"));
182     }
183 
184     public void testNested()
185     {
186         assertEquals("nested property", "value", config.getString("nested.node1.node2.node3"));
187     }
188 
189     public void testSave() throws Exception
190     {
191         File savedFile = new File("target/testsave.plist.xml");
192 
193         // remove the file previously saved if necessary
194         if (savedFile.exists())
195         {
196             assertTrue(savedFile.delete());
197         }
198 
199         // add an array of strings to the configuration
200         /*
201         config.addProperty("string", "value1");
202         List list = new ArrayList();
203         for (int i = 1; i < 5; i++)
204         {
205             list.add("value" + i);
206         }
207         config.addProperty("newarray", list);*/
208         // todo : investigate why the array structure of 'newarray' is lost in the saved file
209 
210         // add a map of strings
211         /*
212         Map map = new HashMap();
213         map.put("foo", "bar");
214         map.put("int", new Integer(123));
215         config.addProperty("newmap", map);
216         */
217         // todo : a Map added to a HierarchicalConfiguration should be decomposed as list of nodes
218 
219         // save the configuration
220         String filename = savedFile.getAbsolutePath();
221         config.save(filename);
222 
223         assertTrue("The saved file doesn't exist", savedFile.exists());
224 
225         // read the configuration and compare the properties
226         Configuration checkConfig = new XMLPropertyListConfiguration(new File(filename));
227 
228         Iterator it = config.getKeys();
229         while (it.hasNext())
230         {
231             String key = (String) it.next();
232             assertTrue("The saved configuration doesn't contain the key '" + key + "'", checkConfig.containsKey(key));
233 
234             Object value = checkConfig.getProperty(key);
235             if (value instanceof byte[])
236             {
237                 byte[] array = (byte[]) value;
238                 ArrayAssert.assertEquals("Value of the '" + key + "' property", (byte[]) config.getProperty(key), array);
239             }
240             else if (value instanceof List)
241             {
242                 List list1 = (List) config.getProperty(key);
243                 List list2 = (List) value;
244 
245                 assertEquals("The size of the list for the key '" + key + "' doesn't match", list1.size(), list2.size());
246 
247                 for (int i = 0; i < list2.size(); i++)
248                 {
249                     Object value1 = list1.get(i);
250                     Object value2 = list2.get(i);
251 
252                     if (value1 instanceof Configuration)
253                     {
254                         ConfigurationComparator comparator = new StrictConfigurationComparator();
255                         assertTrue("The dictionnary at index " + i + " for the key '" + key + "' doesn't match", comparator.compare((Configuration) value1, (Configuration) value2));
256                     }
257                     else
258                     {
259                         assertEquals("Element at index " + i + " for the key '" + key + "'", value1, value2);
260                     }
261                 }
262 
263                 ListAssert.assertEquals("Value of the '" + key + "' property", (List) config.getProperty(key), list1);
264             }
265             else
266             {
267                 assertEquals("Value of the '" + key + "' property", config.getProperty(key), checkConfig.getProperty(key));
268             }
269 
270         }
271     }
272 
273     /***
274      * Ensure that setProperty doesn't alter an array of byte
275      * since it's a first class type in plist file
276      */
277     public void testSetDataProperty() throws Exception
278     {
279         byte[] expected = new byte[]{1, 2, 3, 4};
280         XMLPropertyListConfiguration config = new XMLPropertyListConfiguration();
281         config.setProperty("foo", expected);
282         config.save("target/testdata.plist.xml");
283 
284         XMLPropertyListConfiguration config2 = new XMLPropertyListConfiguration("target/testdata.plist.xml");
285         Object array = config2.getProperty("foo");
286 
287         assertNotNull("data not found", array);
288         assertEquals("property type", byte[].class, array.getClass());
289         ArrayAssert.assertEquals(expected, (byte[]) array);
290     }
291 
292     /***
293      * Ensure that addProperty doesn't alter an array of byte
294      */
295     public void testAddDataProperty() throws Exception
296     {
297         byte[] expected = new byte[]{1, 2, 3, 4};
298         XMLPropertyListConfiguration config = new XMLPropertyListConfiguration();
299         config.addProperty("foo", expected);
300         config.save("target/testdata.plist.xml");
301 
302         XMLPropertyListConfiguration config2 = new XMLPropertyListConfiguration("target/testdata.plist.xml");
303         Object array = config2.getProperty("foo");
304 
305         assertNotNull("data not found", array);
306         assertEquals("property type", byte[].class, array.getClass());
307         ArrayAssert.assertEquals(expected, (byte[]) array);
308     }
309 
310     public void testInitCopy()
311 	{
312 		XMLPropertyListConfiguration copy = new XMLPropertyListConfiguration((HierarchicalConfiguration) config);
313 		StrictConfigurationComparator comp = new StrictConfigurationComparator();
314 		assertTrue("Configurations are not equal", comp.compare(config, copy));
315 	}
316 }