Thursday, 18 May 2023

Utility class to get detailed information about the properties of a class

In this post, I am going to explain about an utility class that provide below functionalities with respect to a field.

 

a.   Check whether a field has getter and setter methods

b.   Check the information about field access modifiers like public, private, and protected

c.    Check whether the field is constant or not

d.   Check whether the field is readable or writeable

 

Find the below working application.

 


FieldInfoUtil.java

package com.sample.app.reflections.util;

public class FieldInfoUtil {
	
	public static String setterName(String fieldName) {
		int len = fieldName.length();
		int setterNameSize = len + 3;
		char[] b = new char[setterNameSize];
		b[0] = 's';
		b[1] = 'e';
		b[2] = 't';
		char propertyFirstChar = fieldName.charAt(0);
		propertyFirstChar = Character.toUpperCase(propertyFirstChar);
		b[3] = propertyFirstChar;
		for (int i = 1; i < len; i++) {
			b[i + 3] = fieldName.charAt(i);
		}
		return new String(b);
	}

	public static String getterName(String fieldName) {
		int len = fieldName.length();
		int getterNameSize = len + 3;
		char[] b = new char[getterNameSize];
		b[0] = 'g';
		b[1] = 'e';
		b[2] = 't';
		char propertyFirstChar = fieldName.charAt(0);
		propertyFirstChar = Character.toUpperCase(propertyFirstChar);
		b[3] = propertyFirstChar;
		for (int i = 1; i < len; i++) {
			b[i + 3] = fieldName.charAt(i);
		}
		return new String(b);
	}

	public static String getterNameForBoolean(String fieldName) {
		int len = fieldName.length();
		int getterNameSize = len + 2;
		char[] b = new char[getterNameSize];
		b[0] = 'i';
		b[1] = 's';
		char propertyFirstChar = fieldName.charAt(0);
		propertyFirstChar = Character.toUpperCase(propertyFirstChar);
		b[2] = propertyFirstChar;
		for (int i = 1; i < len; i++) {
			b[i + 2] = fieldName.charAt(i);
		}
		return new String(b);
	}
}

 

FieldInfo.java

package com.sample.app.model;

import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
import java.lang.reflect.Type;

import com.sample.app.reflections.util.FieldInfoUtil;

public class FieldInfo {

	private Field field;

	private Method setter;

	private Method getter;

	private int index;

	private Class<?> type;

	private Type genericType;

	private FieldInfo() {

	}

	public int getIndex() {
		return index;
	}

	public boolean isEnum() {
		return type.isEnum();
	}

	public String getFieldName() {
		return field.getName();
	}

	public Class<?> getType() {
		return type;
	}

	public Type getGenericType() {
		return genericType;
	}

	public boolean isReadable() {
		return (getter != null || isPublicField());
	}

	public boolean isWritable() {
		if(isConstant()) {
			return false;
		}
		return (setter != null || isPublicField());
	}

	public Field getField() {
		return field;
	}

	public Method getSetter() {
		return setter;
	}

	public Method getGetter() {
		return getter;
	}

	public boolean isReadableAndWriteable() {
		return this.isReadable() && this.isWritable();
	}

	public boolean isPublicField() {
		int modifiers = field.getModifiers();
		return Modifier.isPublic(modifiers);
	}

	public boolean isPublicStaticField() {
		int modifiers = field.getModifiers();
		return Modifier.isPublic(modifiers) && Modifier.isStatic(modifiers);
	}

	public boolean isPrivateField() {
		int modifiers = field.getModifiers();
		return Modifier.isPrivate(modifiers);
	}

	public boolean isPrivateStaticField() {
		int modifiers = field.getModifiers();
		return Modifier.isPrivate(modifiers) && Modifier.isStatic(modifiers);
	}

	public boolean isProtectedField() {
		int modifiers = field.getModifiers();
		return Modifier.isProtected(modifiers);
	}

	public boolean isProtectedStaticField() {
		int modifiers = field.getModifiers();
		return Modifier.isProtected(modifiers) && Modifier.isStatic(modifiers);
	}

	public boolean isStaticField() {
		int modifiers = field.getModifiers();
		return Modifier.isStatic(modifiers);
	}

	public boolean isConstant() {
		int modifiers = field.getModifiers();
		return Modifier.isFinal(modifiers);
	}

	public boolean isStaticConstant() {
		int modifiers = field.getModifiers();
		return Modifier.isFinal(modifiers) && Modifier.isStatic(modifiers);
	}

	public boolean isPublicStaticConstant() {
		int modifiers = field.getModifiers();
		return Modifier.isPublic(modifiers) && Modifier.isStatic(modifiers) && Modifier.isFinal(modifiers);
	}

	public boolean isPrivateStaticConstant() {
		int modifiers = field.getModifiers();
		return Modifier.isPrivate(modifiers) && Modifier.isStatic(modifiers) && Modifier.isFinal(modifiers);
	}

	public boolean isProtectedStaticConstant() {
		int modifiers = field.getModifiers();
		return Modifier.isProtected(modifiers) && Modifier.isStatic(modifiers) && Modifier.isFinal(modifiers);
	}

	public static FieldInfo getFieldInfo(Class<?> clazz, Field field) {
		if (clazz == null) {
			throw new IllegalArgumentException("clazz is null");
		}

		if (field == null) {
			throw new IllegalArgumentException("field is null");
		}

		FieldInfo fieldInfo = new FieldInfo();

		fieldInfo.field = field;
		fieldInfo.type = field.getType();
		fieldInfo.genericType = field.getGenericType();

		if (fieldInfo.isStaticField()) {
			return fieldInfo;
		}

		String setterName = FieldInfoUtil.setterName(field.getName());
		try {
			fieldInfo.setter = clazz.getDeclaredMethod(setterName, field.getType());
		} catch (Exception e) {

		}

		boolean isBool = field.getType().equals(Boolean.TYPE);
		String getterName = null;
		if (isBool) {
			getterName = FieldInfoUtil.getterNameForBoolean(field.getName());
		} else {
			getterName = FieldInfoUtil.getterName(field.getName());
		}

		try {
			fieldInfo.getter = clazz.getDeclaredMethod(getterName);
		} catch (Exception e) {
		}

		return fieldInfo;
	}

}

 

FieldInfoDemo.java

package com.sample.app;

import java.lang.reflect.Field;

import com.sample.app.model.FieldInfo;

public class FieldInfoDemo {

    private static class DemoPojo {
        public final int P1 = 10;
        public static final double PI = 3.14;

        // Field with only setter method
        private int writeOnlyField;

        // Field with only getter method
        private int readOnlyField;

        // Field with both getter and setter methods
        private int readAndWriteableField;

        public void setWriteOnlyField(int writeOnlyField) {
            this.writeOnlyField = writeOnlyField;
        }

        public int getReadOnlyField() {
            return readOnlyField;
        }

        public int getReadAndWriteableField() {
            return readAndWriteableField;
        }

        public void setReadAndWriteableField(int readAndWriteableField) {
            this.readAndWriteableField = readAndWriteableField;
        }
    }

    private static void printFieldInfo(FieldInfo fieldInfo) {
        System.out.println("fieldName : " + fieldInfo.getFieldName());
        System.out.println("index : " + fieldInfo.getIndex());
        System.out.println("class : " + fieldInfo.getClass());
        System.out.println("field : " + fieldInfo.getField());
        System.out.println("generic type : " + fieldInfo.getGenericType());
        System.out.println("getter : " + fieldInfo.getGetter());
        System.out.println("setter : " + fieldInfo.getSetter());
        System.out.println("type : " + fieldInfo.getType());
        System.out.println("isConstant : " + fieldInfo.isConstant());
        System.out.println("isEnum : " + fieldInfo.isEnum());
        System.out.println("isPrivateField : " + fieldInfo.isPrivateField());
        System.out.println("isPrivateStaticConstant : " + fieldInfo.isPrivateStaticConstant());
        System.out.println("isPrivateStaticField : " + fieldInfo.isPrivateStaticField());
        System.out.println("isProtectedField : " + fieldInfo.isProtectedField());
        System.out.println("isProtectedStaticConstant : " + fieldInfo.isProtectedStaticConstant());
        System.out.println("isProtectedStaticField : " + fieldInfo.isProtectedStaticField());
        System.out.println("isPublicField : " + fieldInfo.isPublicField());
        System.out.println("isPublicStaticConstant : " + fieldInfo.isPublicStaticConstant());
        System.out.println("isPublicStaticField : " + fieldInfo.isPublicStaticField());
        System.out.println("isReadable : " + fieldInfo.isReadable());
        System.out.println("isReadableAndWriteable : " + fieldInfo.isReadableAndWriteable());
        System.out.println("isStaticConstant : " + fieldInfo.isStaticConstant());
        System.out.println("isStaticField : " + fieldInfo.isStaticField());
        System.out.println("isWritable : " + fieldInfo.isWritable());
        System.out.println("\n");
    }

    public static void main(String[] args) throws NoSuchFieldException, SecurityException {

        Field field1 = DemoPojo.class.getField("P1");
        Field field2 = DemoPojo.class.getField("PI");
        Field field3 = DemoPojo.class.getDeclaredField("writeOnlyField");
        Field field4 = DemoPojo.class.getDeclaredField("readOnlyField");
        Field field5 = DemoPojo.class.getDeclaredField("readAndWriteableField");

        printFieldInfo(FieldInfo.getFieldInfo(DemoPojo.class, field1));
        printFieldInfo(FieldInfo.getFieldInfo(DemoPojo.class, field2));
        printFieldInfo(FieldInfo.getFieldInfo(DemoPojo.class, field3));
        printFieldInfo(FieldInfo.getFieldInfo(DemoPojo.class, field4));
        printFieldInfo(FieldInfo.getFieldInfo(DemoPojo.class, field5));

    }

}

 

Output

fieldName : P1
index : 0
class : class com.sample.app.model.FieldInfo
field : public final int com.sample.app.FieldInfoDemo$DemoPojo.P1
generic type : int
getter : null
setter : null
type : int
isConstant : true
isEnum : false
isPrivateField : false
isPrivateStaticConstant : false
isPrivateStaticField : false
isProtectedField : false
isProtectedStaticConstant : false
isProtectedStaticField : false
isPublicField : true
isPublicStaticConstant : false
isPublicStaticField : false
isReadable : true
isReadableAndWriteable : false
isStaticConstant : false
isStaticField : false
isWritable : false


fieldName : PI
index : 0
class : class com.sample.app.model.FieldInfo
field : public static final double com.sample.app.FieldInfoDemo$DemoPojo.PI
generic type : double
getter : null
setter : null
type : double
isConstant : true
isEnum : false
isPrivateField : false
isPrivateStaticConstant : false
isPrivateStaticField : false
isProtectedField : false
isProtectedStaticConstant : false
isProtectedStaticField : false
isPublicField : true
isPublicStaticConstant : true
isPublicStaticField : true
isReadable : true
isReadableAndWriteable : false
isStaticConstant : true
isStaticField : true
isWritable : false


fieldName : writeOnlyField
index : 0
class : class com.sample.app.model.FieldInfo
field : private int com.sample.app.FieldInfoDemo$DemoPojo.writeOnlyField
generic type : int
getter : null
setter : public void com.sample.app.FieldInfoDemo$DemoPojo.setWriteOnlyField(int)
type : int
isConstant : false
isEnum : false
isPrivateField : true
isPrivateStaticConstant : false
isPrivateStaticField : false
isProtectedField : false
isProtectedStaticConstant : false
isProtectedStaticField : false
isPublicField : false
isPublicStaticConstant : false
isPublicStaticField : false
isReadable : false
isReadableAndWriteable : false
isStaticConstant : false
isStaticField : false
isWritable : true


fieldName : readOnlyField
index : 0
class : class com.sample.app.model.FieldInfo
field : private int com.sample.app.FieldInfoDemo$DemoPojo.readOnlyField
generic type : int
getter : public int com.sample.app.FieldInfoDemo$DemoPojo.getReadOnlyField()
setter : null
type : int
isConstant : false
isEnum : false
isPrivateField : true
isPrivateStaticConstant : false
isPrivateStaticField : false
isProtectedField : false
isProtectedStaticConstant : false
isProtectedStaticField : false
isPublicField : false
isPublicStaticConstant : false
isPublicStaticField : false
isReadable : true
isReadableAndWriteable : false
isStaticConstant : false
isStaticField : false
isWritable : false


fieldName : readAndWriteableField
index : 0
class : class com.sample.app.model.FieldInfo
field : private int com.sample.app.FieldInfoDemo$DemoPojo.readAndWriteableField
generic type : int
getter : public int com.sample.app.FieldInfoDemo$DemoPojo.getReadAndWriteableField()
setter : public void com.sample.app.FieldInfoDemo$DemoPojo.setReadAndWriteableField(int)
type : int
isConstant : false
isEnum : false
isPrivateField : true
isPrivateStaticConstant : false
isPrivateStaticField : false
isProtectedField : false
isProtectedStaticConstant : false
isProtectedStaticField : false
isPublicField : false
isPublicStaticConstant : false
isPublicStaticField : false
isReadable : true
isReadableAndWriteable : true
isStaticConstant : false
isStaticField : false
isWritable : true

 


Previous                                                 Next                                                 Home

No comments:

Post a Comment