[java][javassist]privateなメソッドにアクセスするもうひとつの方法
2006/07/19
2006/11/26
javassistを利用して、privateなメソッドにアクセスするもうひとつの方法です。
シナリオ:
下記のクラスのprivateなメソッドgetSにアクセスしたいとします。
public class A_A {
private String s = "hello";
private String getS(){
System.out.println("i am privte method!!");
return s;
}
}
方法は、javassistを利用して、メソッドを取得して、そのメソッドをクラスから削除して、アクセス修飾子を変更して、再度クラスにそのメソッドをaddするというまどろっこしい方法をとっています。
import java.io.IOException;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import javassist.CannotCompileException;
import javassist.ClassPool;
import javassist.CtClass;
import javassist.CtMethod;
import javassist.NotFoundException;
import javassist.bytecode.AccessFlag;
public class TestAccessPrivateMethod2 {
public static void main(String[] args) throws NotFoundException,
CannotCompileException, InstantiationException,
IllegalAccessException, SecurityException, NoSuchMethodException,
IllegalArgumentException, InvocationTargetException, IOException {
ClassPool pool = ClassPool.getDefault();
CtClass myCtClass = pool.get("A_A");
CtMethod ctMethod = myCtClass.getDeclaredMethod("getS");
// 既にあるメソッドを削除
myCtClass.removeMethod(ctMethod);
// アクセス修飾子をpublicに変更
ctMethod.getMethodInfo2().setAccessFlags(AccessFlag.PUBLIC);
// 修正したメソッドを追加
myCtClass.addMethod(ctMethod);
Class myClass = myCtClass.toClass();
Object my = myClass.newInstance();
// 何もしなかったら通常 Exception in thread "main" java.lang.NoSuchMethodException: A_A.getS()
Method exeMth = myClass.getMethod("getS", new Class[] {});
System.out.println(exeMth.invoke(my, new Object[] {}));
}
}
シナリオ:
下記のクラスのprivateなメソッドgetSにアクセスしたいとします。
public class A_A {
private String s = "hello";
private String getS(){
System.out.println("i am privte method!!");
return s;
}
}
方法は、javassistを利用して、メソッドを取得して、そのメソッドをクラスから削除して、アクセス修飾子を変更して、再度クラスにそのメソッドをaddするというまどろっこしい方法をとっています。
import java.io.IOException;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import javassist.CannotCompileException;
import javassist.ClassPool;
import javassist.CtClass;
import javassist.CtMethod;
import javassist.NotFoundException;
import javassist.bytecode.AccessFlag;
public class TestAccessPrivateMethod2 {
public static void main(String[] args) throws NotFoundException,
CannotCompileException, InstantiationException,
IllegalAccessException, SecurityException, NoSuchMethodException,
IllegalArgumentException, InvocationTargetException, IOException {
ClassPool pool = ClassPool.getDefault();
CtClass myCtClass = pool.get("A_A");
CtMethod ctMethod = myCtClass.getDeclaredMethod("getS");
// 既にあるメソッドを削除
myCtClass.removeMethod(ctMethod);
// アクセス修飾子をpublicに変更
ctMethod.getMethodInfo2().setAccessFlags(AccessFlag.PUBLIC);
// 修正したメソッドを追加
myCtClass.addMethod(ctMethod);
Class myClass = myCtClass.toClass();
Object my = myClass.newInstance();
// 何もしなかったら通常 Exception in thread "main" java.lang.NoSuchMethodException: A_A.getS()
Method exeMth = myClass.getMethod("getS", new Class[] {});
System.out.println(exeMth.invoke(my, new Object[] {}));
}
}
: