Spring 3.2 AOP - Intercepting methods by annotation
In your test code, you are not allowing Spring to create your MyComponent
, but instead, you are using the new
operator. You should be accessing MyComponent
from Spring's ApplicationContext
.
public class SomeTest {
public static void main(String[] args) throws Exception {
final ApplicationContext appContext = new ClassPathXmlApplicationContext("spring-config.xml");
final MyComponent myComponent = appContext.getBean(MyComponent.class);
//your test here...
}
}
If you do not get your component from Spring, how do you expect it to be proxied?
Comments
-
Lancelot almost 2 years
I'm trying to intercept any method tagged w/ a custom annotation and the reason you read this is because I can't get it to work. I've been following simple examples but can't get it to work.
Here is my code.
MyAnnotation.java:
@Retention(RetentionPolicy.RUNTIME) @Target(ElementType.METHOD) public @interface MyAnnotation { String value() default ""; String key() default ""; String condition() default ""; }
MyAspect.java:
@Aspect public class MyAspect { @Pointcut(value="execution(public * *(..))") public void anyPublicMethod() { } @Around("anyPublicMethod() && @annotation(myAnnotation)") public Object process(ProceedingJoinPoint jointPoint, MyAnnotation myAnnotation) throws Throwable { System.out.println("In AOP process"); return 5; //jointPoint.proceed(); } }
spring-config.xml:
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:mvc="http://www.springframework.org/schema/mvc" xmlns:c="http://www.springframework.org/schema/c" xmlns:context="http://www.springframework.org/schema/context" xmlns:tx="http://www.springframework.org/schema/tx" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop" xmlns:p="http://www.springframework.org/schema/p" xmlns:cache="http://www.springframework.org/schema/cache" xmlns:task="http://www.springframework.org/schema/task" xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.2.xsd http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-3.2.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.2.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-3.2.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-3.2.xsd http://www.springframework.org/schema/cache http://www.springframework.org/schema/cache/spring-cache-3.2.xsd http://www.springframework.org/schema/task http://www.springframework.org/schema/task/spring-task-3.2.xsd"> ... <context:component-scan base-package="com.myapp"> <context:include-filter type="annotation" expression="org.aspectj.lang.annotation.Aspect"/> </context:component-scan> <aop:aspectj-autoproxy proxy-target-class="true" /> <bean id="myAspect" class="com.myapp.annotation.MyAspect" /> ...
MyComponent.java:
@Component public class MyComponent { @MyAnnotation(value="valtest", key="keytest", condition="contest") public int add(int i, int j) { System.out.println("Executing annotation.add"); return i+j; } }
Test code:
final MyComponent m = new MyComponent(); assertTrue(5 == m.add(0, 1)); // Here m.add(...) always returns 1 instead of 5.
As a side note I've tried to define my pointcut many different ways, all with and without the use of the anyPublic() method and its execution pointcut, but none of those worked for me:
@Around("@annotation(com.myapp.annotation.MyAnnotation)") public Object process(ProceedingJoinPoint jointPoint) throws Throwable { .. }
@Around(value="@annotation(myAnnotation)", argNames="myAnnotation") public Object process(ProceedingJoinPoint jointPoint, MyAnnotation myAnnotation) throws Throwable { .. }
@Around("execution(* com.myapp.*.*(..)) && @annotation(com.myapp.annotation.MyAnnotation)") public Object process(ProceedingJoinPoint jointPoint) throws Throwable { .. }
What am I doing wrong?