Apache Commons BeanUtils Example
1. Introduction
Apache Common BeanUtils is one of the most common Java library. The latest version at the time of writing is 1.9.3 and published at September 26, 2016.
BeanUtils provides utility methods for populating JavaBeans properties. In this example, I will demonstrate the following methods:
static Object cloneBean(Object bean)
– Clones a bean even if the bean class does not implementCloneable
.static void copyProperties(Object dest, Object orig)
– Copies property values from the original bean to the destination bean where the property names are the same.static String getIndexedProperty(Object bean, String name)
– Returns theString
value of the specified indexed property of the specified bean.static String getMappedProperty(Object bean, String name)
– Returns theString
value of the specified mapped property of the specified bean.static String getNestedProperty(Object bean, String name)
– Returns theString
value of the nested property of the specified name for the specified bean.static String getProperty(Object bean, String name)
– Returns theString
value of the specified property of the specified bean.static String getSimpleProperty(Object bean, String name)
– Returns theString
value of the specified simple property of the specified bean.static void setProperty(Object bean, String name, Object value)
– Sets the specified property value, performing type conversions as required to conform to the type of the destination property.
2. Technologies used
The example code in this article was built and run using:
- Java 1.11
- Maven 3.3.9
- Eclipse Oxygen
- JUnit 4.12
- Apache commons-beanutils 1.9.3
3. Maven Project
3.1 Dependency
Add JUnit
and commons-beanutils
to pom.xml
.
pom.xml
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>jcg.zheng.demo</groupId> <artifactId>java-beanutils-demo</artifactId> <version>0.0.1-SNAPSHOT</version> <build> <sourceDirectory>src</sourceDirectory> <plugins> <plugin> <artifactId>maven-compiler-plugin</artifactId> <version>3.8.0</version> <configuration> <release>11</release> </configuration> </plugin> </plugins> </build> <dependencies> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>4.12</version> </dependency> <!-- https://mvnrepository.com/artifact/commons-beanutils/commons-beanutils --> <dependency> <groupId>commons-beanutils</groupId> <artifactId>commons-beanutils</artifactId> <version>1.9.3</version> </dependency> </dependencies> </project>
4. JavaBeans
In this step, I will create four Java classes:
Contact
– It is a JavaBean which has two simple properties:firstName
andlastName
; a collection oftopics
; a map ofaddtionalProperties
; two complex data:cellPhone
andhomePhone
.Person
– It is a JavaBean which has similar members asContact
with two more data members:age
andsomeData
.Phone
– It is a JavaBean which has four simple properties:areaCode
,countryCode
,extension
, andphoneNum
.NoDefaultConstructrorPOJO
– It is a POJO with a non-default constructor. I will use it to demonstrate that callingBeanUtils.cloneBean
for non-JavaBean will throw an exception.
4.1 Contact
In this step, I will create a Contact
JavaBean which has simple, indexed, mapped, and nested properties.
Contact.java
package jcg.zheng.demo.data; import java.util.ArrayList; import java.util.HashMap; import java.util.List; public class Contact { private HashMap<String, String> addtionalProperties = new HashMap<>(); private Phone cellPhone; private String firstName; private Phone homePhone; private String lastName; private List<String> topics = new ArrayList<>(); public Contact() { super(); } public HashMap<String, String> getAddtionalProperties() { return addtionalProperties; } public Phone getCellPhone() { return cellPhone; } public String getFirstName() { return firstName; } public Phone getHomePhone() { return homePhone; } public String getLastName() { return lastName; } public List<String> getTopics() { return topics; } public void setAddtionalProperties(HashMap<String, String> addtionalProperties) { this.addtionalProperties = addtionalProperties; } public void setCellPhone(Phone cellPhone) { this.cellPhone = cellPhone; } public void setFirstName(String firstName) { this.firstName = firstName; } public void setHomePhone(Phone homePhone) { this.homePhone = homePhone; } public void setLastName(String lastName) { this.lastName = lastName; } public void setTopics(List<String> topics) { this.topics = topics; } }
4.2 Person
In this step, I will create a Person
JavaBean which has similar members as the Contact
class with two more data members: age
and someData
.
Person.java
package jcg.zheng.demo.data; import java.util.ArrayList; import java.util.HashMap; import java.util.List; public class Person { private HashMap<String, String> addtionalProperties = new HashMap<>(); private int age; private Phone cellPhone; private String firstName; private Phone homePhone; private String lastName; private Boolean someData; private List<String> topics = new ArrayList<>(); public Person() { super(); } public HashMap<String, String> getAddtionalProperties() { return addtionalProperties; } public int getAge() { return age; } public Phone getCellPhone() { return cellPhone; } public String getDummy() { return "Dummy"; } public String getFirstName() { return firstName; } public Phone getHomePhone() { return homePhone; } public String getLastName() { return lastName; } public Boolean getSomeData() { return someData; } public List<String> getTopics() { return topics; } public void setAddtionalProperties(HashMap<String, String> addtionalProperties) { this.addtionalProperties = addtionalProperties; } public void setAge(int age) { this.age = age; } public void setCellPhone(Phone cellPhone) { this.cellPhone = cellPhone; } public void setFirstName(String firstName) { this.firstName = firstName; } public void setHomePhone(Phone homePhone) { this.homePhone = homePhone; } public void setLastName(String lastName) { this.lastName = lastName; } public void setSomeData(Boolean dataNotINContact) { this.someData = dataNotINContact; } public void setTopics(List<String> topics) { this.topics = topics; } /** * This is not following JavaBean Property pattern, so it will not be used by BeanUtils * @return */ public boolean isSomeData() { return someData == null ? false : someData.booleanValue(); } }
4.3 Phone
In this step, I will create a Phone
JavaBean which has simple properties.
Phone.java
package jcg.zheng.demo.data; public class Phone { private String areaCode; private String countryCode; private String extension; private String phoneNum; public Phone() { super(); } public String getAreaCode() { return areaCode; } public String getCountryCode() { return countryCode; } public String getExtension() { return extension; } public String getPhoneNum() { return phoneNum; } public void setAreaCode(String areaCode) { this.areaCode = areaCode; } public void setCountryCode(String countryCode) { this.countryCode = countryCode; } public void setExtension(String extension) { this.extension = extension; } public void setPhoneNum(String phoneNum) { this.phoneNum = phoneNum; } }
4.4 NoDefaultConstructorPOJO
In this step, I will create a class which does not have a default constructor. It will be used to demonstrate the exception thrown by the BeanUtils.cloneBean
method.
NoDefaultConstructorPOJO.java
package jcg.zheng.demo.data; public class NoDefaultConstructorPOJO { private String name; public NoDefaultConstructorPOJO(String name) { super(); this.name = name; } public String getName() { return name; } public void setName(String name) { this.name = name; } }
5. JUnit Tests
I will create several JUnit tests to demonstrate how to use BeanUtils
to copy a JavaBean, clone a JavaBean, get JavaBean’s property, and set JavaBean’s property.
5.1 TestBase
In this step, I will create a TestBase
class to set up the constants and data used in all the test classes.
TestBase.java
package jcg.zheng.demo; import static org.junit.Assert.assertEquals; import static org.junit.Assert.fail; import java.util.Arrays; import java.util.HashMap; import java.util.Map; import org.apache.commons.beanutils.BeanUtils; import org.junit.Before; import org.junit.Test; import jcg.zheng.demo.data.Contact; import jcg.zheng.demo.data.Phone; public class TestBase { protected static final String KEY_1 = "Color"; protected static final String KEY_2 = "Food"; protected static final String SHOULD_NOT_REACH = "should not reach here!"; protected static final String TOPIC_1 = "Interface design"; protected static final String TOPIC_2 = "BeanUtils"; protected static final String TOPIC_3 = "Functional Interface"; protected static final String VALUE_1 = "Purple"; protected static final String VALUE_2 = "Rice"; protected Contact mary; public TestBase() { super(); } protected Contact buildContact(String firstName, String lastName) { Contact contact = new Contact(); contact.setFirstName(firstName); contact.setLastName(lastName); contact.setTopics(Arrays.asList(TOPIC_1, TOPIC_2, TOPIC_3)); HashMap<String, String> addtionalProperties = new HashMap<>(); addtionalProperties.put(KEY_1, VALUE_1); addtionalProperties.put(KEY_2, VALUE_2); contact.setAddtionalProperties(addtionalProperties); contact.setCellPhone(buildPhone("8197000")); contact.setHomePhone(buildPhone("5272943")); return contact; } protected Phone buildPhone(String phoneNum) { Phone cellPhone = new Phone(); cellPhone.setCountryCode("01"); cellPhone.setAreaCode("314"); cellPhone.setPhoneNum(phoneNum); return cellPhone; } @Before public void setup() { mary = buildContact("Mary", "Zheng"); } @Test public void test_describe() { try { Map<String, String> maryContactMeta = BeanUtils.describe(mary); assertEquals("Mary", maryContactMeta.get("firstName")); assertEquals("Zheng", maryContactMeta.get("lastName")); assertEquals("{Color=Purple, Food=Rice}", maryContactMeta.get("addtionalProperties")); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } }
Execute mvn test -Dtest=TestBase
and capture the output.
TestBase Output
Running jcg.zheng.demo.TestBase Tests run: 1, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.281 sec Results : Tests run: 1, Failures: 0, Errors: 0, Skipped: 0 [INFO] ------------------------------------------------------------------------ [INFO] BUILD SUCCESS [INFO] ------------------------------------------------------------------------ [INFO] Total time: 9.263 s [INFO] Finished at: 2019-07-19T20:42:52-05:00 [INFO] ------------------------------------------------------------------------ C:\MaryZheng\Workspaces\jdk12\java-beanutils-demo>
5.2 CloneBeanTest
In this step, I will create a CloneBeanTest
class to show how to use cloneBean
to clone a JavaBean. It will throw InstantiationException
when cloning a POJO which does not have a default constructor.
CloneBeanTest.java
package jcg.zheng.demo; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNotNull; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import org.apache.commons.beanutils.BeanUtils; import org.junit.Test; import jcg.zheng.demo.data.Contact; import jcg.zheng.demo.data.NoDefaultConstructorPOJO; import jcg.zheng.demo.data.Person; public class CloneBeanTest extends TestBase { @Test public void test_cloneBean() { try { Contact cloneMary = (Contact) BeanUtils.cloneBean(mary); assertEquals(mary.getFirstName(), cloneMary.getFirstName()); assertEquals(mary.getLastName(), cloneMary.getLastName()); assertNotNull(cloneMary.getCellPhone()); assertEquals(mary.getCellPhone().getAreaCode(), cloneMary.getCellPhone().getAreaCode()); assertEquals(mary.getCellPhone().getCountryCode(), cloneMary.getCellPhone().getCountryCode()); assertEquals(mary.getCellPhone().getPhoneNum(), cloneMary.getCellPhone().getPhoneNum()); assertNotNull(cloneMary.getHomePhone()); assertEquals(mary.getHomePhone().getAreaCode(), cloneMary.getHomePhone().getAreaCode()); assertEquals(mary.getHomePhone().getCountryCode(), cloneMary.getHomePhone().getCountryCode()); assertEquals(mary.getHomePhone().getPhoneNum(), cloneMary.getHomePhone().getPhoneNum()); assertNotNull(cloneMary.getTopics()); assertEquals(mary.getTopics().size(), cloneMary.getTopics().size()); assertTrue(cloneMary.getTopics().contains(TOPIC_1)); assertTrue(cloneMary.getTopics().contains(TOPIC_2)); assertTrue(cloneMary.getTopics().contains(TOPIC_3)); assertNotNull(cloneMary.getAddtionalProperties()); assertEquals(mary.getAddtionalProperties().size(), cloneMary.getAddtionalProperties().size()); assertEquals(mary.getAddtionalProperties().get(KEY_1), cloneMary.getAddtionalProperties().get(KEY_1)); assertEquals(mary.getAddtionalProperties().get(KEY_2), cloneMary.getAddtionalProperties().get(KEY_2)); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void test_cloneBean_error_NoDefaultConstructorPOJO() { NoDefaultConstructorPOJO object = new NoDefaultConstructorPOJO("Test"); try { BeanUtils.cloneBean(object); } catch (Exception e) { assertEquals(InstantiationException.class, e.getClass()); } } @Test public void test_cloneBean_wont_clone_getter_not_follow_naming() { Person person = new Person(); person.setSomeData(Boolean.TRUE); assertTrue(person.isSomeData()); try { BeanUtils.copyProperties(person, mary); person.setSomeData(Boolean.TRUE); assertTrue(person.isSomeData()); Person clonedPon = (Person) BeanUtils.cloneBean(person); assertFalse(clonedPon.isSomeData()); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } }
Execute mvn test -Dtest=CloneBeanTest
and capture the output.
CloneBeanTest Output
Running jcg.zheng.demo.CloneBeanTest Tests run: 4, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.314 sec Results : Tests run: 4, Failures: 0, Errors: 0, Skipped: 0 [INFO] ------------------------------------------------------------------------ [INFO] BUILD SUCCESS [INFO] ------------------------------------------------------------------------ [INFO] Total time: 10.307 s [INFO] Finished at: 2019-07-19T20:36:05-05:00 [INFO] ------------------------------------------------------------------------ C:\MaryZheng\Workspaces\jdk12\java-beanutils-demo>
5.3 CopyPropertiesTest
In this step, I will create a CopyPropertiesTest
class to show how to use copyProperties
to copy properties from one JavaBean to another. It will work when copying properties from a POJO which does not have a default constructor.
CopyPropertiesTest.java
package jcg.zheng.demo; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNotNull; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import java.lang.reflect.InvocationTargetException; import org.apache.commons.beanutils.BeanUtils; import org.junit.Test; import jcg.zheng.demo.data.NoDefaultConstructorPOJO; import jcg.zheng.demo.data.Person; public class CopyPropertiesTest extends TestBase { @Test public void test_copyProperties() { Person person = new Person(); try { BeanUtils.copyProperties(person, mary); assertEquals(mary.getFirstName(), person.getFirstName()); assertEquals(mary.getLastName(), person.getLastName()); assertNotNull(person.getCellPhone()); assertEquals(mary.getCellPhone().getAreaCode(), person.getCellPhone().getAreaCode()); assertEquals(mary.getCellPhone().getCountryCode(), person.getCellPhone().getCountryCode()); assertEquals(mary.getCellPhone().getPhoneNum(), person.getCellPhone().getPhoneNum()); assertNotNull(person.getHomePhone()); assertEquals(mary.getHomePhone().getAreaCode(), person.getHomePhone().getAreaCode()); assertEquals(mary.getHomePhone().getCountryCode(), person.getHomePhone().getCountryCode()); assertEquals(mary.getHomePhone().getPhoneNum(), person.getHomePhone().getPhoneNum()); assertNotNull(person.getTopics()); assertEquals(mary.getTopics().size(), person.getTopics().size()); assertTrue(person.getTopics().contains(TOPIC_1)); assertTrue(person.getTopics().contains(TOPIC_2)); assertTrue(person.getTopics().contains(TOPIC_3)); assertNotNull(person.getAddtionalProperties()); assertEquals(mary.getAddtionalProperties().size(), person.getAddtionalProperties().size()); assertEquals(mary.getAddtionalProperties().get(KEY_1), person.getAddtionalProperties().get(KEY_1)); assertEquals(mary.getAddtionalProperties().get(KEY_2), person.getAddtionalProperties().get(KEY_2)); assertNull(person.getSomeData()); } catch (IllegalAccessException | InvocationTargetException e) { fail(SHOULD_NOT_REACH); } } @Test public void test_copyProperties_NoDefaultConstructorPOJO() { NoDefaultConstructorPOJO pojo = new NoDefaultConstructorPOJO("Test"); try { BeanUtils.copyProperties(pojo, mary); assertEquals("Test", pojo.getName()); } catch (IllegalAccessException | InvocationTargetException e) { fail(SHOULD_NOT_REACH); } } }
Execute mvn test -Dtest=CopyPropertiesTest
and capture the output.
CopyPropertiesTest Output
Running jcg.zheng.demo.CopyPropertiesTest Tests run: 3, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.349 sec Results : Tests run: 3, Failures: 0, Errors: 0, Skipped: 0 [INFO] ------------------------------------------------------------------------ [INFO] BUILD SUCCESS [INFO] ------------------------------------------------------------------------ [INFO] Total time: 9.050 s [INFO] Finished at: 2019-07-19T20:39:41-05:00 [INFO] ------------------------------------------------------------------------ C:\MaryZheng\Workspaces\jdk12\java-beanutils-demo>
5.4 SimplePropertyTest
In this step, I will create a SimplePropertyTest
class to show how to get and set the indexed properties. I will demonstrate three ways to get and set a simple property:
- get and set the simple property via the getter and setter
- get and set the simple property via
getProperty
andsetProperty
- get and set the simple property via
getSimpleProperty
andsetSimpleProperty
Note: It will throw NoSuchMethodException
when calling setSimpleProperty
at a non-exist property, but it will not throw exception when calling setPropery
at a non-existing property.
SimplePropertyTest.java
package jcg.zheng.demo; import static org.junit.Assert.assertEquals; import static org.junit.Assert.fail; import org.apache.commons.beanutils.BeanUtils; import org.apache.commons.beanutils.PropertyUtils; import org.junit.Test; public class SimplePropertyTest extends TestBase { @Test public void getProperty_for_definedProperty() { try { String fname = BeanUtils.getProperty(mary, "firstName"); assertEquals("Mary", fname); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void getSimpleProperty_retrun_value_for_definedProperty() { try { String firstName = BeanUtils.getSimpleProperty(mary, "firstName"); assertEquals("Mary", firstName); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void getter_return_value_for_definedProperty() { try { assertEquals("Mary", mary.getFirstName()); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void setProperty_for_definedProperty() { try { BeanUtils.setProperty(mary, "firstName", "UpdateMary"); assertEquals("UpdateMary", mary.getFirstName()); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void setProperty_for_not_definedProperty() { try { BeanUtils.setProperty(mary, "noGetter", Integer.valueOf(1)); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void setSimpleProperty_for_definedProperty() { try { PropertyUtils.setSimpleProperty(mary, "firstName", "UpdateMary"); assertEquals("UpdateMary", mary.getFirstName()); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void setSimpleProperty_for_NamingNotMatchProperty() { try { PropertyUtils.setSimpleProperty(mary, "someData", true); } catch (Exception e) { assertEquals(NoSuchMethodException.class, e.getClass()); } } @Test public void setSimpleProperty_for_not_definedProperty() { try { PropertyUtils.setSimpleProperty(mary, "isSomeData", Integer.valueOf(1)); } catch (Exception e) { assertEquals(NoSuchMethodException.class, e.getClass()); } } }
Execute mvn test -Dtest=SimplePropertyTest
and capture the output.
SimplePropertyTest Output
Running jcg.zheng.demo.SimplePropertyTest Tests run: 9, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.313 sec Results : Tests run: 9, Failures: 0, Errors: 0, Skipped: 0 [INFO] ------------------------------------------------------------------------ [INFO] BUILD SUCCESS [INFO] ------------------------------------------------------------------------ [INFO] Total time: 8.985 s [INFO] Finished at: 2019-07-19T20:41:17-05:00 [INFO] ------------------------------------------------------------------------ C:\MaryZheng\Workspaces\jdk12\java-beanutils-demo>
5.5 IndexedPropertyTest
In this step, I will create an IndexedPropertyTest
class to show how to get and set the indexed properties via getProperty
, setProperty
, getIndexedProperty
, and setIndexedProperty
. It will work when setting properties from a POJO which does not have a default constructor.
Note: The indexed property follows the array index naming convention.
IndexedPropertyTest.java
package jcg.zheng.demo; import static org.junit.Assert.assertEquals; import static org.junit.Assert.fail; import org.apache.commons.beanutils.BeanUtils; import org.apache.commons.beanutils.PropertyUtils; import org.junit.Test; import jcg.zheng.demo.data.NoDefaultConstructorPOJO; public class IndexedPropertyTest extends TestBase { @Test public void getIndexedProperty() { try { String topic = BeanUtils.getIndexedProperty(mary, "topics[0]"); assertEquals(TOPIC_1, topic); topic = BeanUtils.getIndexedProperty(mary, "topics[2]"); assertEquals(TOPIC_3, topic); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void getIndexedProperty_error() { try { BeanUtils.getIndexedProperty(mary, "topics[3]"); } catch (Exception e) { assertEquals(ArrayIndexOutOfBoundsException.class, e.getClass()); } } @Test public void getIndexedProperty_index() { try { String topic = BeanUtils.getIndexedProperty(mary, "topics", 1); assertEquals(TOPIC_2, topic); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void getIndexedProperty_index_error() { try { BeanUtils.getIndexedProperty(mary, "topics", 3); } catch (Exception e) { assertEquals(ArrayIndexOutOfBoundsException.class, e.getClass()); } } @Test public void getProperty() { try { String value = BeanUtils.getProperty(mary, "topics[1]"); assertEquals("BeanUtils", value); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void getter() { try { assertEquals(3, mary.getTopics().size()); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void setIndexedProperty() { try { PropertyUtils.setIndexedProperty(mary, "topics[1]", "Java 8"); assertEquals("Java 8", mary.getTopics().get(1)); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void setIndexedProperty_index() { try { PropertyUtils.setIndexedProperty(mary, "topics", 1, "Java 8"); assertEquals("Java 8", mary.getTopics().get(1)); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void setProperty() { try { BeanUtils.setProperty(mary, "topics[1]", "Java 12"); assertEquals("Java 12", mary.getTopics().get(1)); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void setProperty_NoDefaultConstructorPOJO() { NoDefaultConstructorPOJO object = new NoDefaultConstructorPOJO("Test"); try { BeanUtils.setProperty(object, "name", "Java"); assertEquals("Java", object.getName()); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } }
Execute mvn test -Dtest=IndexedPropertyTest
and capture the output.
IndexedPropertyTest Output
Running jcg.zheng.demo.IndexedPropertyTest Tests run: 11, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.323 sec Results : Tests run: 11, Failures: 0, Errors: 0, Skipped: 0 [INFO] ------------------------------------------------------------------------ [INFO] BUILD SUCCESS [INFO] ------------------------------------------------------------------------ [INFO] Total time: 9.683 s [INFO] Finished at: 2019-07-19T21:28:24-05:00 [INFO] ------------------------------------------------------------------------ C:\MaryZheng\Workspaces\jdk12\java-beanutils-demo>
5.6 MappedPropertyTest
In this step, I will create a MappedPropertyTest
class to show how to get and set the mapped properties via getProperty
, setProperty
, getMappedProperty
, and setMappedProperty
. It will throw IllegalArgumentException
when the property doesn’t exist.
Note: The mapped property encloses the key value inside “()”.
MappedPropertyTest.java
package jcg.zheng.demo; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNull; import static org.junit.Assert.fail; import org.apache.commons.beanutils.BeanUtils; import org.apache.commons.beanutils.PropertyUtils; import org.junit.Test; public class MappedPropertyTest extends TestBase { @Test public void getMappedProperty() { try { String colorValue = BeanUtils.getMappedProperty(mary, "addtionalProperties(Color)"); assertEquals(VALUE_1, colorValue); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void getMappedProperty_error_notexist_property() { try { BeanUtils.getMappedProperty(mary, "NA"); } catch (Exception e) { assertEquals(IllegalArgumentException.class, e.getClass()); } } @Test public void getMappedProperty_key() { try { String keyValue = BeanUtils.getMappedProperty(mary, "addtionalProperties", KEY_1); assertEquals(VALUE_1, keyValue); keyValue = BeanUtils.getMappedProperty(mary, "addtionalProperties", KEY_2); assertEquals(VALUE_2, keyValue); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void getMappedProperty_return_null_for_not_exist_key() { try { String naValue = BeanUtils.getMappedProperty(mary, "addtionalProperties", "NA"); assertNull(naValue); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void getProperty() { try { String value = BeanUtils.getProperty(mary, "addtionalProperties(Color)"); assertEquals("Purple", value); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void getter() { try { assertEquals(2, mary.getAddtionalProperties().size()); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void setMappedProperty() { try { PropertyUtils.setMappedProperty(mary, "addtionalProperties(Color)", "Blue"); assertEquals("Blue", mary.getAddtionalProperties().get(KEY_1)); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void setMappedProperty_key() { try { PropertyUtils.setMappedProperty(mary, "addtionalProperties", KEY_1, "Blue"); assertEquals("Blue", mary.getAddtionalProperties().get(KEY_1)); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void setProperty() { try { BeanUtils.setProperty(mary, "addtionalProperties(Color)", "Green"); assertEquals("Green", mary.getAddtionalProperties().get(KEY_1)); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } }
Execute mvn test -Dtest=MappedPropertyTest
and capture the output.
MappedPropertyTest Output
Running jcg.zheng.demo.MappedPropertyTest Tests run: 10, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.331 sec Results : Tests run: 10, Failures: 0, Errors: 0, Skipped: 0 [INFO] ------------------------------------------------------------------------ [INFO] BUILD SUCCESS [INFO] ------------------------------------------------------------------------ [INFO] Total time: 9.816 s [INFO] Finished at: 2019-07-19T21:31:34-05:00 [INFO] ------------------------------------------------------------------------ C:\MaryZheng\Workspaces\jdk12\java-beanutils-demo>
5.7 NestedPropertyTest
In this step, I will create a NestedPropertyTest
class to show how to get and set the nested properties via getProperty
, setProperty
, getNestedProperty
, and setNestedProperty
.
Note: The nested property uses dot(.) for each nested object.
NestedPropertyTest.java
package jcg.zheng.demo; import static org.junit.Assert.assertEquals; import static org.junit.Assert.fail; import org.apache.commons.beanutils.BeanUtils; import org.apache.commons.beanutils.PropertyUtils; import org.junit.Test; public class NestedPropertyTest extends TestBase { @Test public void getNestedProperty() { try { String areaCode = BeanUtils.getNestedProperty(mary, "cellPhone.areaCode"); assertEquals("314", areaCode); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void getProperty() { try { String areaCode = BeanUtils.getProperty(mary, "cellPhone.areaCode"); assertEquals("314", areaCode); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void getter() { try { assertEquals("314", mary.getCellPhone().getAreaCode()); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void setNestedProperty() { try { PropertyUtils.setNestedProperty(mary, "cellPhone.areaCode", "404"); assertEquals("404", mary.getCellPhone().getAreaCode()); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } @Test public void setProperty() { try { BeanUtils.setProperty(mary, "cellPhone.areaCode", "636"); assertEquals("636", mary.getCellPhone().getAreaCode()); } catch (Exception e) { fail(SHOULD_NOT_REACH); } } }
Execute mvn test -Dtest=NestedPropertyTest
and capture the output.
NestedPropertyTest Output
Running jcg.zheng.demo.NestedPropertyTest Tests run: 6, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.318 sec Results : Tests run: 6, Failures: 0, Errors: 0, Skipped: 0 [INFO] ------------------------------------------------------------------------ [INFO] BUILD SUCCESS [INFO] ------------------------------------------------------------------------ [INFO] Total time: 9.756 s [INFO] Finished at: 2019-07-19T21:33:16-05:00 [INFO] ------------------------------------------------------------------------ C:\MaryZheng\Workspaces\jdk12\java-beanutils-demo>
6. Apache Commons BeanUtils – Summary
In this example, I demonstrated how to use the following common methods in BeanUtils
to copy, clone, get, and set properties of a JavaBean:
- static Object cloneBean(Object bean)
- static void copyProperties(Object dest, Object orig)
- static String getProperty(Object bean, String name)
- static void setProperty(Object bean, String name, Object value)
- static String getSimpleProperty(Object bean, String name)
- static void setSimpleProperty(Object bean, String name, Object value)
- static String getIndexedProperty(Object bean, String name)
- static void setIndexedProperty(Object bean, String name, Object value)
- static void setIndexedProperty(Object bean, String name, int index, Object value)
- static String getMappedProperty(Object bean, String name)
- static void setMappedProperty(Object bean, String name, Object value)
- static void setMappedProperty(Object bean, String name,String key, Object value)
- static String getNestedProperty(Object bean, String name)
- static void setNestedProperty(Object bean, String name, Object value)
7. Download the Source Code
This example consists of a Maven project which demonstrates the usage of the BeanUtils
class.
You can download the full source code of this example here: Apache Commons BeanUtils Example