博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Spring aop: 通过注解实现对controller的aop,出现的问题
阅读量:5020 次
发布时间:2019-06-12

本文共 4271 字,大约阅读时间需要 14 分钟。

前提1:web.xml中:

     
Spring-mvc
org.springframework.web.servlet.DispatcherServlet
contextConfigLocation
/WEB-INF/DispatcherServlet.xml
1
Spring-mvc
*.do

  

前提2:DispatcherServlet.xml中(另外就是几个interceptor)

前提3: 后文描述的情况,在<aop:aspectj-autoproxy proxy-target-class="true"/>与<aop:aspectj-autoproxy proxy-target-class="false"/>两种前提下,结果毫无差别。

    

前提4:controller为com.BaseController,通过<context:component-scan base-package="com"></context:component-scan>生成

 

@Component@Aspectpublic class aopDefault {        private long beginTime;        @Pointcut("execution(* org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter.handle(..))")    private void aspect(){}//定义一个切入点          @Pointcut("execution(* com.BaseController.*(..))") private void _aspect(){}//定义一个切入点  @Before("execution(* com.BaseController.*(..))")//定义前置通知 public void doBefore(){ beginTime = System.currentTimeMillis(); System.out.println("doBefore"); } @AfterReturning("execution(* com.BaseController.*(..))")//定义后置通知 public void doAfter(JoinPoint joinpoint){ String className = joinpoint.getTarget().getClass().getName(); String method = joinpoint.getSignature().getName(); long endTime = System.currentTimeMillis(); long duration= endTime-beginTime; System.out.println("doAfter"); System.out.println("Method: "+className+"."+method); System.out.println("Elapsed time : "+duration + "ms"); System.out.println(""); } //doAround注解方法1 @Around("aspect()") public void doAround(){ System.out.println("doAround_1"); } //doAround注解方法2 @Around("_aspect()") public void _doAround(){ System.out.println("doAround_2"); } //doAround注解方法3 @Around("execution(* org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter.handle(..))") public void _doAround_(){ System.out.println("doAround_3"); } }

结果

控制台(显然,“doAround注解方法1” 和 “doAround注解方法3” 完全不起作用,而Before,AfterReturning都OK,说明

("execution(* org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter.handle(..))")

这玩意儿,反正在我这是死活没有一点儿用,再说一遍proxy-target-class="true"还是"false"都没用):

doAround_2doAfterMethod: com.BaseController.loginElapsed time : 1466612786129ms

页面部分结果(结果为error,就算将“返回值json”这一条件去除,也得不到任何返回值):

ajax.js:51 200ajax.js:52 4ajax.js:53 parsererrorajax代码为$.ajax({        url:"login.do",         type:"post",        dataType:"json", data:{userName:username, userPwd:pwd}, error: function(XMLHttpRequest, textStatus, errorThrown) { console.log(XMLHttpRequest.status); console.log(XMLHttpRequest.readyState); console.log(textStatus); }, success: function(json){ ... } });

6月23日补充(之前的结论太糙了。。。):

@Around("execution(* com.BaseController.*(..))")

public Object doAround(ProceedingJoinPoint pjp) throws Throwable {
   Object retVal = pjp.proceed();
   System.out.println("doAround_1");
   return retVal;
}

@Around里,应该引入org.aspectj.lang.ProceedingJoinPoint,让其procced()并将其返回,否则被“切”的controller方法倒是也能继续进行,就是返回值为null(症状跟上文描述的一样,@Before不运行,@AfterReturning能正常运行)。。。。继续琢磨。。。。。

正常的运行顺序,@Before -》 @Around -》 @AfterReturning

写法:

@Pointcut("execution(* com.BaseController.*(..))")

private void aspect(){}//定义一个切入点

@Before("aspect()") ....  

@Around("aspect()") 引入ProceedingJoinPoint,并.proceed(),返回 ....  

@AfterReturning("aspect()") ....  

 

 

6月27日补充:

@RequestMapping(...)    @ResponseBody    @ControllerPointcut(str = ...)     public String initParams(HttpSession session){...}
@Target(ElementType.METHOD)@Retention(RetentionPolicy.RUNTIME)public @interface ControllerPointcut {    ...}
@Component@Aspectpublic class ElapsedTimeAOP {        private long beginTime;        @Pointcut("@annotation(com.annotation.ControllerPointcut)")    private void controller(){}//定义一个切入点     ...}

鉴于刚学了annotation,这里定义一个annotation,在@pointcut里用以上形式做定义,然后到controller类里按需标注在方法前,即可以对该方法做aop,这样可以减少aop定义代码中的耦合,扩展起来还比较方便。

btw,抱歉写的可能很让人头晕,水平有限。

 

这是参考的帖子:

http://itindex.net/detail/50710-springaop-controller-service/

http://yjian84.iteye.com/blog/1920787

http://phoenixfu.iteye.com/blog/2037598

http://www.oschina.net/question/222929_124314?fromerr=BICW0JoJ

http://usherlight.iteye.com/blog/1306111

 

转载于:https://www.cnblogs.com/ajjiangxin/p/5609135.html

你可能感兴趣的文章
在eclipse中设计BPMN 2.0工作流定义的根本步骤
查看>>
Json对象与Json字符串互转(4种转换方式)
查看>>
PAT甲级1002 链表实现方法
查看>>
查看Linux信息
查看>>
Python中sys模块sys.argv取值并判断
查看>>
【详记MySql问题大全集】四、设置MySql大小写敏感(踩坑血泪史)
查看>>
并查集
查看>>
ubuntu 11.04下android开发环境的搭建!
查看>>
Bzoj 3343: 教主的魔法
查看>>
括号序列(栈)
查看>>
一件趣事
查看>>
DevExpress控件TExtLookupComboBox实现多列模糊匹配输入的方法
查看>>
atom 调用g++编译cpp文件
查看>>
H3C HDLC协议特点
查看>>
iptables 网址转译 (Network address translation,NAT)
查看>>
ios __block typeof 编译错误解决
查看>>
android 插件形式运行未安装apk
查看>>
ios开发之 manage the concurrency with NSOperation
查看>>
Android权限 uses-permission
查看>>
NSEnumerator用法小结
查看>>