Extracting and setting enum Values via reflection
I am trying to set a number of Enums to default value I am using the following method:
private void checkEnum(Field field, String setMethod) {
// TODO Auto-generated method stub
try {
String className = Character.toUpperCase(field.getName().charAt(0)) +
field.getName().substring(1);
Class<?> cls = Class.forName("com.citigroup.get.zcc.intf." + className);
Object[] enumArray = cls.getEnumConstants();
//set to the last Enum which is unknown
invoke(setMethod, enumArray[enumArray.length - 1] );
} catch(Exception e) {
System.out.println(e.toString());
}
}
The problem is actually setting the Enum. I have extracted the enum type but to then call the MethodInvoker. Passing in the Enum object is proving a problem. All the enums have the following as the last element of the enum array.
EnumName.UNKNOWN
However this is not being set via the invoke method which looks like:
private Object invoke(String methodName, Object newValue) {
Object value = null;
try {
methodInvoker.setTargetMethod(methodName);
if (newValue != null) {
methodInvoker.setArguments(new Object[]{newValue});
} else {
methodInvoker.setArguments(new Object[]{});
}
methodInvoker.prepare();
value = methodInvoker.invoke();
} catch (ClassNotFoundException e) {
throw new IllegalStateException("Method invocation failed. " + e.getMessage(),e);
} catch (NoSuchMethodException e) {
throw new IllegalStateException("Method invocation failed. " + e.getMessage(),e);
} catch (java.lang.reflect.InvocationTargetException e) {
throw new IllegalStateException("Method invocation failed. " + e.g开发者_如何学编程etMessage(),e);
} catch (IllegalAccessException e) {
throw new IllegalStateException("Method invocation failed. " + e.getMessage(),e);
}
return value;
}
So I'm lost as to why the
invoke(setMethod, enumArray[enumArray.length -1] );
Is not setting my Enum
I attempted to get your code running. The methodInvoker.prepare() call was throwing: java.lang.IllegalArgumentException: Either 'targetClass' or 'targetObject' is required
So I added in the class missing parameter and the code works, if I understand your use case. You appear to be setting a static field whose name must be the name of an Enum class under com.citigroup.get.zcc.intf with the first character in the field name downcased.
Here is my modified code:
public void checkEnum(Field field, String setMethod, Class clazz) {
try {
String className = Character.toUpperCase(field.getName().charAt(0)) +
field.getName().substring(1);
Class<?> cls = Class.forName("com.citigroup.get.zcc.intf." + className);
Object[] enumArray = cls.getEnumConstants();
//set to the last Enum which is unknown
invoke(setMethod, enumArray[enumArray.length - 1], clazz);
} catch (Exception e) {
System.out.println(e.toString());
}
}
private Object invoke(String methodName, Object newValue, Class clazz) {
Object value = null;
try {
MethodInvoker methodInvoker = new MethodInvoker(); // this was missing
methodInvoker.setTargetMethod(methodName);
methodInvoker.setTargetClass(clazz); // This was missing
if (newValue != null) {
methodInvoker.setArguments(new Object[]{newValue});
} else {
methodInvoker.setArguments(new Object[]{});
}
methodInvoker.prepare();
value = methodInvoker.invoke();
} catch (ClassNotFoundException e) {
throw new IllegalStateException("Method invocation failed. " + e.getMessage(), e);
} catch (NoSuchMethodException e) {
throw new IllegalStateException("Method invocation failed. " + e.getMessage(), e);
} catch (java.lang.reflect.InvocationTargetException e) {
throw new IllegalStateException("Method invocation failed. " + e.getMessage(), e);
} catch (IllegalAccessException e) {
throw new IllegalStateException("Method invocation failed. " + e.getMessage(), e);
}
return value;
}
}
My test code resembled (Show is an enum class of mine, MethodNameHelper has been previously posted to StackExchange):
public class StackExchangeTestCase {
protected static final Logger log = Logger.getLogger(StackExchangeTestCase.class);
public static Show show;
public static void setShow(Show newShow) {
show = newShow;
}
@Test
public void testJunk() throws Exception {
Method me = (new Util.MethodNameHelper(){}).getMethod();
Class<?> aClass = me.getDeclaringClass();
Field att1 = aClass.getField("show");
show = null;
methodNameHelper.checkEnum(att1, "setShow", aClass);
System.out.println(show); // worked
}
}
精彩评论