views:

41

answers:

2

Like so : a class has a method called sayHello() . When a instance of the class call the sayHello(), a method in another class is called automatic before the sayHello() is called.

the sample code can be like this:

public class Robot{
  public static void doSomethingBefore(){
       System.out.println("Do something before sayHello");
  }

}


public class Person {

     public void sayHello(){
           System.out.println("hello");
     }

     public static void main(String[] args){
             Person p = new Person();
             p.sayHello();
     }
}

Output Result :

Do something before sayHello
hello

It seems it can be done by using the proxy pattern. But I want it can be more simple.

Use the annotation:

@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.METHOD})
public @interface MethodListener {
      public String className();
      public String methodName();
}

Then put the MethodListener annotation on the method sayHello() in the Person class,

public class Person {
  @MethodListener(className="Robot",methodName="doSomethingBefore")
  public void sayHello(){
       System.out.println("hello");
  }

  public static void main(String[] args){
         Person p = new Person();
         p.sayHello();
  }
 }

When the method which has the MethodListener annotation be called, the method doSomethingBefore() is called automatic.

Should it be possible ? If it can be done, how to achieve it?

+2  A: 

Check AspectJ, and aspect-oriented programming framework. It will allow you to do something similar.

You see, in order to make this happen, you class should be managed by some container which instantiates your objects and makes proxies of them.

AspectJ has an alternative by plugging some "magic" into the VM.

Bozho
+2  A: 

I think you are looking for an aspect-oriented programming framework such as AspectJ, JBoss AOP or Spring AOP.

The decoration of the Person method by the Robot method will happen during construction of the Person instance, but you will need to use a factory class provided by the AOP container instead of new.

richj