Why my Aspect is not detected for Jersey controller (using custom annotation)?

生来就可爱ヽ(ⅴ<●) 提交于 2019-12-04 05:41:02

It looks like the same problem I was having. Based on what you've provided, it looks like you're using Spring AOP on an object that is not created by Spring (presumably Jersey is what creates your controller class instances) and therefore the advice is not being applied. Eclipse says its being advised, but that would only be for instances of your controller that are created by Spring. The ones you are actually using, the ones created by Jersey (or whatever provider you are using), are not advised.

I spent a lot of time trying to get Jersey to use Spring to create controller instances (including a couple of plugins that claimed to be able to do just that), but never could get it to work. I was able to get it working by using AspectJ directly instead of Spring AOP. It wasn't very hard, with exception of figuring out how to get spring to inject into the aspect.

Added:

The annotations remain the same. You just need to remove the AOP stuff from spring.xml, and create an aop.xml file in META-INF. Here's what mine looks like:

<!DOCTYPE aspectj PUBLIC "-//AspectJ//DTD//EN" "http://www.eclipse.org/aspectj/dtd/aspectj.dtd">
<aspectj>
    <aspects>
        <aspect name="com.ancestry.academy.api.ServiceApiAspect" />
        <aspect name="com.ancestry.academy.manager.ManagerApiAspect" />
    </aspects>
</aspectj>

You can keep Spring AOP for classes that are spring loaded. You only have to do this for classes that are created outside of spring (like controllers for jax).

There's one little piece of black magic that I don't really understand. If you need to use spring to inject into your aspect itself, then you need to declare it in spring.xml like this:

<bean id="serviceApiAspect" class="com.ancestry.academy.api.ServiceApiAspect" factory-method="aspectOf" />

<bean id="managerApiAspect" class="com.ancestry.academy.manager.ManagerApiAspect" factory-method="aspectOf" />

Note that my aspects do NOT have a method named aspectOf. Apparently that's added by AspectJ. That was pretty much all there was to it.

Federico Piazza

I found why my aspects weren't working with Jersey because I had to use the weaver for this particular case.

After configuring aspectj-maven-plugin to weave my aspects everything works successfully.

The full details to configure the weaver can be found on this answer: Spring + AspectJ weaving for java 8 using aspectj-maven-plugin

add

compile 'org.aspectj:aspectjtools:1.8.1'
compile 'org.aspectj:aspectjrt:1.8.1'

make annotation

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)
public @interface ParmsAudit
{
  String action();
}

aspect class

@Aspect
public class AuditAspect {

@Before(value="execution(@uk.co.billcomer.audit.ParmsAudit * *(..)) &&   @annotation(parmsAudit)", argNames="parmsAudit")
public void logTheAuditActivity(JoinPoint aPoint, ParmsAudit parmsAudit) {
 String userName = getUserName();
 mlogger.info("Parms Auditing User Name: " + userName);
 mlogger.info("auditType:" + parmsAudit.auditType().getDescription());

 String arguments = getArgs(aPoint.getArgs());

 if (arguments.length() > 0) {
 mlogger.info("args-" + arguments);
 }
}

private String getArgs(Object[] args) {
 String arguments = "";
 int argCount = 0;

 for (Object object : args) {
   if (argCount > 0) {
     arguments += ", ";
   }
   arguments += "arg[" + ++argCount + "]=" + "[" + object + "]";
 }
 return arguments;
}

private String getUserName() {
 try {
   return SecurityContextHolder.getContext().getAuthentication().getName();
 } catch (NullPointerException npe) {
   return "Unknown User";
 }
}
}

This is nice link http://billcomer.blogspot.in/2011/07/auditing-using-aop-and-annotations-in.html

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!