javassist.NotFoundException occurred while Javassist was processing classes generated by Cglib

171 Views Asked by At

My code is below:

  1. pom.xml
    <dependencies>
        <dependency>
            <groupId>org.javassist</groupId>
            <artifactId>javassist</artifactId>
            <version>3.29.2-GA</version>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
            <version>2.7.7</version>
            <scope>compile</scope>
        </dependency>
    </dependencies>
  1. CglibTest.java
public class CglibTest implements MethodInterceptor {
    public void run() {
        System.out.println("hello cglib");
    }

    @Override
    public Object intercept(Object o, Method method, Object[] objects, MethodProxy methodProxy) throws Throwable {
        System.out.println("before run()");
        methodProxy.invokeSuper(o, objects);
        System.out.println("after run()");
        return null;
    }
}
  1. Main.java
public class Main {
    public static void main(String[] args) {
        System.out.println("Hello world!");

        CglibTest cglibTest = new CglibTest();
        Enhancer enhancer = new Enhancer();
        enhancer.setSuperclass(CglibTest.class);
        enhancer.setCallback(cglibTest);
        CglibTest testService = (CglibTest) enhancer.create();
        System.out.println("CglibTest : " + testService.getClass().getName());
    }
}
  1. javaagent + javassist
public class Agent {
    public static void premain(String agentArgs, Instrumentation inst) {
        MonitorTransformer transformer = new MonitorTransformer();
        inst.addTransformer(transformer, true);
    }
}

public class MonitorTransformer implements ClassFileTransformer {

    @Override
    public byte[] transform(ClassLoader loader, String originalClsName, Class<?> classBeingRedefined, ProtectionDomain protectionDomain, byte[] classfileBuffer) {
        String className = originalClsName.replaceAll("/", ".");
        if (className.startsWith("java.") || className.startsWith("sun.")
                || className.startsWith("jdk.") || className.startsWith("javax.")
                || className.startsWith("com.sun.")
        ) {
            return classfileBuffer;
        }

        ClassPool ctPool = ClassPool.getDefault();
        CtClass ctClass;
        try {
            try {
                ctClass = ctPool.get(className);
            } catch (NotFoundException e) {
                ctPool.appendClassPath(new LoaderClassPath(loader));
                try {
                    ctClass = ctPool.get(className);
                } catch (NotFoundException ne) {
                    System.out.println("javassist fail, ctClass not found: " + className + ", origin: " + originalClsName);
                    ne.printStackTrace();
                    return classfileBuffer;
                }
            }
            return ctClass.toBytecode();
        } catch (Error e) {
            e.printStackTrace();
        } catch (Exception e) {
            e.printStackTrace();
        }
        return classfileBuffer;
    }

    @Override
    public byte[] transform(Module module, ClassLoader loader, String className, Class<?> classBeingRedefined, ProtectionDomain protectionDomain, byte[] classfileBuffer) throws IllegalClassFormatException {
        ClassLoader cl = module.getClassLoader() == null ? loader : module.getClassLoader();
        return this.transform(cl, className, classBeingRedefined, protectionDomain, classfileBuffer);
    }
}

I run, then throw exceptions like this: javassist.NotFoundException: org.example.CglibTest$$EnhancerByCGLIB$$f3005a82

I try to use jdk-dynamic-proxy, it is normal in this situation. I don't know why Javassist threw such an exception when encountering Cglib. Can someone help me solve it?

0

There are 0 best solutions below