0

I am trying to learn Spring AOP implementation using AspectJ. I have 5 classes in different packages.

package com.sample.a; Class A{ public void save(){ } } } 

package com.sample.b; Class B { public void save(){ } } 

package com.sample.c; Class C { public void save(){ } } 

package com.sample.d; Class D{ public void save(){ } } 

package com.sample.e; Class E{ public void save(){ } } 

Whenever these method gets called, I need to print "Hello World", How can I achieve the above scenario using Spring AOP (AspectJ). I have done the following so far -

1) Enabled Spring AspectJ support in applicationContext.xml

<aop:aspectj-autoproxy /> 

2) Defined reference of Aspect in applicationContext.xml

<bean id="sampleAspectJ" class="com.sample.xxxxxxxx" /> 

3) Aspect Class

/** * aspect class that contains after advice */ package com.sample; import org.aspectj.lang.JoinPoint; import org.aspectj.lang.annotation.After; import org.aspectj.lang.annotation.Aspect; @Aspect public class SpringAopSample{ @After(value = "execution(* com.sample.*.Save(..))") public void test(JoinPoint joinPoint) { System.out.println("Hello World"); } } 

is there any better way to achieve the above scenario? what if these 5 classes are in different packages and have different method names? Do I need to write 5 different methods in aspect (annotated with @after advice)

2
  • What do you mean by "better"? What exactly do you want your pointcut to match? Commented Dec 20, 2014 at 23:20
  • About your questions - "what if these 5 classes are in different packages and have different method names?" - If they have different names you would still need to have some common pattern so that you can create a regex otherwise the aspect will get applied to all methods in the class which may not be intended. Commented Dec 21, 2014 at 3:38

1 Answer 1

2

You should get acquainted with AspectJ pointcut syntax. For instance

  • your own pointcut execution(* com.sample.*.Save(..)) from the example will not match any of the sample save() methods because
    • you wrote Save() with a capital "S", but the methods have lower-case "s" as their first character,
    • your classes would rather match com.sample.*.* (sub-package!) than just com.sample.*.
  • So you can match all save() methods in sub-package classes like this: execution(* com.sample.*.*.save(..)). The first * is the subpackage a to d, the second * is the class name.
  • If you want to match sub-packages and even classes hierarchically to any depth you can just use the .. syntax like this: execution(* com.sample..save(..))
  • If you want to match only public void methods of any name and without parameters in all sub-packages, you can use execution(public void com.sample..*())

And so forth. I hope this answers your question even though it is kind of unclear what exactly you want to know.

Sign up to request clarification or add additional context in comments.

2 Comments

Thank you so much, your answer indeed has cleared lot of doubts.
I have a little doubt. Class A, B, C, D and E have to be service layer classes annotated with @Service or @Component?

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.