javadelegationbyte-buddyintercept

Java & Bytebuddy : How to get MethodDelegation to work properly


I have the following code

package io.xxx.intercepter;

import java.lang.reflect.Method;
import net.bytebuddy.ByteBuddy;
import net.bytebuddy.implementation.MethodDelegation;
import net.bytebuddy.implementation.bind.annotation.AllArguments;
import net.bytebuddy.implementation.bind.annotation.Empty;
import net.bytebuddy.implementation.bind.annotation.Origin;
import net.bytebuddy.implementation.bind.annotation.RuntimeType;
import net.bytebuddy.implementation.bind.annotation.SuperMethod;
import net.bytebuddy.implementation.bind.annotation.This;
import net.bytebuddy.matcher.ElementMatchers;

public class Proxy {
  
  public static void main(String[] args) throws Exception {

    new ByteBuddy()
    .subclass(Person.class)
    .method(ElementMatchers.any())
    .intercept(MethodDelegation.to(Interceptor.class))
    .make()
    .load(Person.class.getClassLoader())
    .getLoaded()
    .getDeclaredConstructor()
    .newInstance()
    .getJob("egnineer");
  }
  
  public class Person {
    
    private String work = "coding";
    
    public Person() {}
    
    public String getJob(String job) {
      
      this.work = job;
      
      System.out.println("I'm the Person " + work);
      
      return work;
    }
  }

 public class Interceptor {
  
    @RuntimeType
    public static Object intercept(
        @This Object self, 
        @Origin Method method,
        @AllArguments Object[] args,
        @SuperMethod(nullIfImpossible = true) Method superMethod,
        @Empty Object defaultValue) throws Throwable {
  
      if(superMethod == null)
        return defaultValue;
      
      System.out.println("I'm the proxy --> " + method.getName());
 
      Object object = superMethod.invoke(self, args);
  
      return object;

    }
  }
}

Goal : To intercept the person.getJob(String) method

Problem :

Exception in thread "main" java.lang.NoSuchMethodException: io.xxx.intercepter.Proxy$Person$ByteBuddy$LI9kwh7B.<init>()
    at java.base/java.lang.Class.getConstructor0(Class.java:3585)
    at java.base/java.lang.Class.getDeclaredConstructor(Class.java:2754)
    at io.xxx.intercepter.Proxy.main(Proxy.java:25)

Solution

  • Wouldn't you want to intercept to Interceptor.class rather then Proxy.class?

    I assume it's as simple as that.