Reputation: 534
I'm trying to call a method with reflection in java, but when I call the invoke method I get an exception. This is my code:
public void start() {
try {
ServerSocket server = new ServerSocket(port);
while(true) {
Socket s = server.accept();
ObjectInputStream in = new ObjectInputStream(s.getInputStream());
Class<?> myClass = Class.forName(vmi.getClass().toString().split(" ")[1]);
ArrayList<Object> array = new ArrayList();
Constructor<?> cons = myClass.getConstructor(new Class<?>[] {});
String method = null;
for(Method m : myClass.getMethods()) {
method = in.readObject().toString();
if(m.getName().equals(method)) {
Type return_type = m.getGenericReturnType();
for(Type types: m.getGenericParameterTypes()) {
array.add(in.readObject());
}
System.out.println(return_type);
if (return_type.toString().equals("void")) {
m.invoke(vmi, (Object)array);
}
break;
}
}
}
} catch (IOException | ClassNotFoundException | NoSuchMethodException
| SecurityException | IllegalAccessException
| IllegalArgumentException | InvocationTargetException e) {
// TODO Auto-generated catch block
e.printStackTrace();
System.out.println("Skeleton Exception "+ e.toString());
}
}
This is the exception:
java.lang.IllegalArgumentException: wrong number of arguments
I also tried to call the method with empty objects and the exception continues
m.invoke(vmi, new Object(), new Object());
By the way, the variables vmi and port are initialized in the constructor.
Upvotes: 1
Views: 210
Reputation: 31299
The signature of the Method.invoke
method is:
public Object invoke(Object obj, Object... args)
which is syntactic sugar for (in case you're not passing varargs) :
public Object invoke(Object obj, Object[] args)
You are, however, passing (Object,Object)
-> this will take the second object as a single argument for a varargs, so your call is translated by the compiler into m.invoke(vmi, new Object[] { array })
.
Complicating your code is the fact that you have a variable called array
, but its type is actually ArrayList
, which is not an array.
You can change your code to:
m.invoke(vmi, array.toArray());
This will pass your arguments as the whole varargs argument args
rather than as an individual element in the varargs array.
Upvotes: 1