| /* |
| * Licensed to the Apache Software Foundation (ASF) under one or more |
| * contributor license agreements. See the NOTICE file distributed with |
| * this work for additional information regarding copyright ownership. |
| * The ASF licenses this file to You under the Apache License, Version 2.0 |
| * (the "License"); you may not use this file except in compliance with |
| * the License. You may obtain a copy of the License at |
| * |
| * https://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, software |
| * distributed under the License is distributed on an "AS IS" BASIS, |
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| * See the License for the specific language governing permissions and |
| * limitations under the License. |
| */ |
| |
| package org.apache.commons.beanutils2; |
| |
| import static org.junit.jupiter.api.Assertions.assertEquals; |
| import static org.junit.jupiter.api.Assertions.assertFalse; |
| import static org.junit.jupiter.api.Assertions.assertInstanceOf; |
| import static org.junit.jupiter.api.Assertions.assertNotNull; |
| import static org.junit.jupiter.api.Assertions.assertNull; |
| import static org.junit.jupiter.api.Assertions.assertTrue; |
| |
| import java.util.ArrayList; |
| import java.util.HashMap; |
| import java.util.List; |
| import java.util.Map; |
| |
| import org.junit.jupiter.api.AfterEach; |
| import org.junit.jupiter.api.BeforeEach; |
| import org.junit.jupiter.api.Test; |
| |
| /** |
| * Test case for BeanUtils when the underlying bean is actually a DynaBean. |
| */ |
| class DynaBeanUtilsTest { |
| |
| /** |
| * Create and return a {@code DynaClass} instance for our test {@code DynaBean}. |
| */ |
| protected static DynaClass createDynaClass() { |
| |
| final int[] intArray = {}; |
| final String[] stringArray = {}; |
| |
| return new BasicDynaClass("TestDynaClass", null, new DynaProperty[] { new DynaProperty("booleanProperty", Boolean.TYPE), |
| new DynaProperty("booleanSecond", Boolean.TYPE), new DynaProperty("byteProperty", Byte.TYPE), new DynaProperty("doubleProperty", Double.TYPE), |
| new DynaProperty("dupProperty", stringArray.getClass()), new DynaProperty("floatProperty", Float.TYPE), |
| new DynaProperty("intArray", intArray.getClass()), new DynaProperty("intIndexed", intArray.getClass()), |
| new DynaProperty("intProperty", Integer.TYPE), new DynaProperty("listIndexed", List.class), new DynaProperty("longProperty", Long.TYPE), |
| new DynaProperty("mapProperty", Map.class), new DynaProperty("mappedProperty", Map.class), new DynaProperty("mappedIntProperty", Map.class), |
| new DynaProperty("nested", TestBean.class), new DynaProperty("nullProperty", String.class), new DynaProperty("shortProperty", Short.TYPE), |
| new DynaProperty("stringArray", stringArray.getClass()), new DynaProperty("stringIndexed", stringArray.getClass()), |
| new DynaProperty("stringProperty", String.class), }); |
| |
| } |
| |
| /** |
| * The basic test bean for each test. |
| */ |
| protected DynaBean bean; |
| |
| /** |
| * The nested bean pointed at by the "nested" property. |
| */ |
| protected TestBean nested; |
| |
| /** |
| * The set of properties that should be described. |
| */ |
| protected String[] describes = { "booleanProperty", "booleanSecond", "byteProperty", "doubleProperty", "dupProperty", "floatProperty", "intArray", |
| "intIndexed", "intProperty", "listIndexed", "longProperty", "mapProperty", "mappedProperty", "mappedIntProperty", "nested", "nullProperty", |
| // "readOnlyProperty", |
| "shortProperty", "stringArray", "stringIndexed", "stringProperty" }; |
| |
| // Ensure that the nested intArray matches the specified values |
| protected void checkIntArray(final int[] actual, final int[] expected) { |
| assertNotNull(actual, "actual array not null"); |
| assertEquals(expected.length, actual.length, "actual array length"); |
| for (int i = 0; i < actual.length; i++) { |
| assertEquals(expected[i], actual[i], "actual array value[" + i + "]"); |
| } |
| } |
| |
| // Ensure that the actual Map matches the expected Map |
| protected void checkMap(final Map<?, ?> actual, final Map<?, ?> expected) { |
| assertNotNull(actual, "actual map not null"); |
| assertEquals(expected.size(), actual.size(), "actual map size"); |
| for (final Object key : expected.keySet()) { |
| assertEquals(expected.get(key), actual.get(key), "actual map value(" + key + ")"); |
| } |
| } |
| |
| /** |
| * Sets up instance variables required by this test case. |
| */ |
| @BeforeEach |
| public void setUp() throws Exception { |
| |
| ConvertUtils.deregister(); |
| |
| // Instantiate a new DynaBean instance |
| final DynaClass dynaClass = createDynaClass(); |
| bean = dynaClass.newInstance(); |
| |
| // Initialize the DynaBean's property values (like TestBean) |
| bean.set("booleanProperty", Boolean.valueOf(true)); |
| bean.set("booleanSecond", Boolean.valueOf(true)); |
| bean.set("byteProperty", Byte.valueOf((byte) 121)); |
| bean.set("doubleProperty", Double.valueOf(321.0)); |
| bean.set("floatProperty", Float.valueOf((float) 123.0)); |
| final String[] dupProperty = { "Dup 0", "Dup 1", "Dup 2", "Dup 3", "Dup 4" }; |
| bean.set("dupProperty", dupProperty); |
| final int[] intArray = { 0, 10, 20, 30, 40 }; |
| bean.set("intArray", intArray); |
| final int[] intIndexed = { 0, 10, 20, 30, 40 }; |
| bean.set("intIndexed", intIndexed); |
| bean.set("intProperty", Integer.valueOf(123)); |
| final List<String> listIndexed = new ArrayList<>(); |
| listIndexed.add("String 0"); |
| listIndexed.add("String 1"); |
| listIndexed.add("String 2"); |
| listIndexed.add("String 3"); |
| listIndexed.add("String 4"); |
| bean.set("listIndexed", listIndexed); |
| bean.set("longProperty", Long.valueOf(321)); |
| final HashMap<String, Object> mapProperty = new HashMap<>(); |
| mapProperty.put("First Key", "First Value"); |
| mapProperty.put("Second Key", "Second Value"); |
| bean.set("mapProperty", mapProperty); |
| final HashMap<String, Object> mappedProperty = new HashMap<>(); |
| mappedProperty.put("First Key", "First Value"); |
| mappedProperty.put("Second Key", "Second Value"); |
| bean.set("mappedProperty", mappedProperty); |
| final HashMap<String, Integer> mappedIntProperty = new HashMap<>(); |
| mappedIntProperty.put("One", Integer.valueOf(1)); |
| mappedIntProperty.put("Two", Integer.valueOf(2)); |
| bean.set("mappedIntProperty", mappedIntProperty); |
| nested = new TestBean(); |
| bean.set("nested", nested); |
| // Property "nullProperty" is not initialized, so it should return null |
| bean.set("shortProperty", Short.valueOf((short) 987)); |
| final String[] stringArray = { "String 0", "String 1", "String 2", "String 3", "String 4" }; |
| bean.set("stringArray", stringArray); |
| final String[] stringIndexed = { "String 0", "String 1", "String 2", "String 3", "String 4" }; |
| bean.set("stringIndexed", stringIndexed); |
| bean.set("stringProperty", "This is a string"); |
| |
| } |
| |
| /** |
| * Tear down instance variables required by this test case. |
| */ |
| @AfterEach |
| public void tearDown() { |
| |
| bean = null; |
| nested = null; |
| |
| } |
| |
| /** |
| * Test the cloneBean() method from a DynaBean. |
| */ |
| @Test |
| void testCloneDynaBean() throws Exception { |
| |
| // Set up an origin bean with customized properties |
| final DynaClass dynaClass = DynaBeanUtilsTest.createDynaClass(); |
| final DynaBean orig = dynaClass.newInstance(); |
| orig.set("booleanProperty", Boolean.FALSE); |
| orig.set("byteProperty", Byte.valueOf((byte) 111)); |
| orig.set("doubleProperty", Double.valueOf(333.33)); |
| orig.set("dupProperty", new String[] { "New 0", "New 1", "New 2" }); |
| orig.set("intArray", new int[] { 100, 200, 300 }); |
| orig.set("intProperty", Integer.valueOf(333)); |
| orig.set("longProperty", Long.valueOf(3333)); |
| orig.set("shortProperty", Short.valueOf((short) 33)); |
| orig.set("stringArray", new String[] { "New 0", "New 1" }); |
| orig.set("stringProperty", "Custom string"); |
| |
| // Copy the origin bean to our destination test bean |
| final DynaBean clonedBean = (DynaBean) BeanUtils.cloneBean(orig); |
| |
| // Validate the results for scalar properties |
| assertEquals(false, ((Boolean) clonedBean.get("booleanProperty")).booleanValue(), "Cloned boolean property"); |
| assertEquals((byte) 111, ((Byte) clonedBean.get("byteProperty")).byteValue(), "Cloned byte property"); |
| assertEquals(333.33, ((Double) clonedBean.get("doubleProperty")).doubleValue(), 0.005, "Cloned double property"); |
| assertEquals(333, ((Integer) clonedBean.get("intProperty")).intValue(), "Cloned int property"); |
| assertEquals(3333, ((Long) clonedBean.get("longProperty")).longValue(), "Cloned long property"); |
| assertEquals((short) 33, ((Short) clonedBean.get("shortProperty")).shortValue(), "Cloned short property"); |
| assertEquals("Custom string", (String) clonedBean.get("stringProperty"), "Cloned string property"); |
| |
| // Validate the results for array properties |
| final String[] dupProperty = (String[]) clonedBean.get("dupProperty"); |
| assertNotNull(dupProperty, "dupProperty present"); |
| assertEquals(3, dupProperty.length, "dupProperty length"); |
| assertEquals("New 0", dupProperty[0], "dupProperty[0]"); |
| assertEquals("New 1", dupProperty[1], "dupProperty[1]"); |
| assertEquals("New 2", dupProperty[2], "dupProperty[2]"); |
| final int[] intArray = (int[]) clonedBean.get("intArray"); |
| assertNotNull(intArray, "intArray present"); |
| assertEquals(3, intArray.length, "intArray length"); |
| assertEquals(100, intArray[0], "intArray[0]"); |
| assertEquals(200, intArray[1], "intArray[1]"); |
| assertEquals(300, intArray[2], "intArray[2]"); |
| final String[] stringArray = (String[]) clonedBean.get("stringArray"); |
| assertNotNull(stringArray, "stringArray present"); |
| assertEquals(2, stringArray.length, "stringArray length"); |
| assertEquals("New 0", stringArray[0], "stringArray[0]"); |
| assertEquals("New 1", stringArray[1], "stringArray[1]"); |
| |
| } |
| |
| /** |
| * Test the copyProperties() method from a DynaBean. |
| */ |
| @Test |
| void testCopyPropertiesDynaBean() throws Exception { |
| |
| // Set up an origin bean with customized properties |
| final DynaClass dynaClass = DynaBeanUtilsTest.createDynaClass(); |
| final DynaBean orig = dynaClass.newInstance(); |
| orig.set("booleanProperty", Boolean.FALSE); |
| orig.set("byteProperty", Byte.valueOf((byte) 111)); |
| orig.set("doubleProperty", Double.valueOf(333.33)); |
| orig.set("dupProperty", new String[] { "New 0", "New 1", "New 2" }); |
| orig.set("intArray", new int[] { 100, 200, 300 }); |
| orig.set("intProperty", Integer.valueOf(333)); |
| orig.set("longProperty", Long.valueOf(3333)); |
| orig.set("shortProperty", Short.valueOf((short) 33)); |
| orig.set("stringArray", new String[] { "New 0", "New 1" }); |
| orig.set("stringProperty", "Custom string"); |
| |
| // Copy the origin bean to our destination test bean |
| BeanUtils.copyProperties(bean, orig); |
| |
| // Validate the results for scalar properties |
| assertEquals(false, ((Boolean) bean.get("booleanProperty")).booleanValue(), "Copied boolean property"); |
| assertEquals((byte) 111, ((Byte) bean.get("byteProperty")).byteValue(), "Copied byte property"); |
| assertEquals(333.33, ((Double) bean.get("doubleProperty")).doubleValue(), 0.005, "Copied double property"); |
| assertEquals(333, ((Integer) bean.get("intProperty")).intValue(), "Copied int property"); |
| assertEquals(3333, ((Long) bean.get("longProperty")).longValue(), "Copied long property"); |
| assertEquals((short) 33, ((Short) bean.get("shortProperty")).shortValue(), "Copied short property"); |
| assertEquals("Custom string", (String) bean.get("stringProperty"), "Copied string property"); |
| |
| // Validate the results for array properties |
| final String[] dupProperty = (String[]) bean.get("dupProperty"); |
| assertNotNull(dupProperty, "dupProperty present"); |
| assertEquals(3, dupProperty.length, "dupProperty length"); |
| assertEquals("New 0", dupProperty[0], "dupProperty[0]"); |
| assertEquals("New 1", dupProperty[1], "dupProperty[1]"); |
| assertEquals("New 2", dupProperty[2], "dupProperty[2]"); |
| final int[] intArray = (int[]) bean.get("intArray"); |
| assertNotNull(intArray, "intArray present"); |
| assertEquals(3, intArray.length, "intArray length"); |
| assertEquals(100, intArray[0], "intArray[0]"); |
| assertEquals(200, intArray[1], "intArray[1]"); |
| assertEquals(300, intArray[2], "intArray[2]"); |
| final String[] stringArray = (String[]) bean.get("stringArray"); |
| assertNotNull(stringArray, "stringArray present"); |
| assertEquals(2, stringArray.length, "stringArray length"); |
| assertEquals("New 0", stringArray[0], "stringArray[0]"); |
| assertEquals("New 1", stringArray[1], "stringArray[1]"); |
| |
| } |
| |
| /** |
| * Test copyProperties() when the origin is a {@code Map}. |
| */ |
| @Test |
| void testCopyPropertiesMap() throws Exception { |
| |
| final Map<String, Object> map = new HashMap<>(); |
| map.put("booleanProperty", "false"); |
| map.put("byteProperty", "111"); |
| map.put("doubleProperty", "333.0"); |
| map.put("dupProperty", new String[] { "New 0", "New 1", "New 2" }); |
| map.put("floatProperty", "222.0"); |
| map.put("intArray", new String[] { "0", "100", "200" }); |
| map.put("intProperty", "111"); |
| map.put("longProperty", "444"); |
| map.put("shortProperty", "555"); |
| map.put("stringProperty", "New String Property"); |
| |
| BeanUtils.copyProperties(bean, map); |
| |
| // Scalar properties |
| assertEquals(false, ((Boolean) bean.get("booleanProperty")).booleanValue(), "booleanProperty"); |
| assertEquals((byte) 111, ((Byte) bean.get("byteProperty")).byteValue(), "byteProperty"); |
| assertEquals(333.0, ((Double) bean.get("doubleProperty")).doubleValue(), 0.005, "doubleProperty"); |
| assertEquals((float) 222.0, ((Float) bean.get("floatProperty")).floatValue(), (float) 0.005, "floatProperty"); |
| assertEquals(111, ((Integer) bean.get("intProperty")).intValue(), "intProperty"); |
| assertEquals(444, ((Long) bean.get("longProperty")).longValue(), "longProperty"); |
| assertEquals((short) 555, ((Short) bean.get("shortProperty")).shortValue(), "shortProperty"); |
| assertEquals("New String Property", (String) bean.get("stringProperty"), "stringProperty"); |
| |
| // Indexed Properties |
| final String[] dupProperty = (String[]) bean.get("dupProperty"); |
| assertNotNull(dupProperty, "dupProperty present"); |
| assertEquals(3, dupProperty.length, "dupProperty length"); |
| assertEquals("New 0", dupProperty[0], "dupProperty[0]"); |
| assertEquals("New 1", dupProperty[1], "dupProperty[1]"); |
| assertEquals("New 2", dupProperty[2], "dupProperty[2]"); |
| final int[] intArray = (int[]) bean.get("intArray"); |
| assertNotNull(intArray, "intArray present"); |
| assertEquals(3, intArray.length, "intArray length"); |
| assertEquals(0, intArray[0], "intArray[0]"); |
| assertEquals(100, intArray[1], "intArray[1]"); |
| assertEquals(200, intArray[2], "intArray[2]"); |
| |
| } |
| |
| /** |
| * Test the copyProperties() method from a standard JavaBean. |
| */ |
| @Test |
| void testCopyPropertiesStandard() throws Exception { |
| |
| // Set up an origin bean with customized properties |
| final TestBean orig = new TestBean(); |
| orig.setBooleanProperty(false); |
| orig.setByteProperty((byte) 111); |
| orig.setDoubleProperty(333.33); |
| orig.setDupProperty(new String[] { "New 0", "New 1", "New 2" }); |
| orig.setIntArray(new int[] { 100, 200, 300 }); |
| orig.setIntProperty(333); |
| orig.setLongProperty(3333); |
| orig.setShortProperty((short) 33); |
| orig.setStringArray(new String[] { "New 0", "New 1" }); |
| orig.setStringProperty("Custom string"); |
| |
| // Copy the origin bean to our destination test bean |
| BeanUtils.copyProperties(bean, orig); |
| |
| // Validate the results for scalar properties |
| assertEquals(false, ((Boolean) bean.get("booleanProperty")).booleanValue(), "Copied boolean property"); |
| assertEquals((byte) 111, ((Byte) bean.get("byteProperty")).byteValue(), "Copied byte property"); |
| assertEquals(333.33, ((Double) bean.get("doubleProperty")).doubleValue(), 0.005, "Copied double property"); |
| assertEquals(333, ((Integer) bean.get("intProperty")).intValue(), "Copied int property"); |
| assertEquals(3333, ((Long) bean.get("longProperty")).longValue(), "Copied long property"); |
| assertEquals((short) 33, ((Short) bean.get("shortProperty")).shortValue(), "Copied short property"); |
| assertEquals("Custom string", (String) bean.get("stringProperty"), "Copied string property"); |
| |
| // Validate the results for array properties |
| final String[] dupProperty = (String[]) bean.get("dupProperty"); |
| assertNotNull(dupProperty, "dupProperty present"); |
| assertEquals(3, dupProperty.length, "dupProperty length"); |
| assertEquals("New 0", dupProperty[0], "dupProperty[0]"); |
| assertEquals("New 1", dupProperty[1], "dupProperty[1]"); |
| assertEquals("New 2", dupProperty[2], "dupProperty[2]"); |
| final int[] intArray = (int[]) bean.get("intArray"); |
| assertNotNull(intArray, "intArray present"); |
| assertEquals(3, intArray.length, "intArray length"); |
| assertEquals(100, intArray[0], "intArray[0]"); |
| assertEquals(200, intArray[1], "intArray[1]"); |
| assertEquals(300, intArray[2], "intArray[2]"); |
| final String[] stringArray = (String[]) bean.get("stringArray"); |
| assertNotNull(stringArray, "stringArray present"); |
| assertEquals(2, stringArray.length, "stringArray length"); |
| assertEquals("New 0", stringArray[0], "stringArray[0]"); |
| assertEquals("New 1", stringArray[1], "stringArray[1]"); |
| |
| } |
| |
| /** |
| * Test narrowing and widening conversions on byte. |
| */ |
| @Test |
| void testCopyPropertyByte() throws Exception { |
| |
| BeanUtils.setProperty(bean, "byteProperty", Byte.valueOf((byte) 123)); |
| assertEquals((byte) 123, ((Byte) bean.get("byteProperty")).byteValue()); |
| /* |
| * BeanUtils.setProperty(bean, "byteProperty", new Double((double) 123)); assertEquals((byte) 123, ((Byte) bean.get("byteProperty")).byteValue()); |
| * BeanUtils.setProperty(bean, "byteProperty", new Float((float) 123)); assertEquals((byte) 123, ((Byte) bean.get("byteProperty")).byteValue()); |
| */ |
| BeanUtils.setProperty(bean, "byteProperty", Integer.valueOf(123)); |
| assertEquals((byte) 123, ((Byte) bean.get("byteProperty")).byteValue()); |
| BeanUtils.setProperty(bean, "byteProperty", Long.valueOf(123)); |
| assertEquals((byte) 123, ((Byte) bean.get("byteProperty")).byteValue()); |
| BeanUtils.setProperty(bean, "byteProperty", Short.valueOf((short) 123)); |
| assertEquals((byte) 123, ((Byte) bean.get("byteProperty")).byteValue()); |
| |
| } |
| |
| /** |
| * Test narrowing and widening conversions on double. |
| */ |
| @Test |
| void testCopyPropertyDouble() throws Exception { |
| |
| BeanUtils.setProperty(bean, "doubleProperty", Byte.valueOf((byte) 123)); |
| assertEquals(123, ((Double) bean.get("doubleProperty")).doubleValue(), 0.005); |
| BeanUtils.setProperty(bean, "doubleProperty", Double.valueOf(123)); |
| assertEquals(123, ((Double) bean.get("doubleProperty")).doubleValue(), 0.005); |
| BeanUtils.setProperty(bean, "doubleProperty", Float.valueOf(123)); |
| assertEquals(123, ((Double) bean.get("doubleProperty")).doubleValue(), 0.005); |
| BeanUtils.setProperty(bean, "doubleProperty", Integer.valueOf(123)); |
| assertEquals(123, ((Double) bean.get("doubleProperty")).doubleValue(), 0.005); |
| BeanUtils.setProperty(bean, "doubleProperty", Long.valueOf(123)); |
| assertEquals(123, ((Double) bean.get("doubleProperty")).doubleValue(), 0.005); |
| BeanUtils.setProperty(bean, "doubleProperty", Short.valueOf((short) 123)); |
| assertEquals(123, ((Double) bean.get("doubleProperty")).doubleValue(), 0.005); |
| |
| } |
| |
| /** |
| * Test narrowing and widening conversions on float. |
| */ |
| @Test |
| void testCopyPropertyFloat() throws Exception { |
| |
| BeanUtils.setProperty(bean, "floatProperty", Byte.valueOf((byte) 123)); |
| assertEquals(123, ((Float) bean.get("floatProperty")).floatValue(), 0.005); |
| BeanUtils.setProperty(bean, "floatProperty", Double.valueOf(123)); |
| assertEquals(123, ((Float) bean.get("floatProperty")).floatValue(), 0.005); |
| BeanUtils.setProperty(bean, "floatProperty", Float.valueOf(123)); |
| assertEquals(123, ((Float) bean.get("floatProperty")).floatValue(), 0.005); |
| BeanUtils.setProperty(bean, "floatProperty", Integer.valueOf(123)); |
| assertEquals(123, ((Float) bean.get("floatProperty")).floatValue(), 0.005); |
| BeanUtils.setProperty(bean, "floatProperty", Long.valueOf(123)); |
| assertEquals(123, ((Float) bean.get("floatProperty")).floatValue(), 0.005); |
| BeanUtils.setProperty(bean, "floatProperty", Short.valueOf((short) 123)); |
| assertEquals(123, ((Float) bean.get("floatProperty")).floatValue(), 0.005); |
| |
| } |
| |
| /** |
| * Test narrowing and widening conversions on int. |
| */ |
| @Test |
| void testCopyPropertyInteger() throws Exception { |
| |
| BeanUtils.setProperty(bean, "longProperty", Byte.valueOf((byte) 123)); |
| assertEquals(123, ((Integer) bean.get("intProperty")).intValue()); |
| /* |
| * BeanUtils.setProperty(bean, "longProperty", new Double((double) 123)); assertEquals((int) 123, ((Integer) bean.get("intProperty")).intValue()); |
| * BeanUtils.setProperty(bean, "longProperty", new Float((float) 123)); assertEquals((int) 123, ((Integer) bean.get("intProperty")).intValue()); |
| */ |
| BeanUtils.setProperty(bean, "longProperty", Integer.valueOf(123)); |
| assertEquals(123, ((Integer) bean.get("intProperty")).intValue()); |
| BeanUtils.setProperty(bean, "longProperty", Long.valueOf(123)); |
| assertEquals(123, ((Integer) bean.get("intProperty")).intValue()); |
| BeanUtils.setProperty(bean, "longProperty", Short.valueOf((short) 123)); |
| assertEquals(123, ((Integer) bean.get("intProperty")).intValue()); |
| |
| } |
| |
| /** |
| * Test narrowing and widening conversions on long. |
| */ |
| @Test |
| void testCopyPropertyLong() throws Exception { |
| |
| BeanUtils.setProperty(bean, "longProperty", Byte.valueOf((byte) 123)); |
| assertEquals(123, ((Long) bean.get("longProperty")).longValue()); |
| /* |
| * BeanUtils.setProperty(bean, "longProperty", new Double((double) 123)); assertEquals((long) 123, ((Long) bean.get("longProperty")).longValue()); |
| * BeanUtils.setProperty(bean, "longProperty", new Float((float) 123)); assertEquals((long) 123, ((Long) bean.get("longProperty")).longValue()); |
| */ |
| BeanUtils.setProperty(bean, "longProperty", Integer.valueOf(123)); |
| assertEquals(123, ((Long) bean.get("longProperty")).longValue()); |
| BeanUtils.setProperty(bean, "longProperty", Long.valueOf(123)); |
| assertEquals(123, ((Long) bean.get("longProperty")).longValue()); |
| BeanUtils.setProperty(bean, "longProperty", Short.valueOf((short) 123)); |
| assertEquals(123, ((Long) bean.get("longProperty")).longValue()); |
| |
| } |
| |
| /** |
| * Test copying a property using a nested indexed array expression, with and without conversions. |
| */ |
| @Test |
| void testCopyPropertyNestedIndexedArray() throws Exception { |
| |
| final int[] origArray = { 0, 10, 20, 30, 40 }; |
| final int[] intArray = { 0, 0, 0 }; |
| ((TestBean) bean.get("nested")).setIntArray(intArray); |
| final int[] intChanged = { 0, 0, 0 }; |
| |
| // No conversion required |
| BeanUtils.copyProperty(bean, "nested.intArray[1]", Integer.valueOf(1)); |
| checkIntArray((int[]) bean.get("intArray"), origArray); |
| intChanged[1] = 1; |
| checkIntArray(((TestBean) bean.get("nested")).getIntArray(), intChanged); |
| |
| // Widening conversion required |
| BeanUtils.copyProperty(bean, "nested.intArray[1]", Byte.valueOf((byte) 2)); |
| checkIntArray((int[]) bean.get("intArray"), origArray); |
| intChanged[1] = 2; |
| checkIntArray(((TestBean) bean.get("nested")).getIntArray(), intChanged); |
| |
| // Narrowing conversion required |
| BeanUtils.copyProperty(bean, "nested.intArray[1]", Long.valueOf(3)); |
| checkIntArray((int[]) bean.get("intArray"), origArray); |
| intChanged[1] = 3; |
| checkIntArray(((TestBean) bean.get("nested")).getIntArray(), intChanged); |
| |
| // String conversion required |
| BeanUtils.copyProperty(bean, "nested.intArray[1]", "4"); |
| checkIntArray((int[]) bean.get("intArray"), origArray); |
| intChanged[1] = 4; |
| checkIntArray(((TestBean) bean.get("nested")).getIntArray(), intChanged); |
| |
| } |
| |
| /** |
| * Test copying a property using a nested mapped map property. |
| */ |
| @Test |
| void testCopyPropertyNestedMappedMap() throws Exception { |
| |
| final Map<String, Object> origMap = new HashMap<>(); |
| origMap.put("First Key", "First Value"); |
| origMap.put("Second Key", "Second Value"); |
| final Map<String, Object> changedMap = new HashMap<>(); |
| changedMap.put("First Key", "First Value"); |
| changedMap.put("Second Key", "Second Value"); |
| |
| // No conversion required |
| BeanUtils.copyProperty(bean, "nested.mapProperty(Second Key)", "New Second Value"); |
| checkMap((Map<?, ?>) bean.get("mapProperty"), origMap); |
| changedMap.put("Second Key", "New Second Value"); |
| checkMap(((TestBean) bean.get("nested")).getMapProperty(), changedMap); |
| |
| } |
| |
| /** |
| * Test copying a property using a nested simple expression, with and without conversions. |
| */ |
| @Test |
| void testCopyPropertyNestedSimple() throws Exception { |
| |
| bean.set("intProperty", Integer.valueOf(0)); |
| nested.setIntProperty(0); |
| |
| // No conversion required |
| BeanUtils.copyProperty(bean, "nested.intProperty", Integer.valueOf(1)); |
| assertEquals(0, ((Integer) bean.get("intProperty")).intValue()); |
| assertEquals(1, nested.getIntProperty()); |
| |
| // Widening conversion required |
| BeanUtils.copyProperty(bean, "nested.intProperty", Byte.valueOf((byte) 2)); |
| assertEquals(0, ((Integer) bean.get("intProperty")).intValue()); |
| assertEquals(2, nested.getIntProperty()); |
| |
| // Narrowing conversion required |
| BeanUtils.copyProperty(bean, "nested.intProperty", Long.valueOf(3)); |
| assertEquals(0, ((Integer) bean.get("intProperty")).intValue()); |
| assertEquals(3, nested.getIntProperty()); |
| |
| // String conversion required |
| BeanUtils.copyProperty(bean, "nested.intProperty", "4"); |
| assertEquals(0, ((Integer) bean.get("intProperty")).intValue()); |
| assertEquals(4, nested.getIntProperty()); |
| |
| } |
| |
| /** |
| * Test copying a null property value. |
| */ |
| @Test |
| void testCopyPropertyNull() throws Exception { |
| |
| bean.set("nullProperty", "non-null value"); |
| BeanUtils.copyProperty(bean, "nullProperty", null); |
| assertNull(bean.get("nullProperty"), "nullProperty is null"); |
| |
| } |
| |
| /** |
| * Test narrowing and widening conversions on short. |
| */ |
| @Test |
| void testCopyPropertyShort() throws Exception { |
| |
| BeanUtils.setProperty(bean, "shortProperty", Byte.valueOf((byte) 123)); |
| assertEquals((short) 123, ((Short) bean.get("shortProperty")).shortValue()); |
| /* |
| * BeanUtils.setProperty(bean, "shortProperty", new Double((double) 123)); assertEquals((short) 123, ((Short) bean.get("shortProperty")).shortValue()); |
| * BeanUtils.setProperty(bean, "shortProperty", new Float((float) 123)); assertEquals((short) 123, ((Short) bean.get("shortProperty")).shortValue()); |
| */ |
| BeanUtils.setProperty(bean, "shortProperty", Integer.valueOf(123)); |
| assertEquals((short) 123, ((Short) bean.get("shortProperty")).shortValue()); |
| BeanUtils.setProperty(bean, "shortProperty", Long.valueOf(123)); |
| assertEquals((short) 123, ((Short) bean.get("shortProperty")).shortValue()); |
| BeanUtils.setProperty(bean, "shortProperty", Short.valueOf((short) 123)); |
| assertEquals((short) 123, ((Short) bean.get("shortProperty")).shortValue()); |
| |
| } |
| |
| /** |
| * Test the describe() method. |
| */ |
| @Test |
| void testDescribe() throws Exception { |
| |
| final Map<String, Object> map = PropertyUtils.describe(bean); |
| |
| // Verify existence of all the properties that should be present |
| for (final String describe : describes) { |
| assertTrue(map.containsKey(describe), "Property '" + describe + "' is present"); |
| } |
| assertFalse(map.containsKey("writeOnlyProperty"), "Property 'writeOnlyProperty' is not present"); |
| |
| // Verify the values of scalar properties |
| assertEquals(Boolean.TRUE, map.get("booleanProperty"), "Value of 'booleanProperty'"); |
| assertEquals(Byte.valueOf((byte) 121), map.get("byteProperty"), "Value of 'byteProperty'"); |
| assertEquals(Double.valueOf(321.0), map.get("doubleProperty"), "Value of 'doubleProperty'"); |
| assertEquals(Float.valueOf((float) 123.0), map.get("floatProperty"), "Value of 'floatProperty'"); |
| assertEquals(Integer.valueOf(123), map.get("intProperty"), "Value of 'intProperty'"); |
| assertEquals(Long.valueOf(321), map.get("longProperty"), "Value of 'longProperty'"); |
| assertEquals(Short.valueOf((short) 987), map.get("shortProperty"), "Value of 'shortProperty'"); |
| assertEquals("This is a string", (String) map.get("stringProperty"), "Value of 'stringProperty'"); |
| |
| } |
| |
| /** |
| * tests the string and int arrays of TestBean |
| */ |
| @Test |
| void testGetArrayProperty() throws Exception { |
| String[] arr = BeanUtils.getArrayProperty(bean, "stringArray"); |
| final String[] comp = (String[]) bean.get("stringArray"); |
| |
| assertEquals(comp.length, arr.length, "String array length = " + comp.length); |
| |
| arr = BeanUtils.getArrayProperty(bean, "intArray"); |
| final int[] iarr = (int[]) bean.get("intArray"); |
| |
| assertEquals(iarr.length, arr.length, "String array length = " + iarr.length); |
| } |
| |
| /** |
| * tests getting a 'whatever' property |
| */ |
| @Test |
| void testGetGeneralProperty() throws Exception { |
| final String val = BeanUtils.getProperty(bean, "nested.intIndexed[2]"); |
| final String comp = String.valueOf(bean.get("intIndexed", 2)); |
| |
| assertEquals(val, comp, "nested.intIndexed[2] == " + comp); |
| } |
| |
| /** |
| * tests getting an indexed property |
| */ |
| @Test |
| void testGetIndexedProperty1() throws Exception { |
| String val = BeanUtils.getIndexedProperty(bean, "intIndexed[3]"); |
| String comp = String.valueOf(bean.get("intIndexed", 3)); |
| assertEquals(val, comp, "intIndexed[3] == " + comp); |
| |
| val = BeanUtils.getIndexedProperty(bean, "stringIndexed[3]"); |
| comp = (String) bean.get("stringIndexed", 3); |
| assertEquals(val, comp, "stringIndexed[3] == " + comp); |
| } |
| |
| /** |
| * tests getting an indexed property |
| */ |
| @Test |
| void testGetIndexedProperty2() throws Exception { |
| String val = BeanUtils.getIndexedProperty(bean, "intIndexed", 3); |
| String comp = String.valueOf(bean.get("intIndexed", 3)); |
| |
| assertEquals(val, comp, "intIndexed,3 == " + comp); |
| |
| val = BeanUtils.getIndexedProperty(bean, "stringIndexed", 3); |
| comp = (String) bean.get("stringIndexed", 3); |
| |
| assertEquals(val, comp, "stringIndexed,3 == " + comp); |
| } |
| |
| /** |
| * tests getting a nested property |
| */ |
| @Test |
| void testGetNestedProperty() throws Exception { |
| final String val = BeanUtils.getNestedProperty(bean, "nested.stringProperty"); |
| final String comp = nested.getStringProperty(); |
| assertEquals(val, comp, "nested.StringProperty == " + comp); |
| } |
| |
| /** |
| * tests getting a 'whatever' property |
| */ |
| @Test |
| void testGetSimpleProperty() throws Exception { |
| final String val = BeanUtils.getSimpleProperty(bean, "shortProperty"); |
| final String comp = String.valueOf(bean.get("shortProperty")); |
| |
| assertEquals(val, comp, "shortProperty == " + comp); |
| } |
| |
| /** |
| * Test populate() method on individual array elements. |
| */ |
| @Test |
| void testPopulateArrayElements() throws Exception { |
| final HashMap<String, Object> map = new HashMap<>(); |
| map.put("intIndexed[0]", "100"); |
| map.put("intIndexed[2]", "120"); |
| map.put("intIndexed[4]", "140"); |
| |
| BeanUtils.populate(bean, map); |
| final Integer intIndexed0 = (Integer) bean.get("intIndexed", 0); |
| assertEquals(100, intIndexed0.intValue(), "intIndexed[0] is 100"); |
| final Integer intIndexed1 = (Integer) bean.get("intIndexed", 1); |
| assertEquals(10, intIndexed1.intValue(), "intIndexed[1] is 10"); |
| final Integer intIndexed2 = (Integer) bean.get("intIndexed", 2); |
| assertEquals(120, intIndexed2.intValue(), "intIndexed[2] is 120"); |
| final Integer intIndexed3 = (Integer) bean.get("intIndexed", 3); |
| assertEquals(30, intIndexed3.intValue(), "intIndexed[3] is 30"); |
| final Integer intIndexed4 = (Integer) bean.get("intIndexed", 4); |
| assertEquals(140, intIndexed4.intValue(), "intIndexed[4] is 140"); |
| |
| map.clear(); |
| map.put("stringIndexed[1]", "New String 1"); |
| map.put("stringIndexed[3]", "New String 3"); |
| |
| BeanUtils.populate(bean, map); |
| |
| assertEquals("String 0", (String) bean.get("stringIndexed", 0), "stringIndexed[0] is \"String 0\""); |
| assertEquals("New String 1", (String) bean.get("stringIndexed", 1), "stringIndexed[1] is \"New String 1\""); |
| assertEquals("String 2", (String) bean.get("stringIndexed", 2), "stringIndexed[2] is \"String 2\""); |
| assertEquals("New String 3", (String) bean.get("stringIndexed", 3), "stringIndexed[3] is \"New String 3\""); |
| assertEquals("String 4", (String) bean.get("stringIndexed", 4), "stringIndexed[4] is \"String 4\""); |
| } |
| |
| /** |
| * Test populate() method on array properties as a whole. |
| */ |
| @Test |
| void testPopulateArrayProperties() throws Exception { |
| final HashMap<String, Object> map = new HashMap<>(); |
| // int[] intArray = new int[] { 123, 456, 789 }; |
| final String[] intArrayIn = { "123", "456", "789" }; |
| map.put("intArray", intArrayIn); |
| String[] stringArray = { "New String 0", "New String 1" }; |
| map.put("stringArray", stringArray); |
| |
| BeanUtils.populate(bean, map); |
| |
| final int[] intArray = (int[]) bean.get("intArray"); |
| assertNotNull(intArray, "intArray is present"); |
| assertEquals(3, intArray.length, "intArray length"); |
| assertEquals(123, intArray[0], "intArray[0]"); |
| assertEquals(456, intArray[1], "intArray[1]"); |
| assertEquals(789, intArray[2], "intArray[2]"); |
| stringArray = (String[]) bean.get("stringArray"); |
| assertNotNull(stringArray, "stringArray is present"); |
| assertEquals(2, stringArray.length, "stringArray length"); |
| assertEquals("New String 0", stringArray[0], "stringArray[0]"); |
| assertEquals("New String 1", stringArray[1], "stringArray[1]"); |
| } |
| |
| /** |
| * Test populate() on mapped properties. |
| */ |
| @Test |
| void testPopulateMapped() throws Exception { |
| final HashMap<String, Object> map = new HashMap<>(); |
| map.put("mappedProperty(First Key)", "New First Value"); |
| map.put("mappedProperty(Third Key)", "New Third Value"); |
| |
| BeanUtils.populate(bean, map); |
| |
| assertEquals("New First Value", (String) bean.get("mappedProperty", "First Key"), "mappedProperty(First Key)"); |
| assertEquals("Second Value", (String) bean.get("mappedProperty", "Second Key"), "mappedProperty(Second Key)"); |
| assertEquals("New Third Value", (String) bean.get("mappedProperty", "Third Key"), "mappedProperty(Third Key)"); |
| assertNull(bean.get("mappedProperty", "Fourth Key"), "mappedProperty(Fourth Key"); |
| } |
| |
| /** |
| * Test populate() method on nested properties. |
| */ |
| @Test |
| void testPopulateNested() throws Exception { |
| final HashMap<String, Object> map = new HashMap<>(); |
| map.put("nested.booleanProperty", "false"); |
| // booleanSecond is left at true |
| map.put("nested.doubleProperty", "432.0"); |
| // floatProperty is left at 123.0 |
| map.put("nested.intProperty", "543"); |
| // longProperty is left at 321 |
| map.put("nested.shortProperty", "654"); |
| // stringProperty is left at "This is a string" |
| |
| BeanUtils.populate(bean, map); |
| |
| final TestBean nested = (TestBean) bean.get("nested"); |
| assertFalse(nested.getBooleanProperty(), "booleanProperty is false"); |
| assertTrue(nested.isBooleanSecond(), "booleanSecond is true"); |
| assertEquals(432.0, nested.getDoubleProperty(), 0.005, "doubleProperty is 432.0"); |
| assertEquals((float) 123.0, nested.getFloatProperty(), (float) 0.005, "floatProperty is 123.0"); |
| assertEquals(543, nested.getIntProperty(), "intProperty is 543"); |
| assertEquals(321, nested.getLongProperty(), "longProperty is 321"); |
| assertEquals((short) 654, nested.getShortProperty(), "shortProperty is 654"); |
| assertEquals("This is a string", nested.getStringProperty(), "stringProperty is \"This is a string\""); |
| } |
| |
| /** |
| * Test populate() method on scalar properties. |
| */ |
| @Test |
| void testPopulateScalar() throws Exception { |
| bean.set("nullProperty", "non-null value"); |
| |
| final HashMap<String, Object> map = new HashMap<>(); |
| map.put("booleanProperty", "false"); |
| // booleanSecond is left at true |
| map.put("doubleProperty", "432.0"); |
| // floatProperty is left at 123.0 |
| map.put("intProperty", "543"); |
| // longProperty is left at 321 |
| map.put("nullProperty", null); |
| map.put("shortProperty", "654"); |
| // stringProperty is left at "This is a string" |
| |
| BeanUtils.populate(bean, map); |
| |
| final Boolean booleanProperty = (Boolean) bean.get("booleanProperty"); |
| assertFalse(booleanProperty.booleanValue(), "booleanProperty is false"); |
| final Boolean booleanSecond = (Boolean) bean.get("booleanSecond"); |
| assertTrue(booleanSecond.booleanValue(), "booleanSecond is true"); |
| final Double doubleProperty = (Double) bean.get("doubleProperty"); |
| assertEquals(432.0, doubleProperty.doubleValue(), 0.005, "doubleProperty is 432.0"); |
| final Float floatProperty = (Float) bean.get("floatProperty"); |
| assertEquals((float) 123.0, floatProperty.floatValue(), (float) 0.005, "floatProperty is 123.0"); |
| final Integer intProperty = (Integer) bean.get("intProperty"); |
| assertEquals(543, intProperty.intValue(), "intProperty is 543"); |
| final Long longProperty = (Long) bean.get("longProperty"); |
| assertEquals(321, longProperty.longValue(), "longProperty is 321"); |
| assertNull(bean.get("nullProperty"), "nullProperty is null"); |
| final Short shortProperty = (Short) bean.get("shortProperty"); |
| assertEquals((short) 654, shortProperty.shortValue(), "shortProperty is 654"); |
| assertEquals("This is a string", (String) bean.get("stringProperty"), "stringProperty is \"This is a string\""); |
| } |
| |
| /** |
| * Test setting a null property value. |
| */ |
| @Test |
| void testSetPropertyNull() throws Exception { |
| |
| bean.set("nullProperty", "non-null value"); |
| BeanUtils.setProperty(bean, "nullProperty", null); |
| assertNull(bean.get("nullProperty"), "nullProperty is null"); |
| |
| } |
| |
| /** |
| * Test calling setProperty() with null property values. |
| */ |
| @Test |
| void testSetPropertyNullValues() throws Exception { |
| |
| Object oldValue; |
| Object newValue; |
| |
| // Scalar value into array |
| oldValue = PropertyUtils.getSimpleProperty(bean, "stringArray"); |
| BeanUtils.setProperty(bean, "stringArray", null); |
| newValue = PropertyUtils.getSimpleProperty(bean, "stringArray"); |
| assertNotNull(newValue, "stringArray is not null"); |
| assertInstanceOf(String[].class, newValue, "stringArray of correct type"); |
| assertEquals(1, ((String[]) newValue).length, "stringArray length"); |
| PropertyUtils.setProperty(bean, "stringArray", oldValue); |
| |
| // Indexed value into array |
| oldValue = PropertyUtils.getSimpleProperty(bean, "stringArray"); |
| BeanUtils.setProperty(bean, "stringArray[2]", null); |
| newValue = PropertyUtils.getSimpleProperty(bean, "stringArray"); |
| assertNotNull(newValue, "stringArray is not null"); |
| assertInstanceOf(String[].class, newValue, "stringArray of correct type"); |
| assertEquals(5, ((String[]) newValue).length, "stringArray length"); |
| assertNull(((String[]) newValue)[2], "stringArray[2] is null"); |
| PropertyUtils.setProperty(bean, "stringArray", oldValue); |
| |
| // Value into scalar |
| BeanUtils.setProperty(bean, "stringProperty", null); |
| assertNull(BeanUtils.getProperty(bean, "stringProperty"), "stringProperty is now null"); |
| |
| } |
| |
| /** |
| * Test converting to and from primitive wrapper types. |
| */ |
| @Test |
| void testSetPropertyOnPrimitiveWrappers() throws Exception { |
| |
| BeanUtils.setProperty(bean, "intProperty", Integer.valueOf(1)); |
| assertEquals(1, ((Integer) bean.get("intProperty")).intValue()); |
| BeanUtils.setProperty(bean, "stringProperty", Integer.valueOf(1)); |
| assertEquals(1, Integer.parseInt((String) bean.get("stringProperty"))); |
| |
| } |
| |
| } |