開発中のenvでいくつかのサービスを模擬しようとしています。 serviceFactoryコードは次のようなものです:javassistを使用してフィールドの初期値を変更する方法
public class ApiFacadeImpl implements ApiFacade {
private OneService oneService = null;
public OneService getOneService(){
if(oneService==null) {//some initialization steps }
return oneService;
}
}
私はこの工場がうまくコーディングされていないことを知っています。しかし、私はそのコードを変更することはできません。 私の考えでは、バイトコードを変更することですので、私のようなものにそれを再定義することができます。
public class ApiFacadeImpl implements ApiFacade {
private OneService oneService = new MyMockOneService();
....
}
私の第一は、次のとおりです。 がこれを可能に使用してJavassistのでしょうか?そしてどうやって?
私はグーグルを使ってJavassistのを使用してフィールドを再初期化のような何かを見つけることができませんので、私はそれを削除して再作成することによって自分自身を試してみました:
CtField oneServiceField = cc.getDeclaredField("oneService");
cc.removeField(oneServiceField);
CtField f = CtField.make(String.format("private %s %s=new %s();",
oneServiceField.getType().getName(), "oneService",
mockClass.getCanonicalName()), cc);
cc.addField(f);
cc.toClass();
はその後、私は例外が発生しました:
javassist.CannotCompileException: by java.lang.ClassFormatError: Invalid length 99 in LocalVariableTable in class file com/Test
at javassist.ClassPool.toClass(ClassPool.java:1051)
at javassist.ClassPool.toClass(ClassPool.java:994)
at javassist.ClassPool.toClass(ClassPool.java:952)
at javassist.CtClass.toClass(CtClass.java:1079)
私の2番目の質問はなぜこの例外ですか?どのステップがJavaクラスの定義に従わないのですか?
public OneService getOneService(){
if(oneService==null) {//some initialization steps }
return oneService;
}
多くの感謝:私はフィールドを削除する場合のフィールドの参照を削除するのに役立ちJavassistのありません。
mockClass.getCanonicalName()とは何ですか? – longhua
javassistのバージョンは何ですか? – longhua