Javassist загружает файл класса в предварительном основном методе (java instrumentation)
Я пытаюсь загрузить определенный класс с помощью javassist, я делаю это внутри основного метода в качестве следующего:
public byte[] transform(ClassLoader loader, String className, Class<?> classBeingRedefined,
ProtectionDomain protectionDomain, byte[] classfileBuffer) throws IllegalClassFormatException
{
byte[] byteCode = classfileBuffer;
if(className.toLowerCase().endsWith("class1"))
{
ClassPool classPool = ClassPool.getDefault();
CtClass ctClass = classPool.get("com.class2");
}
}
но неудобно, я получаю исключение NotFoundException....
com.class2 - это класс, который будет загружен загрузчиком классов после загрузки класса1, но я добавил, чтобы добавить новый метод для класса 1, который имеет тип возвращаемого типа com.class2
Я пробовал все решения внутри stackoverflow.com, но без каких-либо результатов.....
Наконец, как class1, так и class2 находятся в одном пакете и внутри одного JAR файла, class1 имеет член типа class2, но я понятия не имею, почему этот класс не может загрузить второй.
трассировка стека здесь:
Exception: javassist.NotFoundException: com.Class2
javassist.NotFoundException: com.Class2
at javassist.ClassPool.get(ClassPool.java:439)
at javassist.ClassPool.getCtClass(ClassPool.java:504)
at com.stuff.MainAppletTransformer.transform(MainAppletTransformer.java:69)
at sun.instrument.TransformerManager.transform(Unknown Source)
at sun.instrument.InstrumentationImpl.transform(Unknown Source)
at java.lang.ClassLoader.defineClass1(Native Method)
at java.lang.ClassLoader.defineClass(Unknown Source)
at java.security.SecureClassLoader.defineClass(Unknown Source)
at java.net.URLClassLoader.defineClass(Unknown Source)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at sun.plugin2.applet.Plugin2ClassLoader.defineClassHelper(Unknown Source)
at sun.plugin2.applet.Plugin2ClassLoader.access$100(Unknown Source)
at sun.plugin2.applet.Plugin2ClassLoader$2.run(Unknown Source)
at sun.plugin2.applet.Plugin2ClassLoader$2.run(Unknown Source)
at java.security.AccessController.doPrivileged(Native Method)
at sun.plugin2.applet.Plugin2ClassLoader.findClassHelper(Unknown Source)
at sun.plugin2.applet.Applet2ClassLoader.findClass(Unknown Source)
at sun.plugin2.applet.Plugin2ClassLoader.loadClass0(Unknown Source)
at sun.plugin2.applet.Plugin2ClassLoader.loadClass(Unknown Source)
at sun.plugin2.applet.Plugin2ClassLoader.loadClass(Unknown Source)
at java.lang.ClassLoader.loadClass(Unknown Source)
at sun.plugin2.applet.Plugin2ClassLoader.loadCode(Unknown Source)
at sun.plugin2.applet.Plugin2Manager.initAppletAdapter(Unknown Source)
at sun.plugin2.applet.Plugin2Manager$AppletExecutionRunnable.run(Unknown Source)
at java.lang.Thread.run(Unknown Source)
Ответы
Ответ 1
Ваш метод не имеет возвращаемого значения и поэтому не будет компилироваться. Тем не менее я могу сказать, что происходит не так: вы не настраиваете правильный путь поиска. Из вашей трассировки стека кажется, что вы используете апплет, который экранируется определенным ClassLoader
. Этот классный загрузчик не отображается Javassist в вашей текущей версии.
Используя ClassPool.getDefault()
, вы просматриваете информацию из пути к системному классу. Для вашего апплета вам, вероятно, понадобится добавить загрузчик классов, который передается методом transformatio в качестве аргумента.
Вы можете добавить загрузчик классов в путь поиска Javassist на
ClassPool classPool = ClassPool.getDefault();
classPool.appendClassPath(new LoaderClassPath(classLoader));
После добавления этого пути ваш пример должен работать.