Showing posts with label java-beans. Show all posts
Showing posts with label java-beans. Show all posts

Monday, 27 May 2024

Retrieve the method details of a bean by using BeanInfo#getMethodDescriptors

Using BeanInfo#getMethodDescriptors method, we can get the method descriptors of a bean.

Example

BeanInfo beanInfo = Introspector.getBeanInfo(clazz);
MethodDescriptor[] methodDescriptors = beanInfo.getMethodDescriptors();

 

Find the below working application.

 

Employee.java 
package com.sample.app.model;

public class Employee {
	private static int totalEmployees;

	private Integer id;
	private String name;
	private int age;

	public Integer getId() {
		return id;
	}

	public void setId(Integer id) {
		this.id = id;
	}

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public int getAge() {
		return age;
	}

	public void setAge(int age) {
		this.age = age;
	}

	public static int getTotalemployees() {
		return totalEmployees;
	}

	public static int getTotalEmployees() {
		return totalEmployees;
	}

	public static void setTotalEmployees(int totalEmployees) {
		Employee.totalEmployees = totalEmployees;
	}

	@Override
	public String toString() {
		return "Employee [id=" + id + ", name=" + name + ", age=" + age + "]";
	}

}

 

GetMethodsOfABean.java

package com.sample.app.introspector;

import java.beans.BeanInfo;
import java.beans.IntrospectionException;
import java.beans.Introspector;
import java.beans.MethodDescriptor;
import java.lang.reflect.Method;

import com.sample.app.model.Employee;

public class GetMethodsOfABean {

	private static MethodDescriptor[] methodDescriptors(final Class<?> clazz) throws IntrospectionException {
		BeanInfo beanInfo = Introspector.getBeanInfo(clazz);
		return beanInfo.getMethodDescriptors();
	}

	public static void main(String[] args) throws IntrospectionException {
		MethodDescriptor[] methodDescriptors = methodDescriptors(Employee.class);

		for (MethodDescriptor methodDescriptor : methodDescriptors) {

			Method method = methodDescriptor.getMethod();
			// Check if the method belongs to the specified class (Employee)
			if (!method.getDeclaringClass().equals(Employee.class)) {
				continue;
			}

			String name = method.getName();
			System.out.println("Method name : " + name);

			Class<?>[] parameterTypes = method.getParameterTypes();

			if (parameterTypes.length == 0) {
				continue;
			}

			System.out.println("  Paramters : ");
			for (Class<?> parameterType : parameterTypes) {
				System.out.println("    " + parameterType);
			}

		}

	}

}

 

Output

Method name : getName
Method name : setTotalEmployees
  Paramters : 
    int
Method name : setId
  Paramters : 
    class java.lang.Integer
Method name : getTotalEmployees
Method name : setAge
  Paramters : 
    int
Method name : setName
  Paramters : 
    class java.lang.String
Method name : getAge
Method name : getId
Method name : getTotalemployees
Method name : toString

 

 

Previous                                                    Next                                                    Home

Sunday, 26 May 2024

Populating a Java Bean from a Map Using Introspection

In this post, I am going to explain how to populate a Java bean from a map.

Input

Map<String, Object> map = new HashMap<>();

map.put("id", 123);
map.put("name", "Krishna Gurram");
map.put("age", 34);

We need to write an utility method, that takes a Map and a bean class as argument, and return the bean by populating the properties from the map.

 

public static <T> T fromMap(Map<String, Object> map, Class<T> clazz) throws Exception {

}

 

Simple solution looks like below.

Get all property descriptors of the class.

BeanInfo beanInfo = Introspector.getBeanInfo(clazz);
PropertyDescriptor[] propertyDescriptors = beanInfo.getPropertyDescriptors();

For each property of the class, find the setter method of this property and set the value.

for (PropertyDescriptor propertyDescriptor : propertyDescriptors) {
  String name = propertyDescriptor.getName();
  Object value = map.get(name);
  Method setterMethod = propertyDescriptor.getWriteMethod();
  setterMethod.invoke(object, value);
}

 

Apart from this, we need to handle other scenarios like

a.   Whether the value is compatible with given value.

b.   Whether is there any setter method for the given variable etc.,

 

Find the below working application.

 

Employee.java

 

package com.sample.app.model;

public class Employee {
  private static int totalEmployees;

  private Integer id;
  private String name;
  private int age;

  public Integer getId() {
    return id;
  }

  public void setId(Integer id) {
    this.id = id;
  }

  public String getName() {
    return name;
  }

  public void setName(String name) {
    this.name = name;
  }

  public int getAge() {
    return age;
  }

  public void setAge(int age) {
    this.age = age;
  }

  public static int getTotalemployees() {
    return totalEmployees;
  }

  @Override
  public String toString() {
    return "Employee [id=" + id + ", name=" + name + ", age=" + age + "]";
  }

}

PopulateJavaObjectFromAMap.java

package com.sample.app.introspector;

import java.beans.BeanInfo;
import java.beans.Introspector;
import java.beans.PropertyDescriptor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.Map;

import com.sample.app.model.Employee;

public class PopulateJavaObjectFromAMap {

  private static boolean matchesPrimitive(final Class<?> targetType, final Class<?> valueType) {
    if (!targetType.isPrimitive()) {
      return false;
    }

    try {
      // see if there is a "TYPE" field. This is present for primitive wrappers.
      final Field typeField = valueType.getField("TYPE");
      final Object primitiveValueType = typeField.get(valueType);

      if (targetType == primitiveValueType) {
        return true;
      }
    } catch (final NoSuchFieldException | IllegalAccessException ignored) {
      // If the TYPE field is inaccessible, it suggests that we're not dealing with a
      // primitive wrapper.
      // There's no action required in this case, as we can't check for compatibility.
    }
    return false;
  }

  private static boolean isCompatibleType(final Object value, final Class<?> type) {
    return value == null || type.isInstance(value) || matchesPrimitive(type, value.getClass());
  }

  public static <T> T fromMap(Map<String, Object> map, Class<T> clazz) throws Exception {
    BeanInfo beanInfo = Introspector.getBeanInfo(clazz);
    PropertyDescriptor[] propertyDescriptors = beanInfo.getPropertyDescriptors();

    T object = clazz.getDeclaredConstructor().newInstance();

    for (PropertyDescriptor propertyDescriptor : propertyDescriptors) {

      try {
        String name = propertyDescriptor.getName();
        Object value = map.get(name);

        Method setterMethod = propertyDescriptor.getWriteMethod();
        if (setterMethod == null) {
          continue;
        }
        final Class<?> firstParameterType = setterMethod.getParameterTypes()[0];

        if (!isCompatibleType(value, firstParameterType)) {
          throw new Exception("Can't set the value " + value + " to the " + name);
        }
        setterMethod.invoke(object, value);

      } catch (Exception e) {
        throw e;
      }

    }

    return object;

  }

  public static void main(String[] args) throws Exception {
    Map<String, Object> map = new HashMap<>();

    map.put("id", 123);
    map.put("name", "Krishna Gurram");
    map.put("age", 34);

    Employee emp = fromMap(map, Employee.class);
    System.out.println(emp);

  }

}

Output

Employee [id=123, name=Krishna Gurram, age=34]

 

Previous                                                    Next                                                    Home

Saturday, 25 May 2024

Retrieve Class Property Details Using BeanInfo#getPropertyDescriptors Method

Using BeanInfo#getPropertyDescriptors method, we can get all the properties of the bean.

Example

PropertyDescriptor[] propertyDescriptors(final Class<?> c) throws IntrospectionException {
  BeanInfo beanInfo = Introspector.getBeanInfo(c);
  return beanInfo.getPropertyDescriptors();
}

Above code defines a method propertyDescriptors that retrieves PropertyDescriptor objects for a given class using introspection. It leverages Java's Introspector.getBeanInfo() to obtain class information and then calls getPropertyDescriptors() to retrieve property descriptors. These descriptors provide details about JavaBean properties, aiding dynamic introspection of bean properties at runtime.

 

Find the below working application.

 

Employee.java

package com.sample.app.model;

public class Employee {
  private static int totalEmployees;

  private Integer id;
  private String name;
  private Integer age;

  public Integer getId() {
    return id;
  }

  public void setId(Integer id) {
    this.id = id;
  }

  public String getName() {
    return name;
  }

  public void setName(String name) {
    this.name = name;
  }

  public Integer getAge() {
    return age;
  }

  public void setAge(Integer age) {
    this.age = age;
  }

  public static int getTotalemployees() {
    return totalEmployees;
  }

}

GetPropertiesOfClass.java

package com.sample.app.introspector;

import java.beans.BeanInfo;
import java.beans.IntrospectionException;
import java.beans.Introspector;
import java.beans.PropertyDescriptor;
import java.lang.reflect.Method;

import com.sample.app.model.Employee;

public class GetPropertiesOfClass {

  private static PropertyDescriptor[] propertyDescriptors(final Class<?> c) throws IntrospectionException {
    BeanInfo beanInfo = Introspector.getBeanInfo(c);
    return beanInfo.getPropertyDescriptors();
  }

  public static void main(String[] args) throws Exception {
    PropertyDescriptor[] propertyDescriptors = propertyDescriptors(Employee.class);

    for (PropertyDescriptor propertyDescriptor : propertyDescriptors) {
      String name = propertyDescriptor.getName();
      Class<?> type = propertyDescriptor.getPropertyType();
      Method methodToReadThisProperty = propertyDescriptor.getReadMethod();
      Method methodToUpdateThisProperty = propertyDescriptor.getWriteMethod();

      System.out.println("name : " + name);
      System.out.println("type : " + type);
      if (methodToReadThisProperty != null) {
        System.out.println("methodToReadThisProperty : " + methodToReadThisProperty.getName());
      }
      if (methodToUpdateThisProperty != null) {
        System.out.println("methodToUpdateThisProperty : " + methodToUpdateThisProperty.getName());
      }
      System.out.println();

    }

  }

}

Output

name : age
type : class java.lang.Integer
methodToReadThisProperty : getAge
methodToUpdateThisProperty : setAge

name : class
type : class java.lang.Class
methodToReadThisProperty : getClass

name : id
type : class java.lang.Integer
methodToReadThisProperty : getId
methodToUpdateThisProperty : setId

name : name
type : class java.lang.String
methodToReadThisProperty : getName
methodToUpdateThisProperty : setName


 

Previous                                                    Next                                                    Home

Java beans package tutorial


Retrieve Class Property Details Using BeanInfo#getPropertyDescriptors Method
Populating a Java Bean from a Map Using Introspection
Retrieve the method details of a bean by using BeanInfo#getMethodDescriptors

Previous                                                    Next                                                    Home