CGLIB dynamic proxy

What is Cglib?

CGLIB(Code Generation Library) is an open-source project!

Is a powerful, high-performance, high-quality code-generated library that extends Java classes and implements Java interfaces at run time.

CGLIB is a powerful high-performance code generation package. It is widely used by many AOP frameworks, such as Spring AOP and Dynaop, to provide methods for interception. Hibernate, the most popular OR Mapping tool, also uses CGLIB to broker single-ended(many-to-one and one-to-one) associations (lazy fetching of collections is implemented using other mechanisms). EasyMock and jMock are packages that test Java code using mock objects. They both use CGLIB to create mock objects for classes that have no interfaces.

CGLIIB implements dynamic proxies

We’ll start with a service notice there’s no interface

public class CglibService {
    public CglibService(a) {
        System.out.println("CglibDao constructor");
    }

    /** * This method cannot be overridden by subclasses. Cglib is not a proxy for final modified methods@param name
     * @return* /
    final public String sayOthers(String name){
        System.out.println("CglibDao final sayOthers:"+name);
        return null;
    }

    public void sayHello(a){
        System.out.println("CglibDao:sayHello"); }}Copy the code

Create a new Interceptor implementation org. Springframework. Additional, proxy. MethodInterceptor

public class MyMethodInterceptor implements MethodInterceptor {
    / * * * *@paramO Proxy object *@paramMethod Method of the proxied object *@paramThe objects method takes the parameter *@paramMethodProxy Proxy method *@return
     * @throws Throwable
     */
    @Override
    public Object intercept(Object o, Method method, Object[] objects, MethodProxy methodProxy) throws Throwable {
        System.out.println("====== Insert pre-notification ======");
        Object object = methodProxy.invokeSuper(o, objects);
        System.out.println("====== insert post-notification ======");
        returnobject; }}Copy the code

Creating a Test Class

/** * cglib dynamic proxy test */
public class cglibAgentTest {

    @Test
    public void testCglibAgent(a){
        Enhancer enhancer = new Enhancer();
        enhancer.setSuperclass(CglibService.class);
        // Set the enhancer callback object
        enhancer.setCallback(new MyMethodInterceptor());
        // Create a proxy object
        CglibService proxy= (CglibService)enhancer.create();
        // Call the target method through the proxy object
        proxy.sayHello();
        proxy.sayOthers("Xiao Ming"); }}Copy the code

Print the value of the

CglibDao constructor = = = = = = insert front notice = = = = = = CglibDao: insert rear sayHello = = = = = = = = = = = = CglibDao noticefinalSayOthers: xiao MingCopy the code

You can see that their constructor is going to execute first and their proxy method is going to be called first when sayHello is called if the proxy can’t be implemented when the method is final

conclusion

Unlike the dynamic proxy implemented by InvocationHandler, Cglib does not have a write interface

Aop in Spring can also be configured to adopt the Cglib approach

In addition to the CGLIB package, scripting languages such as Groovy and BeanShell also use ASM to generate Java bytecode. Of course, direct use of ASM is discouraged,

Because it requires you to be familiar with the JVM’s internal structure, including the class file format and instruction set, Cglib is recommended