1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.springframework.beans;
18
19 import java.beans.PropertyEditorSupport;
20 import java.math.BigDecimal;
21 import java.math.BigInteger;
22 import java.util.ArrayList;
23 import java.util.Arrays;
24 import java.util.Collection;
25 import java.util.Collections;
26 import java.util.HashMap;
27 import java.util.HashSet;
28 import java.util.LinkedList;
29 import java.util.List;
30 import java.util.Map;
31 import java.util.Optional;
32 import java.util.Properties;
33 import java.util.Set;
34 import java.util.SortedMap;
35 import java.util.SortedSet;
36 import java.util.TreeMap;
37 import java.util.TreeSet;
38
39 import org.apache.commons.logging.LogFactory;
40 import org.junit.Test;
41
42 import org.springframework.beans.factory.annotation.Autowire;
43 import org.springframework.beans.propertyeditors.CustomNumberEditor;
44 import org.springframework.beans.propertyeditors.StringArrayPropertyEditor;
45 import org.springframework.beans.propertyeditors.StringTrimmerEditor;
46 import org.springframework.beans.support.DerivedFromProtectedBaseBean;
47 import org.springframework.core.convert.ConversionFailedException;
48 import org.springframework.core.convert.TypeDescriptor;
49 import org.springframework.core.convert.support.DefaultConversionService;
50 import org.springframework.core.convert.support.GenericConversionService;
51 import org.springframework.tests.Assume;
52 import org.springframework.tests.TestGroup;
53 import org.springframework.tests.sample.beans.BooleanTestBean;
54 import org.springframework.tests.sample.beans.ITestBean;
55 import org.springframework.tests.sample.beans.IndexedTestBean;
56 import org.springframework.tests.sample.beans.NumberTestBean;
57 import org.springframework.tests.sample.beans.TestBean;
58 import org.springframework.util.StopWatch;
59 import org.springframework.util.StringUtils;
60
61 import static org.hamcrest.Matchers.*;
62 import static org.junit.Assert.*;
63
64
65
66
67
68
69
70
71
72 public final class BeanWrapperTests extends AbstractConfigurablePropertyAccessorTests {
73
74 @Override
75 protected ConfigurablePropertyAccessor createAccessor(Object target) {
76 return new BeanWrapperImpl(target);
77 }
78
79 @Test
80 public void testNullNestedTypeDescriptor() {
81 Foo foo = new Foo();
82 BeanWrapperImpl wrapper = new BeanWrapperImpl(foo);
83 wrapper.setConversionService(new DefaultConversionService());
84 wrapper.setAutoGrowNestedPaths(true);
85 wrapper.setPropertyValue("listOfMaps[0]['luckyNumber']", "9");
86 assertEquals("9", foo.listOfMaps.get(0).get("luckyNumber"));
87 }
88
89 @Test
90 public void testNullNestedTypeDescriptor2() {
91 Foo foo = new Foo();
92 BeanWrapperImpl wrapper = new BeanWrapperImpl(foo);
93 wrapper.setConversionService(new DefaultConversionService());
94 wrapper.setAutoGrowNestedPaths(true);
95 Map<String, String> map = new HashMap<String, String>();
96 map.put("favoriteNumber", "9");
97 wrapper.setPropertyValue("list[0]", map);
98 assertEquals(map, foo.list.get(0));
99 }
100
101 @Test
102 public void testNullNestedTypeDescriptorWithNoConversionService() {
103 Foo foo = new Foo();
104 BeanWrapperImpl wrapper = new BeanWrapperImpl(foo);
105 wrapper.setAutoGrowNestedPaths(true);
106 wrapper.setPropertyValue("listOfMaps[0]['luckyNumber']", "9");
107 assertEquals("9", foo.listOfMaps.get(0).get("luckyNumber"));
108 }
109
110 @Test
111 public void testNullNestedTypeDescriptorWithBadConversionService() {
112 Foo foo = new Foo();
113 BeanWrapperImpl wrapper = new BeanWrapperImpl(foo);
114 wrapper.setConversionService(new GenericConversionService() {
115 @Override
116 public Object convert(Object source, TypeDescriptor sourceType, TypeDescriptor targetType) {
117 throw new ConversionFailedException(sourceType, targetType, source, null);
118 }
119 });
120 wrapper.setAutoGrowNestedPaths(true);
121 wrapper.setPropertyValue("listOfMaps[0]['luckyNumber']", "9");
122 assertEquals("9", foo.listOfMaps.get(0).get("luckyNumber"));
123 }
124
125
126 @Test
127 public void testReadableAndWritableForIndexedProperties() {
128 BeanWrapper bw = new BeanWrapperImpl(IndexedTestBean.class);
129
130 assertTrue(bw.isReadableProperty("array"));
131 assertTrue(bw.isReadableProperty("list"));
132 assertTrue(bw.isReadableProperty("set"));
133 assertTrue(bw.isReadableProperty("map"));
134 assertFalse(bw.isReadableProperty("xxx"));
135
136 assertTrue(bw.isWritableProperty("array"));
137 assertTrue(bw.isWritableProperty("list"));
138 assertTrue(bw.isWritableProperty("set"));
139 assertTrue(bw.isWritableProperty("map"));
140 assertFalse(bw.isWritableProperty("xxx"));
141
142 assertTrue(bw.isReadableProperty("array[0]"));
143 assertTrue(bw.isReadableProperty("array[0].name"));
144 assertTrue(bw.isReadableProperty("list[0]"));
145 assertTrue(bw.isReadableProperty("list[0].name"));
146 assertTrue(bw.isReadableProperty("set[0]"));
147 assertTrue(bw.isReadableProperty("set[0].name"));
148 assertTrue(bw.isReadableProperty("map[key1]"));
149 assertTrue(bw.isReadableProperty("map[key1].name"));
150 assertTrue(bw.isReadableProperty("map[key4][0]"));
151 assertTrue(bw.isReadableProperty("map[key4][0].name"));
152 assertTrue(bw.isReadableProperty("map[key4][1]"));
153 assertTrue(bw.isReadableProperty("map[key4][1].name"));
154 assertFalse(bw.isReadableProperty("array[key1]"));
155
156 assertTrue(bw.isWritableProperty("array[0]"));
157 assertTrue(bw.isWritableProperty("array[0].name"));
158 assertTrue(bw.isWritableProperty("list[0]"));
159 assertTrue(bw.isWritableProperty("list[0].name"));
160 assertTrue(bw.isWritableProperty("set[0]"));
161 assertTrue(bw.isWritableProperty("set[0].name"));
162 assertTrue(bw.isWritableProperty("map[key1]"));
163 assertTrue(bw.isWritableProperty("map[key1].name"));
164 assertTrue(bw.isWritableProperty("map[key4][0]"));
165 assertTrue(bw.isWritableProperty("map[key4][0].name"));
166 assertTrue(bw.isWritableProperty("map[key4][1]"));
167 assertTrue(bw.isWritableProperty("map[key4][1].name"));
168 assertFalse(bw.isWritableProperty("array[key1]"));
169 }
170
171 @Test
172 public void testTypeDeterminationForIndexedProperty() {
173 BeanWrapper bw = new BeanWrapperImpl(IndexedTestBean.class);
174 assertEquals(null, bw.getPropertyType("map[key0]"));
175
176 bw = new BeanWrapperImpl(IndexedTestBean.class);
177 bw.setPropertyValue("map[key0]", "my String");
178 assertEquals(String.class, bw.getPropertyType("map[key0]"));
179
180 bw = new BeanWrapperImpl(IndexedTestBean.class);
181 bw.registerCustomEditor(String.class, "map[key0]", new StringTrimmerEditor(false));
182 assertEquals(String.class, bw.getPropertyType("map[key0]"));
183 }
184
185 @Test
186 public void testGetterThrowsException() {
187 GetterBean gb = new GetterBean();
188 BeanWrapper bw = new BeanWrapperImpl(gb);
189 bw.setPropertyValue("name", "tom");
190 assertTrue("Set name to tom", gb.getName().equals("tom"));
191 }
192
193 @Test
194 public void testEmptyPropertyValuesSet() {
195 TestBean t = new TestBean();
196 int age = 50;
197 String name = "Tony";
198 t.setAge(age);
199 t.setName(name);
200 try {
201 BeanWrapper bw = new BeanWrapperImpl(t);
202 assertTrue("age is OK", t.getAge() == age);
203 assertTrue("name is OK", name.equals(t.getName()));
204 bw.setPropertyValues(new MutablePropertyValues());
205
206 assertTrue("age is OK", t.getAge() == age);
207 assertTrue("name is OK", name.equals(t.getName()));
208 }
209 catch (BeansException ex) {
210 fail("Shouldn't throw exception when everything is valid");
211 }
212 }
213
214 @Test
215 public void testAllValid() {
216 TestBean t = new TestBean();
217 String newName = "tony";
218 int newAge = 65;
219 String newTouchy = "valid";
220 try {
221 BeanWrapper bw = new BeanWrapperImpl(t);
222 MutablePropertyValues pvs = new MutablePropertyValues();
223 pvs.addPropertyValue(new PropertyValue("age", new Integer(newAge)));
224 pvs.addPropertyValue(new PropertyValue("name", newName));
225
226 pvs.addPropertyValue(new PropertyValue("touchy", newTouchy));
227 bw.setPropertyValues(pvs);
228 assertTrue("Validly set property must stick", t.getName().equals(newName));
229 assertTrue("Validly set property must stick", t.getTouchy().equals(newTouchy));
230 assertTrue("Validly set property must stick", t.getAge() == newAge);
231 }
232 catch (BeansException ex) {
233 fail("Shouldn't throw exception when everything is valid");
234 }
235 }
236
237 @Test
238 public void testBeanWrapperUpdates() {
239 TestBean t = new TestBean();
240 int newAge = 33;
241 try {
242 BeanWrapper bw = new BeanWrapperImpl(t);
243 t.setAge(newAge);
244 Object bwAge = bw.getPropertyValue("age");
245 assertTrue("Age is an integer", bwAge instanceof Integer);
246 int bwi = ((Integer) bwAge).intValue();
247 assertTrue("Bean wrapper must pick up changes", bwi == newAge);
248 }
249 catch (Exception ex) {
250 fail("Shouldn't throw exception when everything is valid");
251 }
252 }
253
254 @Test
255 public void testValidNullUpdate() {
256 TestBean t = new TestBean();
257 t.setName("Frank");
258 t.setSpouse(t);
259 BeanWrapper bw = new BeanWrapperImpl(t);
260 assertTrue("name is not null to start off", t.getName() != null);
261 bw.setPropertyValue("name", null);
262 assertTrue("name is now null", t.getName() == null);
263
264 assertTrue("spouse is not null to start off", t.getSpouse() != null);
265 bw.setPropertyValue("spouse", null);
266 assertTrue("spouse is now null", t.getSpouse() == null);
267 }
268
269 @Test
270 public void testIgnoringIndexedProperty() {
271 MutablePropertyValues values = new MutablePropertyValues();
272 values.add("toBeIgnored[0]", new Integer(42));
273 BeanWrapper bw = new BeanWrapperImpl(new Object());
274 bw.setPropertyValues(values, true);
275 }
276
277 @Test
278 public void testConvertPrimitiveToString() {
279 MutablePropertyValues values = new MutablePropertyValues();
280 values.add("name", new Integer(42));
281 TestBean tb = new TestBean();
282 BeanWrapper bw = new BeanWrapperImpl(tb);
283 bw.setPropertyValues(values);
284 assertEquals("42", tb.getName());
285 }
286
287 @Test
288 public void testConvertClassToString() {
289 MutablePropertyValues values = new MutablePropertyValues();
290 values.add("name", Integer.class);
291 TestBean tb = new TestBean();
292 BeanWrapper bw = new BeanWrapperImpl(tb);
293 bw.registerCustomEditor(String.class, new PropertyEditorSupport() {
294 @Override
295 public void setValue(Object value) {
296 super.setValue(value.toString());
297 }
298 });
299 bw.setPropertyValues(values);
300 assertEquals(Integer.class.toString(), tb.getName());
301 }
302
303 @Test
304 public void testBooleanObject() {
305 BooleanTestBean tb = new BooleanTestBean();
306 BeanWrapper bw = new BeanWrapperImpl(tb);
307
308 bw.setPropertyValue("bool2", "true");
309 assertTrue("Correct bool2 value", Boolean.TRUE.equals(bw.getPropertyValue("bool2")));
310 assertTrue("Correct bool2 value", tb.getBool2().booleanValue());
311
312 bw.setPropertyValue("bool2", "false");
313 assertTrue("Correct bool2 value", Boolean.FALSE.equals(bw.getPropertyValue("bool2")));
314 assertTrue("Correct bool2 value", !tb.getBool2().booleanValue());
315
316 }
317
318 @Test
319 public void testNumberObjects() {
320 NumberTestBean tb = new NumberTestBean();
321 BeanWrapper bw = new BeanWrapperImpl(tb);
322
323 try {
324 bw.setPropertyValue("short2", "2");
325 bw.setPropertyValue("int2", "8");
326 bw.setPropertyValue("long2", "6");
327 bw.setPropertyValue("bigInteger", "3");
328 bw.setPropertyValue("float2", "8.1");
329 bw.setPropertyValue("double2", "6.1");
330 bw.setPropertyValue("bigDecimal", "4.0");
331 }
332 catch (BeansException ex) {
333 fail("Should not throw BeansException: " + ex.getMessage());
334 }
335
336 assertTrue("Correct short2 value", new Short("2").equals(bw.getPropertyValue("short2")));
337 assertTrue("Correct short2 value", new Short("2").equals(tb.getShort2()));
338 assertTrue("Correct int2 value", new Integer("8").equals(bw.getPropertyValue("int2")));
339 assertTrue("Correct int2 value", new Integer("8").equals(tb.getInt2()));
340 assertTrue("Correct long2 value", new Long("6").equals(bw.getPropertyValue("long2")));
341 assertTrue("Correct long2 value", new Long("6").equals(tb.getLong2()));
342 assertTrue("Correct bigInteger value", new BigInteger("3").equals(bw.getPropertyValue("bigInteger")));
343 assertTrue("Correct bigInteger value", new BigInteger("3").equals(tb.getBigInteger()));
344 assertTrue("Correct float2 value", new Float("8.1").equals(bw.getPropertyValue("float2")));
345 assertTrue("Correct float2 value", new Float("8.1").equals(tb.getFloat2()));
346 assertTrue("Correct double2 value", new Double("6.1").equals(bw.getPropertyValue("double2")));
347 assertTrue("Correct double2 value", new Double("6.1").equals(tb.getDouble2()));
348 assertTrue("Correct bigDecimal value", new BigDecimal("4.0").equals(bw.getPropertyValue("bigDecimal")));
349 assertTrue("Correct bigDecimal value", new BigDecimal("4.0").equals(tb.getBigDecimal()));
350 }
351
352 @Test
353 public void testNumberCoercion() {
354 NumberTestBean tb = new NumberTestBean();
355 BeanWrapper bw = new BeanWrapperImpl(tb);
356
357 try {
358 bw.setPropertyValue("short2", new Integer(2));
359 bw.setPropertyValue("int2", new Long(8));
360 bw.setPropertyValue("long2", new BigInteger("6"));
361 bw.setPropertyValue("bigInteger", new Integer(3));
362 bw.setPropertyValue("float2", new Double(8.1));
363 bw.setPropertyValue("double2", new BigDecimal(6.1));
364 bw.setPropertyValue("bigDecimal", new Float(4.0));
365 }
366 catch (BeansException ex) {
367 fail("Should not throw BeansException: " + ex.getMessage());
368 }
369
370 assertTrue("Correct short2 value", new Short("2").equals(bw.getPropertyValue("short2")));
371 assertTrue("Correct short2 value", new Short("2").equals(tb.getShort2()));
372 assertTrue("Correct int2 value", new Integer("8").equals(bw.getPropertyValue("int2")));
373 assertTrue("Correct int2 value", new Integer("8").equals(tb.getInt2()));
374 assertTrue("Correct long2 value", new Long("6").equals(bw.getPropertyValue("long2")));
375 assertTrue("Correct long2 value", new Long("6").equals(tb.getLong2()));
376 assertTrue("Correct bigInteger value", new BigInteger("3").equals(bw.getPropertyValue("bigInteger")));
377 assertTrue("Correct bigInteger value", new BigInteger("3").equals(tb.getBigInteger()));
378 assertTrue("Correct float2 value", new Float("8.1").equals(bw.getPropertyValue("float2")));
379 assertTrue("Correct float2 value", new Float("8.1").equals(tb.getFloat2()));
380 assertTrue("Correct double2 value", new Double("6.1").equals(bw.getPropertyValue("double2")));
381 assertTrue("Correct double2 value", new Double("6.1").equals(tb.getDouble2()));
382 assertTrue("Correct bigDecimal value", new BigDecimal("4.0").equals(bw.getPropertyValue("bigDecimal")));
383 assertTrue("Correct bigDecimal value", new BigDecimal("4.0").equals(tb.getBigDecimal()));
384 }
385
386 @Test
387 public void testEnumByFieldName() {
388 EnumTester et = new EnumTester();
389 BeanWrapper bw = new BeanWrapperImpl(et);
390
391 bw.setPropertyValue("autowire", "BY_NAME");
392 assertEquals(Autowire.BY_NAME, et.getAutowire());
393
394 bw.setPropertyValue("autowire", " BY_TYPE ");
395 assertEquals(Autowire.BY_TYPE, et.getAutowire());
396
397 try {
398 bw.setPropertyValue("autowire", "NHERITED");
399 fail("Should have thrown TypeMismatchException");
400 }
401 catch (TypeMismatchException ex) {
402
403 }
404 }
405
406 @Test
407 public void testPropertiesProperty() throws Exception {
408 PropsTester pt = new PropsTester();
409 BeanWrapper bw = new BeanWrapperImpl(pt);
410 bw.setPropertyValue("name", "ptest");
411
412
413 String ps = "peace=war\nfreedom=slavery";
414 bw.setPropertyValue("properties", ps);
415
416 assertTrue("name was set", pt.name.equals("ptest"));
417 assertTrue("props non null", pt.props != null);
418 String freedomVal = pt.props.getProperty("freedom");
419 String peaceVal = pt.props.getProperty("peace");
420 assertTrue("peace==war", peaceVal.equals("war"));
421 assertTrue("Freedom==slavery", freedomVal.equals("slavery"));
422 }
423
424 @Test
425 public void testStringArrayProperty() throws Exception {
426 PropsTester pt = new PropsTester();
427 BeanWrapper bw = new BeanWrapperImpl(pt);
428
429 bw.setPropertyValue("stringArray", new String[] {"foo", "fi", "fi", "fum"});
430 assertTrue("stringArray length = 4", pt.stringArray.length == 4);
431 assertTrue("correct values", pt.stringArray[0].equals("foo") && pt.stringArray[1].equals("fi") &&
432 pt.stringArray[2].equals("fi") && pt.stringArray[3].equals("fum"));
433
434 List<String> list = new ArrayList<String>();
435 list.add("foo");
436 list.add("fi");
437 list.add("fi");
438 list.add("fum");
439 bw.setPropertyValue("stringArray", list);
440 assertTrue("stringArray length = 4", pt.stringArray.length == 4);
441 assertTrue("correct values", pt.stringArray[0].equals("foo") && pt.stringArray[1].equals("fi") &&
442 pt.stringArray[2].equals("fi") && pt.stringArray[3].equals("fum"));
443
444 Set<String> set = new HashSet<String>();
445 set.add("foo");
446 set.add("fi");
447 set.add("fum");
448 bw.setPropertyValue("stringArray", set);
449 assertTrue("stringArray length = 3", pt.stringArray.length == 3);
450 List<String> result = Arrays.asList(pt.stringArray);
451 assertTrue("correct values", result.contains("foo") && result.contains("fi") && result.contains("fum"));
452
453 bw.setPropertyValue("stringArray", "one");
454 assertTrue("stringArray length = 1", pt.stringArray.length == 1);
455 assertTrue("stringArray elt is ok", pt.stringArray[0].equals("one"));
456
457 bw.setPropertyValue("stringArray", null);
458 assertTrue("stringArray is null", pt.stringArray == null);
459 }
460
461 @Test
462 public void testStringArrayPropertyWithCustomStringEditor() throws Exception {
463 PropsTester pt = new PropsTester();
464 BeanWrapper bw = new BeanWrapperImpl(pt);
465 bw.registerCustomEditor(String.class, "stringArray", new PropertyEditorSupport() {
466 @Override
467 public void setAsText(String text) {
468 setValue(text.substring(1));
469 }
470 });
471
472 bw.setPropertyValue("stringArray", new String[] {"4foo", "7fi", "6fi", "5fum"});
473 assertTrue("stringArray length = 4", pt.stringArray.length == 4);
474 assertTrue("correct values", pt.stringArray[0].equals("foo") && pt.stringArray[1].equals("fi") &&
475 pt.stringArray[2].equals("fi") && pt.stringArray[3].equals("fum"));
476
477 List<String> list = new ArrayList<String>();
478 list.add("4foo");
479 list.add("7fi");
480 list.add("6fi");
481 list.add("5fum");
482 bw.setPropertyValue("stringArray", list);
483 assertTrue("stringArray length = 4", pt.stringArray.length == 4);
484 assertTrue("correct values", pt.stringArray[0].equals("foo") && pt.stringArray[1].equals("fi") &&
485 pt.stringArray[2].equals("fi") && pt.stringArray[3].equals("fum"));
486
487 Set<String> set = new HashSet<String>();
488 set.add("4foo");
489 set.add("7fi");
490 set.add("6fum");
491 bw.setPropertyValue("stringArray", set);
492 assertTrue("stringArray length = 3", pt.stringArray.length == 3);
493 List<String> result = Arrays.asList(pt.stringArray);
494 assertTrue("correct values", result.contains("foo") && result.contains("fi") && result.contains("fum"));
495
496 bw.setPropertyValue("stringArray", "8one");
497 assertTrue("stringArray length = 1", pt.stringArray.length == 1);
498 assertTrue("correct values", pt.stringArray[0].equals("one"));
499 }
500
501 @Test
502 public void testStringArrayPropertyWithStringSplitting() throws Exception {
503 PropsTester pt = new PropsTester();
504 BeanWrapperImpl bw = new BeanWrapperImpl(pt);
505 bw.useConfigValueEditors();
506 bw.setPropertyValue("stringArray", "a1,b2");
507 assertTrue("stringArray length = 2", pt.stringArray.length == 2);
508 assertTrue("correct values", pt.stringArray[0].equals("a1") && pt.stringArray[1].equals("b2"));
509 }
510
511 @Test
512 public void testStringArrayPropertyWithCustomStringDelimiter() throws Exception {
513 PropsTester pt = new PropsTester();
514 BeanWrapper bw = new BeanWrapperImpl(pt);
515 bw.registerCustomEditor(String[].class, "stringArray", new StringArrayPropertyEditor("-"));
516 bw.setPropertyValue("stringArray", "a1-b2");
517 assertTrue("stringArray length = 2", pt.stringArray.length == 2);
518 assertTrue("correct values", pt.stringArray[0].equals("a1") && pt.stringArray[1].equals("b2"));
519 }
520
521 @Test
522 public void testStringArrayAutoGrow() throws Exception {
523 StringArrayBean target = new StringArrayBean();
524 BeanWrapper bw = new BeanWrapperImpl(target);
525 bw.setAutoGrowNestedPaths(true);
526
527 bw.setPropertyValue("array[0]", "Test0");
528 assertEquals(1, target.getArray().length);
529
530 bw.setPropertyValue("array[2]", "Test2");
531 assertEquals(3, target.getArray().length);
532 assertTrue("correct values", target.getArray()[0].equals("Test0") && target.getArray()[1] == null &&
533 target.getArray()[2].equals("Test2"));
534 }
535
536 @Test
537 public void testPrimitiveArrayAutoGrow() throws Exception {
538 PrimitiveArrayBean target = new PrimitiveArrayBean();
539 BeanWrapper bw = new BeanWrapperImpl(target);
540 bw.setAutoGrowNestedPaths(true);
541
542 bw.setPropertyValue("array[0]", 1);
543 assertEquals(1, target.getArray().length);
544
545 bw.setPropertyValue("array[2]", 3);
546 assertEquals(3, target.getArray().length);
547 assertTrue("correct values", target.getArray()[0] == 1 && target.getArray()[1] == 0 &&
548 target.getArray()[2] == 3);
549 }
550
551 @Test
552 public void testStringPropertyWithCustomEditor() throws Exception {
553 TestBean tb = new TestBean();
554 BeanWrapper bw = new BeanWrapperImpl(tb);
555 bw.registerCustomEditor(String.class, "name", new PropertyEditorSupport() {
556 @Override
557 public void setValue(Object value) {
558 if (value instanceof String[]) {
559 setValue(StringUtils.arrayToDelimitedString(((String[]) value), "-"));
560 }
561 else {
562 super.setValue(value != null ? value : "");
563 }
564 }
565 });
566 bw.setPropertyValue("name", new String[] {});
567 assertEquals("", tb.getName());
568 bw.setPropertyValue("name", new String[] {"a1", "b2"});
569 assertEquals("a1-b2", tb.getName());
570 bw.setPropertyValue("name", null);
571 assertEquals("", tb.getName());
572 }
573
574 @Test
575 public void testIntArrayProperty() {
576 PropsTester pt = new PropsTester();
577 BeanWrapper bw = new BeanWrapperImpl(pt);
578
579 bw.setPropertyValue("intArray", new int[] {4, 5, 2, 3});
580 assertTrue("intArray length = 4", pt.intArray.length == 4);
581 assertTrue("correct values", pt.intArray[0] == 4 && pt.intArray[1] == 5 &&
582 pt.intArray[2] == 2 && pt.intArray[3] == 3);
583
584 bw.setPropertyValue("intArray", new String[] {"4", "5", "2", "3"});
585 assertTrue("intArray length = 4", pt.intArray.length == 4);
586 assertTrue("correct values", pt.intArray[0] == 4 && pt.intArray[1] == 5 &&
587 pt.intArray[2] == 2 && pt.intArray[3] == 3);
588
589 List<Object> list = new ArrayList<Object>();
590 list.add(new Integer(4));
591 list.add("5");
592 list.add(new Integer(2));
593 list.add("3");
594 bw.setPropertyValue("intArray", list);
595 assertTrue("intArray length = 4", pt.intArray.length == 4);
596 assertTrue("correct values", pt.intArray[0] == 4 && pt.intArray[1] == 5 &&
597 pt.intArray[2] == 2 && pt.intArray[3] == 3);
598
599 Set<Object> set = new HashSet<Object>();
600 set.add("4");
601 set.add(new Integer(5));
602 set.add("3");
603 bw.setPropertyValue("intArray", set);
604 assertTrue("intArray length = 3", pt.intArray.length == 3);
605 List<Integer> result = new ArrayList<Integer>();
606 result.add(new Integer(pt.intArray[0]));
607 result.add(new Integer(pt.intArray[1]));
608 result.add(new Integer(pt.intArray[2]));
609 assertTrue("correct values", result.contains(new Integer(4)) && result.contains(new Integer(5)) &&
610 result.contains(new Integer(3)));
611
612 bw.setPropertyValue("intArray", new Integer[] {new Integer(1)});
613 assertTrue("intArray length = 4", pt.intArray.length == 1);
614 assertTrue("correct values", pt.intArray[0] == 1);
615
616 bw.setPropertyValue("intArray", new Integer(1));
617 assertTrue("intArray length = 4", pt.intArray.length == 1);
618 assertTrue("correct values", pt.intArray[0] == 1);
619
620 bw.setPropertyValue("intArray", new String[] {"1"});
621 assertTrue("intArray length = 4", pt.intArray.length == 1);
622 assertTrue("correct values", pt.intArray[0] == 1);
623
624 bw.setPropertyValue("intArray", "1");
625 assertTrue("intArray length = 4", pt.intArray.length == 1);
626 assertTrue("correct values", pt.intArray[0] == 1);
627 }
628
629 @Test
630 public void testIntArrayPropertyWithCustomEditor() {
631 PropsTester pt = new PropsTester();
632 BeanWrapper bw = new BeanWrapperImpl(pt);
633 bw.registerCustomEditor(int.class, new PropertyEditorSupport() {
634 @Override
635 public void setAsText(String text) {
636 setValue(new Integer(Integer.parseInt(text) + 1));
637 }
638 });
639
640 bw.setPropertyValue("intArray", new int[] {4, 5, 2, 3});
641 assertTrue("intArray length = 4", pt.intArray.length == 4);
642 assertTrue("correct values", pt.intArray[0] == 4 && pt.intArray[1] == 5 &&
643 pt.intArray[2] == 2 && pt.intArray[3] == 3);
644
645 bw.setPropertyValue("intArray", new String[] {"3", "4", "1", "2"});
646 assertTrue("intArray length = 4", pt.intArray.length == 4);
647 assertTrue("correct values", pt.intArray[0] == 4 && pt.intArray[1] == 5 &&
648 pt.intArray[2] == 2 && pt.intArray[3] == 3);
649
650 bw.setPropertyValue("intArray", new Integer(1));
651 assertTrue("intArray length = 4", pt.intArray.length == 1);
652 assertTrue("correct values", pt.intArray[0] == 1);
653
654 bw.setPropertyValue("intArray", new String[] {"0"});
655 assertTrue("intArray length = 4", pt.intArray.length == 1);
656 assertTrue("correct values", pt.intArray[0] == 1);
657
658 bw.setPropertyValue("intArray", "0");
659 assertTrue("intArray length = 4", pt.intArray.length == 1);
660 assertTrue("correct values", pt.intArray[0] == 1);
661 }
662
663 @Test
664 public void testIntArrayPropertyWithStringSplitting() throws Exception {
665 PropsTester pt = new PropsTester();
666 BeanWrapperImpl bw = new BeanWrapperImpl(pt);
667 bw.useConfigValueEditors();
668 bw.setPropertyValue("intArray", "4,5");
669 assertTrue("intArray length = 2", pt.intArray.length == 2);
670 assertTrue("correct values", pt.intArray[0] == 4 && pt.intArray[1] == 5);
671 }
672
673 @Test
674 public void testIndividualAllValid() {
675 TestBean t = new TestBean();
676 String newName = "tony";
677 int newAge = 65;
678 String newTouchy = "valid";
679 try {
680 BeanWrapper bw = new BeanWrapperImpl(t);
681 bw.setPropertyValue("age", new Integer(newAge));
682 bw.setPropertyValue(new PropertyValue("name", newName));
683 bw.setPropertyValue(new PropertyValue("touchy", newTouchy));
684 assertTrue("Validly set property must stick", t.getName().equals(newName));
685 assertTrue("Validly set property must stick", t.getTouchy().equals(newTouchy));
686 assertTrue("Validly set property must stick", t.getAge() == newAge);
687 }
688 catch (BeansException ex) {
689 fail("Shouldn't throw exception when everything is valid");
690 }
691 }
692
693 @Test
694 public void test2Invalid() {
695 TestBean t = new TestBean();
696 String newName = "tony";
697 String invalidTouchy = ".valid";
698 try {
699 BeanWrapper bw = new BeanWrapperImpl(t);
700 MutablePropertyValues pvs = new MutablePropertyValues();
701 pvs.addPropertyValue(new PropertyValue("age", "foobar"));
702 pvs.addPropertyValue(new PropertyValue("name", newName));
703 pvs.addPropertyValue(new PropertyValue("touchy", invalidTouchy));
704 bw.setPropertyValues(pvs);
705 fail("Should throw exception when everything is valid");
706 }
707 catch (PropertyBatchUpdateException ex) {
708 assertTrue("Must contain 2 exceptions", ex.getExceptionCount() == 2);
709
710 assertTrue("Validly set property must stick", t.getName().equals(newName));
711 assertTrue("Invalidly set property must retain old value", t.getAge() == 0);
712 assertTrue("New value of dodgy setter must be available through exception",
713 ex.getPropertyAccessException("touchy").getPropertyChangeEvent().getNewValue().equals(invalidTouchy));
714 }
715 }
716
717 @Test
718 public void testPossibleMatches() {
719 TestBean tb = new TestBean();
720 try {
721 BeanWrapper bw = new BeanWrapperImpl(tb);
722 bw.setPropertyValue("ag", "foobar");
723 fail("Should throw exception on invalid property");
724 }
725 catch (NotWritablePropertyException ex) {
726
727 assertEquals(1, ex.getPossibleMatches().length);
728 assertEquals("age", ex.getPossibleMatches()[0]);
729 }
730 }
731
732 @Test
733 public void testTypeMismatch() {
734 TestBean t = new TestBean();
735 try {
736 BeanWrapper bw = new BeanWrapperImpl(t);
737 bw.setPropertyValue("age", "foobar");
738 fail("Should throw exception on type mismatch");
739 }
740 catch (TypeMismatchException ex) {
741
742 }
743 }
744
745 @Test
746 public void testEmptyValueForPrimitiveProperty() {
747 TestBean t = new TestBean();
748 try {
749 BeanWrapper bw = new BeanWrapperImpl(t);
750 bw.setPropertyValue("age", "");
751 fail("Should throw exception on type mismatch");
752 }
753 catch (TypeMismatchException ex) {
754
755 }
756 catch (Exception ex) {
757 fail("Shouldn't throw exception other than Type mismatch");
758 }
759 }
760
761 @Test
762 public void testSetPropertyValuesIgnoresInvalidNestedOnRequest() {
763 ITestBean rod = new TestBean();
764 MutablePropertyValues pvs = new MutablePropertyValues();
765 pvs.addPropertyValue(new PropertyValue("name", "rod"));
766 pvs.addPropertyValue(new PropertyValue("graceful.rubbish", "tony"));
767 pvs.addPropertyValue(new PropertyValue("more.garbage", new Object()));
768 BeanWrapper bw = new BeanWrapperImpl(rod);
769 bw.setPropertyValues(pvs, true);
770 assertTrue("Set valid and ignored invalid", rod.getName().equals("rod"));
771 try {
772
773 bw.setPropertyValues(pvs, false);
774 fail("Shouldn't have ignored invalid updates");
775 }
776 catch (NotWritablePropertyException ex) {
777
778 }
779 }
780
781 @Test
782 public void testGetNestedProperty() {
783 ITestBean rod = new TestBean("rod", 31);
784 ITestBean kerry = new TestBean("kerry", 35);
785 rod.setSpouse(kerry);
786 kerry.setSpouse(rod);
787 BeanWrapper bw = new BeanWrapperImpl(rod);
788 Integer KA = (Integer) bw.getPropertyValue("spouse.age");
789 assertTrue("kerry is 35", KA.intValue() == 35);
790 Integer RA = (Integer) bw.getPropertyValue("spouse.spouse.age");
791 assertTrue("rod is 31, not" + RA, RA.intValue() == 31);
792 ITestBean spousesSpouse = (ITestBean) bw.getPropertyValue("spouse.spouse");
793 assertTrue("spousesSpouse = initial point", rod == spousesSpouse);
794 }
795
796 @Test
797 public void testGetNestedPropertyNullValue() throws Exception {
798 ITestBean rod = new TestBean("rod", 31);
799 ITestBean kerry = new TestBean("kerry", 35);
800 rod.setSpouse(kerry);
801
802 BeanWrapper bw = new BeanWrapperImpl(rod);
803 try {
804 bw.getPropertyValue("spouse.spouse.age");
805 fail("Shouldn't have succeded with null path");
806 }
807 catch (NullValueInNestedPathException ex) {
808
809 assertTrue("it was the spouse.spouse property that was null, not " + ex.getPropertyName(),
810 ex.getPropertyName().equals("spouse.spouse"));
811 }
812 }
813
814 @Test
815 public void testSetNestedProperty() throws Exception {
816 ITestBean rod = new TestBean("rod", 31);
817 ITestBean kerry = new TestBean("kerry", 0);
818
819 BeanWrapper bw = new BeanWrapperImpl(rod);
820 bw.setPropertyValue("spouse", kerry);
821
822 assertTrue("nested set worked", rod.getSpouse() == kerry);
823 assertTrue("no back relation", kerry.getSpouse() == null);
824 bw.setPropertyValue(new PropertyValue("spouse.spouse", rod));
825 assertTrue("nested set worked", kerry.getSpouse() == rod);
826 assertTrue("kerry age not set", kerry.getAge() == 0);
827 bw.setPropertyValue(new PropertyValue("spouse.age", new Integer(35)));
828 assertTrue("Set primitive on spouse", kerry.getAge() == 35);
829
830 assertEquals(kerry, bw.getPropertyValue("spouse"));
831 assertEquals(rod, bw.getPropertyValue("spouse.spouse"));
832 }
833
834 @Test
835 public void testSetNestedPropertyNullValue() throws Exception {
836 ITestBean rod = new TestBean("rod", 31);
837 BeanWrapper bw = new BeanWrapperImpl(rod);
838 try {
839 bw.setPropertyValue("spouse.age", new Integer(31));
840 fail("Shouldn't have succeeded with null path");
841 }
842 catch (NullValueInNestedPathException ex) {
843
844 assertTrue("it was the spouse property that was null, not " + ex.getPropertyName(),
845 ex.getPropertyName().equals("spouse"));
846 }
847 }
848
849 @Test
850 public void testSetNestedPropertyPolymorphic() throws Exception {
851 ITestBean rod = new TestBean("rod", 31);
852 ITestBean kerry = new Employee();
853
854 BeanWrapper bw = new BeanWrapperImpl(rod);
855 bw.setPropertyValue("spouse", kerry);
856 bw.setPropertyValue("spouse.age", new Integer(35));
857 bw.setPropertyValue("spouse.name", "Kerry");
858 bw.setPropertyValue("spouse.company", "Lewisham");
859 assertTrue("kerry name is Kerry", kerry.getName().equals("Kerry"));
860
861 assertTrue("nested set worked", rod.getSpouse() == kerry);
862 assertTrue("no back relation", kerry.getSpouse() == null);
863 bw.setPropertyValue(new PropertyValue("spouse.spouse", rod));
864 assertTrue("nested set worked", kerry.getSpouse() == rod);
865
866 BeanWrapper kbw = new BeanWrapperImpl(kerry);
867 assertTrue("spouse.spouse.spouse.spouse.company=Lewisham",
868 "Lewisham".equals(kbw.getPropertyValue("spouse.spouse.spouse.spouse.company")));
869 }
870
871 @Test
872 public void testNullObject() {
873 try {
874 new BeanWrapperImpl((Object) null);
875 fail("Must throw an exception when constructed with null object");
876 }
877 catch (IllegalArgumentException ex) {
878
879 }
880 }
881
882 @Test
883 public void testNestedProperties() {
884 String doctorCompany = "";
885 String lawyerCompany = "Dr. Sueem";
886 TestBean tb = new TestBean();
887 BeanWrapper bw = new BeanWrapperImpl(tb);
888 bw.setPropertyValue("doctor.company", doctorCompany);
889 bw.setPropertyValue("lawyer.company", lawyerCompany);
890 assertEquals(doctorCompany, tb.getDoctor().getCompany());
891 assertEquals(lawyerCompany, tb.getLawyer().getCompany());
892 }
893
894 @Test
895 public void testIndexedProperties() {
896 IndexedTestBean bean = new IndexedTestBean();
897 BeanWrapper bw = new BeanWrapperImpl(bean);
898 TestBean tb0 = bean.getArray()[0];
899 TestBean tb1 = bean.getArray()[1];
900 TestBean tb2 = ((TestBean) bean.getList().get(0));
901 TestBean tb3 = ((TestBean) bean.getList().get(1));
902 TestBean tb6 = ((TestBean) bean.getSet().toArray()[0]);
903 TestBean tb7 = ((TestBean) bean.getSet().toArray()[1]);
904 TestBean tb4 = ((TestBean) bean.getMap().get("key1"));
905 TestBean tb5 = ((TestBean) bean.getMap().get("key.3"));
906 assertEquals("name0", tb0.getName());
907 assertEquals("name1", tb1.getName());
908 assertEquals("name2", tb2.getName());
909 assertEquals("name3", tb3.getName());
910 assertEquals("name6", tb6.getName());
911 assertEquals("name7", tb7.getName());
912 assertEquals("name4", tb4.getName());
913 assertEquals("name5", tb5.getName());
914 assertEquals("name0", bw.getPropertyValue("array[0].name"));
915 assertEquals("name1", bw.getPropertyValue("array[1].name"));
916 assertEquals("name2", bw.getPropertyValue("list[0].name"));
917 assertEquals("name3", bw.getPropertyValue("list[1].name"));
918 assertEquals("name6", bw.getPropertyValue("set[0].name"));
919 assertEquals("name7", bw.getPropertyValue("set[1].name"));
920 assertEquals("name4", bw.getPropertyValue("map[key1].name"));
921 assertEquals("name5", bw.getPropertyValue("map[key.3].name"));
922 assertEquals("name4", bw.getPropertyValue("map['key1'].name"));
923 assertEquals("name5", bw.getPropertyValue("map[\"key.3\"].name"));
924 assertEquals("nameX", bw.getPropertyValue("map[key4][0].name"));
925 assertEquals("nameY", bw.getPropertyValue("map[key4][1].name"));
926
927 MutablePropertyValues pvs = new MutablePropertyValues();
928 pvs.add("array[0].name", "name5");
929 pvs.add("array[1].name", "name4");
930 pvs.add("list[0].name", "name3");
931 pvs.add("list[1].name", "name2");
932 pvs.add("set[0].name", "name8");
933 pvs.add("set[1].name", "name9");
934 pvs.add("map[key1].name", "name1");
935 pvs.add("map['key.3'].name", "name0");
936 pvs.add("map[key4][0].name", "nameA");
937 pvs.add("map[key4][1].name", "nameB");
938 bw.setPropertyValues(pvs);
939 assertEquals("name5", tb0.getName());
940 assertEquals("name4", tb1.getName());
941 assertEquals("name3", tb2.getName());
942 assertEquals("name2", tb3.getName());
943 assertEquals("name1", tb4.getName());
944 assertEquals("name0", tb5.getName());
945 assertEquals("name5", bw.getPropertyValue("array[0].name"));
946 assertEquals("name4", bw.getPropertyValue("array[1].name"));
947 assertEquals("name3", bw.getPropertyValue("list[0].name"));
948 assertEquals("name2", bw.getPropertyValue("list[1].name"));
949 assertEquals("name8", bw.getPropertyValue("set[0].name"));
950 assertEquals("name9", bw.getPropertyValue("set[1].name"));
951 assertEquals("name1", bw.getPropertyValue("map[\"key1\"].name"));
952 assertEquals("name0", bw.getPropertyValue("map['key.3'].name"));
953 assertEquals("nameA", bw.getPropertyValue("map[key4][0].name"));
954 assertEquals("nameB", bw.getPropertyValue("map[key4][1].name"));
955 }
956
957 @Test
958 public void testIndexedPropertiesWithDirectAccess() {
959 IndexedTestBean bean = new IndexedTestBean();
960 BeanWrapper bw = new BeanWrapperImpl(bean);
961 TestBean tb0 = bean.getArray()[0];
962 TestBean tb1 = bean.getArray()[1];
963 TestBean tb2 = ((TestBean) bean.getList().get(0));
964 TestBean tb3 = ((TestBean) bean.getList().get(1));
965 TestBean tb6 = ((TestBean) bean.getSet().toArray()[0]);
966 TestBean tb7 = ((TestBean) bean.getSet().toArray()[1]);
967 TestBean tb4 = ((TestBean) bean.getMap().get("key1"));
968 TestBean tb5 = ((TestBean) bean.getMap().get("key2"));
969 assertEquals(tb0, bw.getPropertyValue("array[0]"));
970 assertEquals(tb1, bw.getPropertyValue("array[1]"));
971 assertEquals(tb2, bw.getPropertyValue("list[0]"));
972 assertEquals(tb3, bw.getPropertyValue("list[1]"));
973 assertEquals(tb6, bw.getPropertyValue("set[0]"));
974 assertEquals(tb7, bw.getPropertyValue("set[1]"));
975 assertEquals(tb4, bw.getPropertyValue("map[key1]"));
976 assertEquals(tb5, bw.getPropertyValue("map[key2]"));
977 assertEquals(tb4, bw.getPropertyValue("map['key1']"));
978 assertEquals(tb5, bw.getPropertyValue("map[\"key2\"]"));
979
980 MutablePropertyValues pvs = new MutablePropertyValues();
981 pvs.add("array[0]", tb5);
982 pvs.add("array[1]", tb4);
983 pvs.add("list[0]", tb3);
984 pvs.add("list[1]", tb2);
985 pvs.add("list[2]", tb0);
986 pvs.add("list[4]", tb1);
987 pvs.add("map[key1]", tb1);
988 pvs.add("map['key2']", tb0);
989 pvs.add("map[key5]", tb4);
990 pvs.add("map['key9']", tb5);
991 bw.setPropertyValues(pvs);
992 assertEquals(tb5, bean.getArray()[0]);
993 assertEquals(tb4, bean.getArray()[1]);
994 assertEquals(tb3, (bean.getList().get(0)));
995 assertEquals(tb2, (bean.getList().get(1)));
996 assertEquals(tb0, (bean.getList().get(2)));
997 assertEquals(null, (bean.getList().get(3)));
998 assertEquals(tb1, (bean.getList().get(4)));
999 assertEquals(tb1, (bean.getMap().get("key1")));
1000 assertEquals(tb0, (bean.getMap().get("key2")));
1001 assertEquals(tb4, (bean.getMap().get("key5")));
1002 assertEquals(tb5, (bean.getMap().get("key9")));
1003 assertEquals(tb5, bw.getPropertyValue("array[0]"));
1004 assertEquals(tb4, bw.getPropertyValue("array[1]"));
1005 assertEquals(tb3, bw.getPropertyValue("list[0]"));
1006 assertEquals(tb2, bw.getPropertyValue("list[1]"));
1007 assertEquals(tb0, bw.getPropertyValue("list[2]"));
1008 assertEquals(null, bw.getPropertyValue("list[3]"));
1009 assertEquals(tb1, bw.getPropertyValue("list[4]"));
1010 assertEquals(tb1, bw.getPropertyValue("map[\"key1\"]"));
1011 assertEquals(tb0, bw.getPropertyValue("map['key2']"));
1012 assertEquals(tb4, bw.getPropertyValue("map[\"key5\"]"));
1013 assertEquals(tb5, bw.getPropertyValue("map['key9']"));
1014 }
1015
1016 @Test
1017 public void testMapAccessWithTypeConversion() {
1018 IndexedTestBean bean = new IndexedTestBean();
1019 BeanWrapper bw = new BeanWrapperImpl(bean);
1020 bw.registerCustomEditor(TestBean.class, new PropertyEditorSupport() {
1021 @Override
1022 public void setAsText(String text) throws IllegalArgumentException {
1023 if (!StringUtils.hasLength(text)) {
1024 throw new IllegalArgumentException();
1025 }
1026 setValue(new TestBean(text));
1027 }
1028 });
1029
1030 MutablePropertyValues pvs = new MutablePropertyValues();
1031 pvs.add("map[key1]", "rod");
1032 pvs.add("map[key2]", "rob");
1033 bw.setPropertyValues(pvs);
1034 assertEquals("rod", ((TestBean) bean.getMap().get("key1")).getName());
1035 assertEquals("rob", ((TestBean) bean.getMap().get("key2")).getName());
1036
1037 pvs = new MutablePropertyValues();
1038 pvs.add("map[key1]", "rod");
1039 pvs.add("map[key2]", "");
1040 try {
1041 bw.setPropertyValues(pvs);
1042 fail("Should have thrown TypeMismatchException");
1043 }
1044 catch (PropertyBatchUpdateException ex) {
1045 PropertyAccessException pae = ex.getPropertyAccessException("map[key2]");
1046 assertTrue(pae instanceof TypeMismatchException);
1047 }
1048 }
1049
1050 @Test
1051 public void testMapAccessWithUnmodifiableMap() {
1052 IndexedTestBean bean = new IndexedTestBean();
1053 BeanWrapper bw = new BeanWrapperImpl(bean);
1054 bw.registerCustomEditor(TestBean.class, "map", new PropertyEditorSupport() {
1055 @Override
1056 public void setAsText(String text) throws IllegalArgumentException {
1057 if (!StringUtils.hasLength(text)) {
1058 throw new IllegalArgumentException();
1059 }
1060 setValue(new TestBean(text));
1061 }
1062 });
1063
1064 Map<Integer, String> inputMap = new HashMap<Integer, String>();
1065 inputMap.put(new Integer(1), "rod");
1066 inputMap.put(new Integer(2), "rob");
1067 MutablePropertyValues pvs = new MutablePropertyValues();
1068 pvs.add("map", Collections.unmodifiableMap(inputMap));
1069 bw.setPropertyValues(pvs);
1070 assertEquals("rod", ((TestBean) bean.getMap().get(new Integer(1))).getName());
1071 assertEquals("rob", ((TestBean) bean.getMap().get(new Integer(2))).getName());
1072 }
1073
1074 @Test
1075 public void testMapAccessWithCustomUnmodifiableMap() {
1076 IndexedTestBean bean = new IndexedTestBean();
1077 BeanWrapper bw = new BeanWrapperImpl(bean);
1078 bw.registerCustomEditor(TestBean.class, "map", new PropertyEditorSupport() {
1079 @Override
1080 public void setAsText(String text) throws IllegalArgumentException {
1081 if (!StringUtils.hasLength(text)) {
1082 throw new IllegalArgumentException();
1083 }
1084 setValue(new TestBean(text));
1085 }
1086 });
1087
1088 Map<Object, Object> inputMap = new HashMap<Object, Object>();
1089 inputMap.put(new Integer(1), "rod");
1090 inputMap.put(new Integer(2), "rob");
1091 MutablePropertyValues pvs = new MutablePropertyValues();
1092 pvs.add("map", new ReadOnlyMap(inputMap));
1093 bw.setPropertyValues(pvs);
1094 assertEquals("rod", ((TestBean) bean.getMap().get(new Integer(1))).getName());
1095 assertEquals("rob", ((TestBean) bean.getMap().get(new Integer(2))).getName());
1096 }
1097
1098 @SuppressWarnings("unchecked")
1099 @Test
1100 public void testRawMapAccessWithNoEditorRegistered() {
1101 IndexedTestBean bean = new IndexedTestBean();
1102 BeanWrapper bw = new BeanWrapperImpl(bean);
1103 Map inputMap = new HashMap();
1104 inputMap.put(new Integer(1), "rod");
1105 inputMap.put(new Integer(2), "rob");
1106 ReadOnlyMap readOnlyMap = new ReadOnlyMap(inputMap);
1107 MutablePropertyValues pvs = new MutablePropertyValues();
1108 pvs.add("map", readOnlyMap);
1109 bw.setPropertyValues(pvs);
1110 assertSame(readOnlyMap, bean.getMap());
1111 assertFalse(readOnlyMap.isAccessed());
1112 }
1113
1114 @Test
1115 public void testTypedMapReadOnlyMap() {
1116 TypedReadOnlyMap map = new TypedReadOnlyMap(Collections.singletonMap("key", new TestBean()));
1117 TypedReadOnlyMapClient bean = new TypedReadOnlyMapClient();
1118 BeanWrapper bw = new BeanWrapperImpl(bean);
1119 bw.setPropertyValue("map", map);
1120 }
1121
1122 @Test
1123 public void testPrimitiveArray() {
1124 PrimitiveArrayBean tb = new PrimitiveArrayBean();
1125 BeanWrapper bw = new BeanWrapperImpl(tb);
1126 bw.setPropertyValue("array", new String[] {"1", "2"});
1127 assertEquals(2, tb.getArray().length);
1128 assertEquals(1, tb.getArray()[0]);
1129 assertEquals(2, tb.getArray()[1]);
1130 }
1131
1132 @Test
1133 public void testLargeMatchingPrimitiveArray() {
1134 Assume.group(TestGroup.PERFORMANCE);
1135 Assume.notLogging(LogFactory.getLog(BeanWrapperTests.class));
1136
1137 PrimitiveArrayBean tb = new PrimitiveArrayBean();
1138 BeanWrapper bw = new BeanWrapperImpl(tb);
1139 int[] input = new int[1024];
1140 StopWatch sw = new StopWatch();
1141 sw.start("array1");
1142 for (int i = 0; i < 1000; i++) {
1143 bw.setPropertyValue("array", input);
1144 }
1145 sw.stop();
1146 assertEquals(1024, tb.getArray().length);
1147 assertEquals(0, tb.getArray()[0]);
1148 long time1 = sw.getLastTaskTimeMillis();
1149 assertTrue("Took too long", sw.getLastTaskTimeMillis() < 100);
1150
1151 bw.registerCustomEditor(String.class, new StringTrimmerEditor(false));
1152 sw.start("array2");
1153 for (int i = 0; i < 1000; i++) {
1154 bw.setPropertyValue("array", input);
1155 }
1156 sw.stop();
1157 assertTrue("Took too long", sw.getLastTaskTimeMillis() < 125);
1158
1159 bw.registerCustomEditor(int.class, "array.somePath", new CustomNumberEditor(Integer.class, false));
1160 sw.start("array3");
1161 for (int i = 0; i < 1000; i++) {
1162 bw.setPropertyValue("array", input);
1163 }
1164 sw.stop();
1165 assertTrue("Took too long", sw.getLastTaskTimeMillis() < 100);
1166
1167 bw.registerCustomEditor(int.class, "array[0].somePath", new CustomNumberEditor(Integer.class, false));
1168 sw.start("array3");
1169 for (int i = 0; i < 1000; i++) {
1170 bw.setPropertyValue("array", input);
1171 }
1172 sw.stop();
1173 assertTrue("Took too long", sw.getLastTaskTimeMillis() < 100);
1174
1175 bw.registerCustomEditor(int.class, new CustomNumberEditor(Integer.class, false));
1176 sw.start("array4");
1177 for (int i = 0; i < 100; i++) {
1178 bw.setPropertyValue("array", input);
1179 }
1180 sw.stop();
1181 assertEquals(1024, tb.getArray().length);
1182 assertEquals(0, tb.getArray()[0]);
1183 assertTrue("Took too long", sw.getLastTaskTimeMillis() > time1);
1184 }
1185
1186 @Test
1187 public void testLargeMatchingPrimitiveArrayWithSpecificEditor() {
1188 PrimitiveArrayBean tb = new PrimitiveArrayBean();
1189 BeanWrapper bw = new BeanWrapperImpl(tb);
1190 bw.registerCustomEditor(int.class, "array", new PropertyEditorSupport() {
1191 @Override
1192 public void setValue(Object value) {
1193 if (value instanceof Integer) {
1194 super.setValue(new Integer(((Integer) value).intValue() + 1));
1195 }
1196 }
1197 });
1198 int[] input = new int[1024];
1199 bw.setPropertyValue("array", input);
1200 assertEquals(1024, tb.getArray().length);
1201 assertEquals(1, tb.getArray()[0]);
1202 assertEquals(1, tb.getArray()[1]);
1203 }
1204
1205 @Test
1206 public void testLargeMatchingPrimitiveArrayWithIndexSpecificEditor() {
1207 PrimitiveArrayBean tb = new PrimitiveArrayBean();
1208 BeanWrapper bw = new BeanWrapperImpl(tb);
1209 bw.registerCustomEditor(int.class, "array[1]", new PropertyEditorSupport() {
1210 @Override
1211 public void setValue(Object value) {
1212 if (value instanceof Integer) {
1213 super.setValue(new Integer(((Integer) value).intValue() + 1));
1214 }
1215 }
1216 });
1217 int[] input = new int[1024];
1218 bw.setPropertyValue("array", input);
1219 assertEquals(1024, tb.getArray().length);
1220 assertEquals(0, tb.getArray()[0]);
1221 assertEquals(1, tb.getArray()[1]);
1222 }
1223
1224 @Test
1225 public void testPropertiesInProtectedBaseBean() {
1226 DerivedFromProtectedBaseBean bean = new DerivedFromProtectedBaseBean();
1227 BeanWrapper bw = new BeanWrapperImpl(bean);
1228 bw.setPropertyValue("someProperty", "someValue");
1229 assertEquals("someValue", bw.getPropertyValue("someProperty"));
1230 assertEquals("someValue", bean.getSomeProperty());
1231 }
1232
1233 @Test
1234 public void testErrorMessageOfNestedProperty() {
1235 ITestBean parent = new TestBean();
1236 ITestBean child = new DifferentTestBean();
1237 child.setName("test");
1238 parent.setSpouse(child);
1239 BeanWrapper bw = new BeanWrapperImpl(parent);
1240 try {
1241 bw.getPropertyValue("spouse.bla");
1242 }
1243 catch (NotReadablePropertyException ex) {
1244 assertTrue(ex.getMessage().indexOf(TestBean.class.getName()) != -1);
1245 }
1246 }
1247
1248 @Test
1249 public void testMatchingCollections() {
1250 IndexedTestBean tb = new IndexedTestBean();
1251 BeanWrapper bw = new BeanWrapperImpl(tb);
1252 Collection<String> coll = new HashSet<String>();
1253 coll.add("coll1");
1254 bw.setPropertyValue("collection", coll);
1255 Set<String> set = new HashSet<String>();
1256 set.add("set1");
1257 bw.setPropertyValue("set", set);
1258 SortedSet<String> sortedSet = new TreeSet<String>();
1259 sortedSet.add("sortedSet1");
1260 bw.setPropertyValue("sortedSet", sortedSet);
1261 List<String> list = new LinkedList<String>();
1262 list.add("list1");
1263 bw.setPropertyValue("list", list);
1264 assertSame(coll, tb.getCollection());
1265 assertSame(set, tb.getSet());
1266 assertSame(sortedSet, tb.getSortedSet());
1267 assertSame(list, tb.getList());
1268 }
1269
1270 @SuppressWarnings("unchecked")
1271 @Test
1272 public void testNonMatchingCollections() {
1273 IndexedTestBean tb = new IndexedTestBean();
1274 BeanWrapper bw = new BeanWrapperImpl(tb);
1275 Collection<String> coll = new ArrayList<String>();
1276 coll.add("coll1");
1277 bw.setPropertyValue("collection", coll);
1278 List<String> set = new LinkedList<String>();
1279 set.add("set1");
1280 bw.setPropertyValue("set", set);
1281 List<String> sortedSet = new ArrayList<String>();
1282 sortedSet.add("sortedSet1");
1283 bw.setPropertyValue("sortedSet", sortedSet);
1284 Set<String> list = new HashSet<String>();
1285 list.add("list1");
1286 bw.setPropertyValue("list", list);
1287 assertEquals(1, tb.getCollection().size());
1288 assertTrue(tb.getCollection().containsAll(coll));
1289 assertEquals(1, tb.getSet().size());
1290 assertTrue(tb.getSet().containsAll(set));
1291 assertEquals(1, tb.getSortedSet().size());
1292 assertTrue(tb.getSortedSet().containsAll(sortedSet));
1293 assertEquals(1, tb.getList().size());
1294 assertTrue(tb.getList().containsAll(list));
1295 }
1296
1297 @SuppressWarnings("unchecked")
1298 @Test
1299 public void testCollectionsWithArrayValues() {
1300 IndexedTestBean tb = new IndexedTestBean();
1301 BeanWrapper bw = new BeanWrapperImpl(tb);
1302 Collection<String> coll = new HashSet<String>();
1303 coll.add("coll1");
1304 bw.setPropertyValue("collection", coll.toArray());
1305 List<String> set = new LinkedList<String>();
1306 set.add("set1");
1307 bw.setPropertyValue("set", set.toArray());
1308 List<String> sortedSet = new ArrayList<String>();
1309 sortedSet.add("sortedSet1");
1310 bw.setPropertyValue("sortedSet", sortedSet.toArray());
1311 Set<String> list = new HashSet<String>();
1312 list.add("list1");
1313 bw.setPropertyValue("list", list.toArray());
1314 assertEquals(1, tb.getCollection().size());
1315 assertTrue(tb.getCollection().containsAll(coll));
1316 assertEquals(1, tb.getSet().size());
1317 assertTrue(tb.getSet().containsAll(set));
1318 assertEquals(1, tb.getSortedSet().size());
1319 assertTrue(tb.getSortedSet().containsAll(sortedSet));
1320 assertEquals(1, tb.getList().size());
1321 assertTrue(tb.getList().containsAll(list));
1322 }
1323
1324 @SuppressWarnings("unchecked")
1325 @Test
1326 public void testCollectionsWithIntArrayValues() {
1327 IndexedTestBean tb = new IndexedTestBean();
1328 BeanWrapper bw = new BeanWrapperImpl(tb);
1329 Collection<Integer> coll = new HashSet<Integer>();
1330 coll.add(new Integer(0));
1331 bw.setPropertyValue("collection", new int[] {0});
1332 List<Integer> set = new LinkedList<Integer>();
1333 set.add(new Integer(1));
1334 bw.setPropertyValue("set", new int[] {1});
1335 List<Integer> sortedSet = new ArrayList<Integer>();
1336 sortedSet.add(new Integer(2));
1337 bw.setPropertyValue("sortedSet", new int[] {2});
1338 Set<Integer> list = new HashSet<Integer>();
1339 list.add(new Integer(3));
1340 bw.setPropertyValue("list", new int[] {3});
1341 assertEquals(1, tb.getCollection().size());
1342 assertTrue(tb.getCollection().containsAll(coll));
1343 assertEquals(1, tb.getSet().size());
1344 assertTrue(tb.getSet().containsAll(set));
1345 assertEquals(1, tb.getSortedSet().size());
1346 assertTrue(tb.getSortedSet().containsAll(sortedSet));
1347 assertEquals(1, tb.getList().size());
1348 assertTrue(tb.getList().containsAll(list));
1349 }
1350
1351 @SuppressWarnings("unchecked")
1352 @Test
1353 public void testCollectionsWithIntegerValues() {
1354 IndexedTestBean tb = new IndexedTestBean();
1355 BeanWrapper bw = new BeanWrapperImpl(tb);
1356 Collection<Integer> coll = new HashSet<Integer>();
1357 coll.add(new Integer(0));
1358 bw.setPropertyValue("collection", new Integer(0));
1359 List<Integer> set = new LinkedList<Integer>();
1360 set.add(new Integer(1));
1361 bw.setPropertyValue("set", new Integer(1));
1362 List<Integer> sortedSet = new ArrayList<Integer>();
1363 sortedSet.add(new Integer(2));
1364 bw.setPropertyValue("sortedSet", new Integer(2));
1365 Set<Integer> list = new HashSet<Integer>();
1366 list.add(new Integer(3));
1367 bw.setPropertyValue("list", new Integer(3));
1368 assertEquals(1, tb.getCollection().size());
1369 assertTrue(tb.getCollection().containsAll(coll));
1370 assertEquals(1, tb.getSet().size());
1371 assertTrue(tb.getSet().containsAll(set));
1372 assertEquals(1, tb.getSortedSet().size());
1373 assertTrue(tb.getSortedSet().containsAll(sortedSet));
1374 assertEquals(1, tb.getList().size());
1375 assertTrue(tb.getList().containsAll(list));
1376 }
1377
1378 @SuppressWarnings("unchecked")
1379 @Test
1380 public void testCollectionsWithStringValues() {
1381 IndexedTestBean tb = new IndexedTestBean();
1382 BeanWrapper bw = new BeanWrapperImpl(tb);
1383 List<String> set = new LinkedList<String>();
1384 set.add("set1");
1385 bw.setPropertyValue("set", "set1");
1386 List<String> sortedSet = new ArrayList<String>();
1387 sortedSet.add("sortedSet1");
1388 bw.setPropertyValue("sortedSet", "sortedSet1");
1389 Set<String> list = new HashSet<String>();
1390 list.add("list1");
1391 bw.setPropertyValue("list", "list1");
1392 assertEquals(1, tb.getSet().size());
1393 assertTrue(tb.getSet().containsAll(set));
1394 assertEquals(1, tb.getSortedSet().size());
1395 assertTrue(tb.getSortedSet().containsAll(sortedSet));
1396 assertEquals(1, tb.getList().size());
1397 assertTrue(tb.getList().containsAll(list));
1398 }
1399
1400 @Test
1401 public void testCollectionsWithStringValuesAndCustomEditor() {
1402 IndexedTestBean tb = new IndexedTestBean();
1403 BeanWrapper bw = new BeanWrapperImpl(tb);
1404 bw.registerCustomEditor(String.class, "set", new StringTrimmerEditor(false));
1405 bw.registerCustomEditor(String.class, "list", new StringTrimmerEditor(false));
1406
1407 bw.setPropertyValue("set", "set1 ");
1408 bw.setPropertyValue("sortedSet", "sortedSet1");
1409 bw.setPropertyValue("list", "list1 ");
1410 assertEquals(1, tb.getSet().size());
1411 assertTrue(tb.getSet().contains("set1"));
1412 assertEquals(1, tb.getSortedSet().size());
1413 assertTrue(tb.getSortedSet().contains("sortedSet1"));
1414 assertEquals(1, tb.getList().size());
1415 assertTrue(tb.getList().contains("list1"));
1416
1417 bw.setPropertyValue("list", Arrays.asList(new String[] {"list1 "}));
1418 assertTrue(tb.getList().contains("list1"));
1419 }
1420
1421 @Test
1422 public void testMatchingMaps() {
1423 IndexedTestBean tb = new IndexedTestBean();
1424 BeanWrapper bw = new BeanWrapperImpl(tb);
1425 Map<String, String> map = new HashMap<String, String>();
1426 map.put("key", "value");
1427 bw.setPropertyValue("map", map);
1428 SortedMap<?, ?> sortedMap = new TreeMap<Object, Object>();
1429 map.put("sortedKey", "sortedValue");
1430 bw.setPropertyValue("sortedMap", sortedMap);
1431 assertSame(map, tb.getMap());
1432 assertSame(sortedMap, tb.getSortedMap());
1433 }
1434
1435 @Test
1436 public void testNonMatchingMaps() {
1437 IndexedTestBean tb = new IndexedTestBean();
1438 BeanWrapper bw = new BeanWrapperImpl(tb);
1439 Map<String, String> map = new TreeMap<String, String>();
1440 map.put("key", "value");
1441 bw.setPropertyValue("map", map);
1442 Map<String, String> sortedMap = new TreeMap<String, String>();
1443 sortedMap.put("sortedKey", "sortedValue");
1444 bw.setPropertyValue("sortedMap", sortedMap);
1445 assertEquals(1, tb.getMap().size());
1446 assertEquals("value", tb.getMap().get("key"));
1447 assertEquals(1, tb.getSortedMap().size());
1448 assertEquals("sortedValue", tb.getSortedMap().get("sortedKey"));
1449 }
1450
1451 @Test
1452 public void testSetNumberProperties() {
1453 NumberPropertyBean bean = new NumberPropertyBean();
1454 BeanWrapper bw = new BeanWrapperImpl(bean);
1455
1456 String byteValue = " " + Byte.MAX_VALUE + " ";
1457 String shortValue = " " + Short.MAX_VALUE + " ";
1458 String intValue = " " + Integer.MAX_VALUE + " ";
1459 String longValue = " " + Long.MAX_VALUE + " ";
1460 String floatValue = " " + Float.MAX_VALUE + " ";
1461 String doubleValue = " " + Double.MAX_VALUE + " ";
1462
1463 bw.setPropertyValue("myPrimitiveByte", byteValue);
1464 bw.setPropertyValue("myByte", byteValue);
1465
1466 bw.setPropertyValue("myPrimitiveShort", shortValue);
1467 bw.setPropertyValue("myShort", shortValue);
1468
1469 bw.setPropertyValue("myPrimitiveInt", intValue);
1470 bw.setPropertyValue("myInteger", intValue);
1471
1472 bw.setPropertyValue("myPrimitiveLong", longValue);
1473 bw.setPropertyValue("myLong", longValue);
1474
1475 bw.setPropertyValue("myPrimitiveFloat", floatValue);
1476 bw.setPropertyValue("myFloat", floatValue);
1477
1478 bw.setPropertyValue("myPrimitiveDouble", doubleValue);
1479 bw.setPropertyValue("myDouble", doubleValue);
1480
1481 assertEquals(Byte.MAX_VALUE, bean.getMyPrimitiveByte());
1482 assertEquals(Byte.MAX_VALUE, bean.getMyByte().byteValue());
1483
1484 assertEquals(Short.MAX_VALUE, bean.getMyPrimitiveShort());
1485 assertEquals(Short.MAX_VALUE, bean.getMyShort().shortValue());
1486
1487 assertEquals(Integer.MAX_VALUE, bean.getMyPrimitiveInt());
1488 assertEquals(Integer.MAX_VALUE, bean.getMyInteger().intValue());
1489
1490 assertEquals(Long.MAX_VALUE, bean.getMyPrimitiveLong());
1491 assertEquals(Long.MAX_VALUE, bean.getMyLong().longValue());
1492
1493 assertEquals(Float.MAX_VALUE, bean.getMyPrimitiveFloat(), 0.001);
1494 assertEquals(Float.MAX_VALUE, bean.getMyFloat().floatValue(), 0.001);
1495
1496 assertEquals(Double.MAX_VALUE, bean.getMyPrimitiveDouble(), 0.001);
1497 assertEquals(Double.MAX_VALUE, bean.getMyDouble().doubleValue(), 0.001);
1498
1499 }
1500
1501 @Test
1502 public void testAlternativesForTypo() {
1503 IntelliBean ib = new IntelliBean();
1504 BeanWrapper bw = new BeanWrapperImpl(ib);
1505 try {
1506 bw.setPropertyValue("names", "Alef");
1507 }
1508 catch (NotWritablePropertyException ex) {
1509 assertNotNull("Possible matches not determined", ex.getPossibleMatches());
1510 assertEquals("Invalid amount of alternatives", 1, ex.getPossibleMatches().length);
1511 }
1512 }
1513
1514 @Test
1515 public void testAlternativesForTypos() {
1516 IntelliBean ib = new IntelliBean();
1517 BeanWrapper bw = new BeanWrapperImpl(ib);
1518 try {
1519 bw.setPropertyValue("mystring", "Arjen");
1520 }
1521 catch (NotWritablePropertyException ex) {
1522 assertNotNull("Possible matches not determined", ex.getPossibleMatches());
1523 assertEquals("Invalid amount of alternatives", 3, ex.getPossibleMatches().length);
1524 }
1525 }
1526
1527 @Test
1528 public void testGenericEnum() {
1529 EnumConsumer consumer = new EnumConsumer();
1530 BeanWrapper bw = new BeanWrapperImpl(consumer);
1531 bw.setPropertyValue("enumValue", TestEnum.class.getName() + ".TEST_VALUE");
1532 assertEquals(TestEnum.TEST_VALUE, consumer.getEnumValue());
1533 }
1534
1535 @Test
1536 public void testWildcardedGenericEnum() {
1537 WildcardEnumConsumer consumer = new WildcardEnumConsumer();
1538 BeanWrapper bw = new BeanWrapperImpl(consumer);
1539 bw.setPropertyValue("enumValue", TestEnum.class.getName() + ".TEST_VALUE");
1540 assertEquals(TestEnum.TEST_VALUE, consumer.getEnumValue());
1541 }
1542
1543 @Test
1544 public void cornerSpr10115() {
1545 Spr10115Bean foo = new Spr10115Bean();
1546 BeanWrapperImpl bwi = new BeanWrapperImpl(foo);
1547 bwi.setPropertyValue("prop1", "val1");
1548 assertEquals("val1", Spr10115Bean.prop1);
1549 }
1550
1551 @Test
1552 public void testArrayToObject() {
1553 ArrayToObject foo = new ArrayToObject();
1554 BeanWrapperImpl bwi = new BeanWrapperImpl(foo);
1555
1556 Object[] array = new Object[] {"1","2"};
1557 bwi.setPropertyValue("object", array);
1558 assertThat(foo.getObject(), equalTo((Object) array));
1559
1560 array = new Object[] {"1"};
1561 bwi.setPropertyValue("object", array);
1562 assertThat(foo.getObject(), equalTo((Object) array));
1563 }
1564
1565 @Test
1566 public void testPropertyTypeMismatch() {
1567 PropertyTypeMismatch foo = new PropertyTypeMismatch();
1568 BeanWrapperImpl bwi = new BeanWrapperImpl(foo);
1569 bwi.setPropertyValue("object", "a String");
1570 assertEquals("a String", foo.value);
1571 assertTrue(foo.getObject() == 8);
1572 assertEquals(8, bwi.getPropertyValue("object"));
1573 }
1574
1575 @Test
1576 public void testGetterWithOptional() {
1577 GetterWithOptional foo = new GetterWithOptional();
1578 TestBean tb = new TestBean("x");
1579 BeanWrapperImpl bwi = new BeanWrapperImpl(foo);
1580
1581 bwi.setPropertyValue("object", tb);
1582 assertSame(tb, foo.value);
1583 assertSame(tb, foo.getObject().get());
1584 assertSame(tb, ((Optional<String>) bwi.getPropertyValue("object")).get());
1585 assertEquals("x", foo.value.getName());
1586 assertEquals("x", foo.getObject().get().getName());
1587 assertEquals("x", bwi.getPropertyValue("object.name"));
1588
1589 bwi.setPropertyValue("object.name", "y");
1590 assertSame(tb, foo.value);
1591 assertSame(tb, foo.getObject().get());
1592 assertSame(tb, ((Optional<String>) bwi.getPropertyValue("object")).get());
1593 assertEquals("y", foo.value.getName());
1594 assertEquals("y", foo.getObject().get().getName());
1595 assertEquals("y", bwi.getPropertyValue("object.name"));
1596 }
1597
1598 @Test
1599 public void testGetterWithOptionalAndAutoGrowing() {
1600 GetterWithOptional foo = new GetterWithOptional();
1601 BeanWrapperImpl bwi = new BeanWrapperImpl(foo);
1602 bwi.setAutoGrowNestedPaths(true);
1603
1604 bwi.setPropertyValue("object.name", "x");
1605 assertEquals("x", foo.value.getName());
1606 assertEquals("x", foo.getObject().get().getName());
1607 assertEquals("x", bwi.getPropertyValue("object.name"));
1608 }
1609
1610 @Test
1611 public void testGenericArraySetter() {
1612 SkipReaderStub foo = new SkipReaderStub();
1613 BeanWrapperImpl bwi = new BeanWrapperImpl(foo);
1614 List<String> values = new LinkedList<String>();
1615 values.add("1");
1616 values.add("2");
1617 values.add("3");
1618 values.add("4");
1619 bwi.setPropertyValue("items", values);
1620 Object[] result = foo.items;
1621 assertEquals(4, result.length);
1622 assertEquals("1", result[0]);
1623 assertEquals("2", result[1]);
1624 assertEquals("3", result[2]);
1625 assertEquals("4", result[3]);
1626 }
1627
1628
1629 static class Spr10115Bean {
1630
1631 private static String prop1;
1632
1633 public static void setProp1(String prop1) {
1634 Spr10115Bean.prop1 = prop1;
1635 }
1636 }
1637
1638
1639 @SuppressWarnings("unused")
1640 private static class Foo {
1641
1642 private List list;
1643
1644 private List<Map> listOfMaps;
1645
1646 public List getList() {
1647 return list;
1648 }
1649
1650 public void setList(List list) {
1651 this.list = list;
1652 }
1653
1654 public List<Map> getListOfMaps() {
1655 return listOfMaps;
1656 }
1657
1658 public void setListOfMaps(List<Map> listOfMaps) {
1659 this.listOfMaps = listOfMaps;
1660 }
1661 }
1662
1663
1664 private static class DifferentTestBean extends TestBean {
1665
1666 }
1667
1668
1669
1670
1671 @SuppressWarnings("unused")
1672 private static class EnumTester {
1673
1674 private Autowire autowire;
1675
1676 public void setAutowire(Autowire autowire) {
1677 this.autowire = autowire;
1678 }
1679
1680 public Autowire getAutowire() {
1681 return autowire;
1682 }
1683 }
1684
1685
1686 @SuppressWarnings("unused")
1687 private static class PropsTester {
1688
1689 private Properties props;
1690
1691 private String name;
1692
1693 private String[] stringArray;
1694
1695 private int[] intArray;
1696
1697 public void setProperties(Properties p) {
1698 props = p;
1699 }
1700
1701 public void setName(String name) {
1702 this.name = name;
1703 }
1704
1705 public void setStringArray(String[] sa) {
1706 this.stringArray = sa;
1707 }
1708
1709 public void setIntArray(int[] intArray) {
1710 this.intArray = intArray;
1711 }
1712 }
1713
1714
1715 @SuppressWarnings("unused")
1716 private static class GetterBean {
1717
1718 private String name;
1719
1720 public void setName(String name) {
1721 this.name = name;
1722 }
1723
1724 public String getName() {
1725 if (this.name == null) {
1726 throw new RuntimeException("name property must be set");
1727 }
1728 return name;
1729 }
1730 }
1731
1732
1733 @SuppressWarnings("unused")
1734 private static class ThrowsException {
1735
1736 public void doSomething(Throwable t) throws Throwable {
1737 throw t;
1738 }
1739 }
1740
1741
1742 @SuppressWarnings("unused")
1743 private static class PrimitiveArrayBean {
1744
1745 private int[] array;
1746
1747 public int[] getArray() {
1748 return array;
1749 }
1750
1751 public void setArray(int[] array) {
1752 this.array = array;
1753 }
1754 }
1755
1756 @SuppressWarnings("unused")
1757 private static class StringArrayBean {
1758
1759 private String[] array;
1760
1761 public String[] getArray() {
1762 return array;
1763 }
1764
1765 public void setArray(String[] array) {
1766 this.array = array;
1767 }
1768 }
1769
1770
1771 @SuppressWarnings("unused")
1772 private static class NumberPropertyBean {
1773
1774 private byte myPrimitiveByte;
1775 private Byte myByte;
1776
1777 private short myPrimitiveShort;
1778 private Short myShort;
1779
1780 private int myPrimitiveInt;
1781 private Integer myInteger;
1782
1783 private long myPrimitiveLong;
1784 private Long myLong;
1785
1786 private float myPrimitiveFloat;
1787 private Float myFloat;
1788
1789 private double myPrimitiveDouble;
1790 private Double myDouble;
1791
1792 public byte getMyPrimitiveByte() {
1793 return myPrimitiveByte;
1794 }
1795
1796 public void setMyPrimitiveByte(byte myPrimitiveByte) {
1797 this.myPrimitiveByte = myPrimitiveByte;
1798 }
1799
1800 public Byte getMyByte() {
1801 return myByte;
1802 }
1803
1804 public void setMyByte(Byte myByte) {
1805 this.myByte = myByte;
1806 }
1807
1808 public short getMyPrimitiveShort() {
1809 return myPrimitiveShort;
1810 }
1811
1812 public void setMyPrimitiveShort(short myPrimitiveShort) {
1813 this.myPrimitiveShort = myPrimitiveShort;
1814 }
1815
1816 public Short getMyShort() {
1817 return myShort;
1818 }
1819
1820 public void setMyShort(Short myShort) {
1821 this.myShort = myShort;
1822 }
1823
1824 public int getMyPrimitiveInt() {
1825 return myPrimitiveInt;
1826 }
1827
1828 public void setMyPrimitiveInt(int myPrimitiveInt) {
1829 this.myPrimitiveInt = myPrimitiveInt;
1830 }
1831
1832 public Integer getMyInteger() {
1833 return myInteger;
1834 }
1835
1836 public void setMyInteger(Integer myInteger) {
1837 this.myInteger = myInteger;
1838 }
1839
1840 public long getMyPrimitiveLong() {
1841 return myPrimitiveLong;
1842 }
1843
1844 public void setMyPrimitiveLong(long myPrimitiveLong) {
1845 this.myPrimitiveLong = myPrimitiveLong;
1846 }
1847
1848 public Long getMyLong() {
1849 return myLong;
1850 }
1851
1852 public void setMyLong(Long myLong) {
1853 this.myLong = myLong;
1854 }
1855
1856 public float getMyPrimitiveFloat() {
1857 return myPrimitiveFloat;
1858 }
1859
1860 public void setMyPrimitiveFloat(float myPrimitiveFloat) {
1861 this.myPrimitiveFloat = myPrimitiveFloat;
1862 }
1863
1864 public Float getMyFloat() {
1865 return myFloat;
1866 }
1867
1868 public void setMyFloat(Float myFloat) {
1869 this.myFloat = myFloat;
1870 }
1871
1872 public double getMyPrimitiveDouble() {
1873 return myPrimitiveDouble;
1874 }
1875
1876 public void setMyPrimitiveDouble(double myPrimitiveDouble) {
1877 this.myPrimitiveDouble = myPrimitiveDouble;
1878 }
1879
1880 public Double getMyDouble() {
1881 return myDouble;
1882 }
1883
1884 public void setMyDouble(Double myDouble) {
1885 this.myDouble = myDouble;
1886 }
1887 }
1888
1889
1890 @SuppressWarnings("unused")
1891 private static class IntelliBean {
1892
1893 public void setName(String name) {}
1894
1895 public void setMyString(String string) {}
1896
1897 public void setMyStrings(String string) {}
1898
1899 public void setMyStriNg(String string) {}
1900
1901 public void setMyStringss(String string) {}
1902 }
1903
1904
1905 @SuppressWarnings("unused")
1906 private static class Employee extends TestBean {
1907
1908 private String co;
1909
1910 public String getCompany() {
1911 return co;
1912 }
1913
1914 public void setCompany(String co) {
1915 this.co = co;
1916 }
1917 }
1918
1919
1920 @SuppressWarnings("serial")
1921 public static class ReadOnlyMap<K, V> extends HashMap<K, V> {
1922
1923 private boolean frozen = false;
1924
1925 private boolean accessed = false;
1926
1927 public ReadOnlyMap() {
1928 this.frozen = true;
1929 }
1930
1931 public ReadOnlyMap(Map<? extends K, ? extends V> map) {
1932 super(map);
1933 this.frozen = true;
1934 }
1935
1936 @Override
1937 public V put(K key, V value) {
1938 if (this.frozen) {
1939 throw new UnsupportedOperationException();
1940 }
1941 else {
1942 return super.put(key, value);
1943 }
1944 }
1945
1946 @Override
1947 public Set<Map.Entry<K, V>> entrySet() {
1948 this.accessed = true;
1949 return super.entrySet();
1950 }
1951
1952 @Override
1953 public Set<K> keySet() {
1954 this.accessed = true;
1955 return super.keySet();
1956 }
1957
1958 @Override
1959 public int size() {
1960 this.accessed = true;
1961 return super.size();
1962 }
1963
1964 public boolean isAccessed() {
1965 return this.accessed;
1966 }
1967 }
1968
1969
1970 @SuppressWarnings("serial")
1971 public static class TypedReadOnlyMap extends ReadOnlyMap<String, TestBean> {
1972
1973 public TypedReadOnlyMap() {
1974 }
1975
1976 public TypedReadOnlyMap(Map<? extends String, ? extends TestBean> map) {
1977 super(map);
1978 }
1979 }
1980
1981
1982 public static class TypedReadOnlyMapClient {
1983
1984 public void setMap(TypedReadOnlyMap map) {
1985 }
1986 }
1987
1988
1989 public static class EnumConsumer {
1990
1991 private Enum<TestEnum> enumValue;
1992
1993 public Enum<TestEnum> getEnumValue() {
1994 return enumValue;
1995 }
1996
1997 public void setEnumValue(Enum<TestEnum> enumValue) {
1998 this.enumValue = enumValue;
1999 }
2000 }
2001
2002
2003 public static class WildcardEnumConsumer {
2004
2005 private Enum<?> enumValue;
2006
2007 public Enum<?> getEnumValue() {
2008 return enumValue;
2009 }
2010
2011 public void setEnumValue(Enum<?> enumValue) {
2012 this.enumValue = enumValue;
2013 }
2014 }
2015
2016
2017 public enum TestEnum {
2018
2019 TEST_VALUE
2020 }
2021
2022
2023 public static class ArrayToObject {
2024
2025 private Object object;
2026
2027 public void setObject(Object object) {
2028 this.object = object;
2029 }
2030
2031 public Object getObject() {
2032 return object;
2033 }
2034 }
2035
2036
2037 public static class PropertyTypeMismatch {
2038
2039 public String value;
2040
2041 public void setObject(String object) {
2042 this.value = object;
2043 }
2044
2045 public Integer getObject() {
2046 return (this.value != null ? this.value.length() : null);
2047 }
2048 }
2049
2050
2051 public static class GetterWithOptional {
2052
2053 public TestBean value;
2054
2055 public void setObject(TestBean object) {
2056 this.value = object;
2057 }
2058
2059 public Optional<TestBean> getObject() {
2060 return Optional.ofNullable(this.value);
2061 }
2062 }
2063
2064
2065 public static class SkipReaderStub<T> {
2066
2067 public T[] items;
2068
2069 public SkipReaderStub() {
2070 }
2071
2072 public SkipReaderStub(T... items) {
2073 this.items = items;
2074 }
2075
2076 public void setItems(T... items) {
2077 this.items = items;
2078 }
2079 }
2080
2081 }