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.betwixt.io.read;
18  
19  import java.io.StringReader;
20  import java.io.StringWriter;
21  import java.util.Iterator;
22  
23  import org.apache.commons.betwixt.AbstractTestCase;
24  import org.apache.commons.betwixt.ElementDescriptor;
25  import org.apache.commons.betwixt.XMLBeanInfo;
26  import org.apache.commons.betwixt.XMLIntrospector;
27  import org.apache.commons.betwixt.io.BeanReader;
28  import org.apache.commons.betwixt.io.BeanWriter;
29  import org.apache.commons.betwixt.strategy.MappingDerivationStrategy;
30  import org.xml.sax.InputSource;
31  
32  /***
33   * @author <a href='http://commons.apache.org'>Apache Commons Team</a>, <a href='http://www.apache.org'>Apache Software Foundation</a>
34   */
35  public class TestBindTimeTypeMapping extends AbstractTestCase {
36      
37      
38      
39      public TestBindTimeTypeMapping(String testName) {
40          super(testName);
41      }
42  
43      //todo: note to self need to consider how the design of the introspection will work when you have strategy which takes 
44      // singular property which is not know until after the digestion
45      
46      public void testDefaultMappingDerivationStrategy() throws Exception {
47          XMLIntrospector xmlIntrospector = new XMLIntrospector();
48          XMLBeanInfo xmlBeanInfo = xmlIntrospector.introspect(Animals.class);
49          ElementDescriptor animalsDescriptor = xmlBeanInfo.getElementDescriptor();
50          assertEquals("Use bind time type", true, animalsDescriptor.isUseBindTimeTypeForMapping());
51          ElementDescriptor animalDescriptor = animalsDescriptor.getElementDescriptors()[0];
52          assertEquals("Use bind time type", true, animalDescriptor.isUseBindTimeTypeForMapping());
53      }
54      
55      public void testIntrospectionTimeMappingDerivationStrategy() throws Exception {
56          XMLIntrospector xmlIntrospector = new XMLIntrospector();
57          xmlIntrospector.getConfiguration().setMappingDerivationStrategy(MappingDerivationStrategy.USE_INTROSPECTION_TIME_TYPE);
58          XMLBeanInfo xmlBeanInfo = xmlIntrospector.introspect(Animals.class);
59          ElementDescriptor animalsDescriptor = xmlBeanInfo.getElementDescriptor();
60          assertEquals("Use introspection time type", false, animalsDescriptor.isUseBindTimeTypeForMapping());
61          ElementDescriptor animalDescriptor = animalsDescriptor.getElementDescriptors()[0];
62          assertEquals("Use introspection time type", false, animalDescriptor.isUseBindTimeTypeForMapping());
63      }
64  
65      public void testBindTypeMappingDerivationStrategy() throws Exception {
66          XMLIntrospector xmlIntrospector = new XMLIntrospector();
67          xmlIntrospector.getConfiguration().setMappingDerivationStrategy(MappingDerivationStrategy.USE_BIND_TIME_TYPE);
68          XMLBeanInfo xmlBeanInfo = xmlIntrospector.introspect(Animals.class);
69          ElementDescriptor animalsDescriptor = xmlBeanInfo.getElementDescriptor();
70          assertEquals("Use bind time type", true, animalsDescriptor.isUseBindTimeTypeForMapping());
71          ElementDescriptor animalDescriptor = animalsDescriptor.getElementDescriptors()[0];
72          assertEquals("Use bind time type", true, animalDescriptor.isUseBindTimeTypeForMapping());
73      }
74      
75      public void testBindTypeMappingDerivationDotBetwixt() throws Exception {
76          String mappingDocument="<?xml version='1.0'?><info>" +
77          		"<element name='pet-record'>" +
78          		"	<element name='pet' property='pet' mappingDerivation='bind'/>" +
79          		"</element>" +
80          		"</info>";
81          XMLIntrospector xmlIntrospector = new XMLIntrospector();
82          xmlIntrospector.getConfiguration().setMappingDerivationStrategy(MappingDerivationStrategy.USE_INTROSPECTION_TIME_TYPE);
83          XMLBeanInfo xmlBeanInfo = xmlIntrospector.introspect(PetBean.class, new InputSource(new StringReader(mappingDocument)));
84          ElementDescriptor petDescriptor = xmlBeanInfo.getElementDescriptor();
85          assertEquals("Use type from strategy", true, petDescriptor.isUseBindTimeTypeForMapping());
86          ElementDescriptor animalDescriptor = petDescriptor.getElementDescriptors()[0];
87          assertEquals("Use type from document", true, animalDescriptor.isUseBindTimeTypeForMapping());
88      }
89      
90      public void testIntrospectionTypeMappingDerivationDotBetwixt() throws Exception {
91          String mappingDocument="<?xml version='1.0'?><info>" +
92          		"<element name='pet-record'>" +
93          		"	<element name='pet' property='pet' mappingDerivation='introspection'/>" +
94          		"</element>" +
95          		"</info>";
96          XMLIntrospector xmlIntrospector = new XMLIntrospector();
97          xmlIntrospector.getConfiguration().setMappingDerivationStrategy(MappingDerivationStrategy.USE_BIND_TIME_TYPE);
98          XMLBeanInfo xmlBeanInfo = xmlIntrospector.introspect(PetBean.class, new InputSource(new StringReader(mappingDocument)));
99          ElementDescriptor petDescriptor = xmlBeanInfo.getElementDescriptor();
100         assertEquals("Use type from strategy", true, petDescriptor.isUseBindTimeTypeForMapping());
101         ElementDescriptor animalDescriptor = petDescriptor.getElementDescriptors()[0];
102         assertEquals("Use type from document", false, animalDescriptor.isUseBindTimeTypeForMapping());
103     }
104     
105     public void testMappingDerivationDotBetwixtAddDefaults() throws Exception {
106         String mappingDocument="<?xml version='1.0'?><info>" +
107         		"<element name='pet-record'>" +
108         		"	<element name='pet' property='pet' mappingDerivation='introspection'/>" +
109         		"   <addDefaults/>" +
110         		"</element>" +
111         		"</info>";
112         XMLIntrospector xmlIntrospector = new XMLIntrospector();
113         xmlIntrospector.getConfiguration().setMappingDerivationStrategy(MappingDerivationStrategy.USE_BIND_TIME_TYPE);
114         XMLBeanInfo xmlBeanInfo = xmlIntrospector.introspect(PetBean.class, new InputSource(new StringReader(mappingDocument)));
115         ElementDescriptor petDescriptor = xmlBeanInfo.getElementDescriptor();
116         assertEquals("Use type from strategy", true, petDescriptor.isUseBindTimeTypeForMapping());
117         ElementDescriptor animalDescriptor = petDescriptor.getElementDescriptors()[0];
118         assertEquals("Use type from document", false, animalDescriptor.isUseBindTimeTypeForMapping());
119         ElementDescriptor personDescriptor = petDescriptor.getElementDescriptors()[1];
120         assertEquals("Use type from document", true, personDescriptor.isUseBindTimeTypeForMapping());
121     }
122     
123     public void testBindTimeTypeWrite() throws Exception {
124         StringWriter out = new StringWriter();
125         out.write("<?xml version='1.0'?>");
126         
127         Animals animals = new Animals();
128         animals.addAnimal(new FerretBean("albino", "Lector"));
129         animals.addAnimal(new CatBean("Sam", "black"));
130         animals.addAnimal(new DogBean("Bobby"));
131        
132         BeanWriter writer = new BeanWriter(out);
133         writer.getXMLIntrospector().getConfiguration()
134         		.setMappingDerivationStrategy(MappingDerivationStrategy.USE_BIND_TIME_TYPE);
135         writer.getXMLIntrospector().getConfiguration()
136         		.setWrapCollectionsInElement(false);
137         writer.getBindingConfiguration().setMapIDs(false);
138         writer.write(animals);
139         
140         String expected = "<?xml version='1.0'?>" +
141         		"<Animals>" +
142         		"	<animal>" +
143         		"		<call>Dook</call><colour>albino</colour>" +
144         		"		<latinName>Mustela putoris furo</latinName><name>Lector</name>" +
145         		"	</animal>" +
146         		"	<animal>" +
147         		"		<call>Meow</call><colour>black</colour>" +
148         		"		<latinName>Felis catus</latinName><name>Sam</name>" +
149         		"	</animal>" +
150         		"	<animal>" +
151         		"		<breed>mongrol</breed><call>Woof</call><latinName>Canis familiaris</latinName>" +
152         		"		<name>Bobby</name><pedigree>false</pedigree>" +
153         		"	</animal>" +
154         		"</Animals>";
155         
156         xmlAssertIsomorphicContent(parseString(expected), parseString(out), true);
157     }
158     
159     public void testBindTimeTypeRead() throws Exception {
160         String xml = "<?xml version='1.0'?>" +
161 		"<Animals>" +
162 		"	<animal className='org.apache.commons.betwixt.io.read.FerretBean'>" +
163 		"		<call>Dook</call><colour>albino</colour>" +
164 		"		<latinName>Mustela putoris furo</latinName><name>Lector</name>" +
165 		"	</animal>" +
166 		"	<animal className='org.apache.commons.betwixt.io.read.CatBean'>" +
167 		"		<call>Meow</call><colour>black</colour>" +
168 		"		<latinName>Felis catus</latinName><name>Sam</name>" +
169 		"	</animal>" +
170 		"	<animal className='org.apache.commons.betwixt.io.read.DogBean'>" +
171 		"		<breed>mongrol</breed><call>Woof</call><latinName>Canis familiaris</latinName>" +
172 		"		<name>Bobby</name><pedigree>false</pedigree>" +
173 		"	</animal>" +
174 		"</Animals>";
175         
176         BeanReader reader = new BeanReader();
177         reader.getXMLIntrospector().getConfiguration()
178         		.setMappingDerivationStrategy(MappingDerivationStrategy.USE_BIND_TIME_TYPE);
179         reader.getXMLIntrospector().getConfiguration()
180 			.setWrapCollectionsInElement(false);
181         reader.getBindingConfiguration().setMapIDs(false);
182         
183         reader.registerBeanClass(Animals.class);
184         Animals animals = (Animals) reader.parse(new StringReader(xml));
185         assertEquals("Expexted three animals", 3, animals.size()); 
186         Iterator it=animals.getAnimals(); 
187         Animal animalOne = (Animal) it.next();
188         assertTrue("Expected ferret", animalOne instanceof FerretBean);
189         FerretBean ferretBean = (FerretBean) animalOne;
190         assertEquals("Latin name property mapped", "Mustela putoris furo" , ferretBean.getLatinName());
191         assertEquals("Call property mapped", "Dook" , ferretBean.getCall());
192         assertEquals("Colour property mapped", "albino", ferretBean.getColour());
193         assertEquals("Name property mapped", "Lector", ferretBean.getName());
194         Animal animalTwo = (Animal) it.next();
195         assertTrue("Expected cat", animalTwo instanceof CatBean);
196         CatBean catBean = (CatBean) animalTwo;
197         assertEquals("Latin name property mapped", "Felis catus" , catBean.getLatinName());
198         assertEquals("Call property mapped", "Meow" , catBean.getCall());
199         assertEquals("Colour property mapped", "black", catBean.getColour());
200         assertEquals("Name property mapped", "Sam", catBean.getName());
201         Animal animalThree = (Animal) it.next();
202         assertTrue("Expected dog", animalThree instanceof DogBean);
203         DogBean dogBean = (DogBean) animalThree;
204         assertEquals("Latin name property mapped", "Canis familiaris" , dogBean.getLatinName());
205         assertEquals("Call property mapped", "Woof" , dogBean.getCall());
206         assertEquals("Breed property mapped", "mongrol", dogBean.getBreed());
207         assertEquals("Name property mapped", "Bobby", dogBean.getName());
208     }
209     
210     public void testIntrospectionTimeTypeWrite() throws Exception {
211         StringWriter out = new StringWriter();
212         out.write("<?xml version='1.0'?>");
213         
214         Animals animals = new Animals();
215         animals.addAnimal(new FerretBean("albino", "Lector"));
216         animals.addAnimal(new CatBean("Sam", "black"));
217         animals.addAnimal(new DogBean("Bobby"));
218        
219         BeanWriter writer = new BeanWriter(out);
220         writer.getXMLIntrospector().getConfiguration()
221         		.setMappingDerivationStrategy(MappingDerivationStrategy.USE_INTROSPECTION_TIME_TYPE);
222         writer.getXMLIntrospector().getConfiguration()
223         		.setWrapCollectionsInElement(false);
224         writer.getBindingConfiguration().setMapIDs(false);
225         writer.write(animals);
226         
227         String expected = "<?xml version='1.0'?><Animals>" +
228         		"	<animal><call>Dook</call><latinName>Mustela putoris furo</latinName></animal>" +
229         		"	<animal><call>Meow</call><latinName>Felis catus</latinName></animal>" +
230         		"	<animal><call>Woof</call><latinName>Canis familiaris</latinName></animal>" +
231         		"</Animals>";
232         
233         xmlAssertIsomorphicContent(parseString(expected), parseString(out), true);        
234     }
235     
236     public void testIntrospectionTimeTypeRead() throws Exception {
237         String xml = "<?xml version='1.0'?>" +
238 		"<Animals>" +
239 		"	<animal className='org.apache.commons.betwixt.io.read.FerretBean'>" +
240 		"		<call>Dook</call><colour>albino</colour>" +
241 		"		<latinName>Mustela putoris furo</latinName><name>Lector</name>" +
242 		"	</animal>" +
243 		"	<animal className='org.apache.commons.betwixt.io.read.CatBean'>" +
244 		"		<call>Meow</call><colour>black</colour>" +
245 		"		<latinName>Felis catus</latinName><name>Sam</name>" +
246 		"	</animal>" +
247 		"	<animal className='org.apache.commons.betwixt.io.read.DogBean'>" +
248 		"		<breed>mongrol</breed><call>Woof</call><latinName>Canis familiaris</latinName>" +
249 		"		<name>Bobby</name><pedigree>false</pedigree>" +
250 		"	</animal>" +
251 		"</Animals>";
252         
253         BeanReader reader = new BeanReader();
254         reader.getXMLIntrospector().getConfiguration()
255         		.setMappingDerivationStrategy(MappingDerivationStrategy.USE_INTROSPECTION_TIME_TYPE);
256         reader.getXMLIntrospector().getConfiguration()
257 			.setWrapCollectionsInElement(false);
258         reader.getBindingConfiguration().setMapIDs(false);
259         
260         reader.registerBeanClass(Animals.class);
261         Animals animals = (Animals) reader.parse(new StringReader(xml));
262         assertEquals("Expexted three animals", 3, animals.size()); 
263         Iterator it=animals.getAnimals(); 
264         Animal animalOne = (Animal) it.next();
265         assertTrue("Expected ferret", animalOne instanceof FerretBean);
266         FerretBean ferretBean = (FerretBean) animalOne;
267         assertEquals("Latin name property mapped", "Mustela putoris furo" , ferretBean.getLatinName());
268         assertEquals("Call property mapped", "Dook" , ferretBean.getCall());
269         assertNull("Colour property not mapped", ferretBean.getColour());
270         assertNull("Name property not mapped", ferretBean.getName());
271         Animal animalTwo = (Animal) it.next();
272         assertTrue("Expected cat", animalTwo instanceof CatBean);
273         CatBean catBean = (CatBean) animalTwo;
274         assertEquals("Latin name property mapped", "Felis catus" , catBean.getLatinName());
275         assertEquals("Call property mapped", "Meow" , catBean.getCall());
276         assertNull("Colour property not mapped", catBean.getColour());
277         assertNull("Name property not mapped", catBean.getName());
278         Animal animalThree = (Animal) it.next();
279         assertTrue("Expected dog", animalThree instanceof DogBean);
280         DogBean dogBean = (DogBean) animalThree;
281         assertEquals("Latin name property mapped", "Canis familiaris" , dogBean.getLatinName());
282         assertEquals("Call property mapped", "Woof" , dogBean.getCall());
283         assertNull("Breed property not mapped", dogBean.getBreed());
284         assertNull("Name property not mapped", dogBean.getName());
285     }
286 }