动态代理study高级原理aspectj_第1页
已阅读1页,还剩11页未读 继续免费阅读

付费下载

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

1、Aop其它阅读除了javaWeb标准的Filter有着AOP的感觉外,AOP一共有两大写法,都适用于web项目1、AspectJ参见 HYPERLINK /u012150370/article/details/51394915 /u012150370/article/details/51394915 SpringAOP面向切面详解(带实例) 【基本】 HYPERLINK /winter_chen001/article/details/71170872 /winter_chen001/article/details/71170872 利用拦截实现登陆控制【基本】2、springMVC自带的拦截器

2、 Interceptor它仅适用于、也专针对于web项目,满足web一般需要,有丰富的功能。Aop概念连接点Joinpoint可以进行切入开发的点。如一个方法、一个代码块、一个try块(AspectJ中原本规定可以有这些)。但是spring只支持把方法作为连接点。切入点Pointcut已经被选定作为切面开发的点。通知/增强Advice对切入点可以做的各种事情。如前置通知before()、后置通知after()、环绕通知around()、异常通知exception()等。java程序中,往往把这些通知放入到一个额外的类中书写。目标对象Target(略)目标对象是被切入的对象。但是由于类是对象的模

3、板,是由类new()出来的,所以目标当然就是一个个的类了。代理对象Proxy(略)由于本章节,是spring自行内在完成代理对象的所有工作,我们只管用就好,所以不必专门学习。如果要知道原理请学习动态代理。切面Aspect切入点被融入通知后,产生的整体效应。(不必强行理解这个词)AspectJ的使用步骤0、所用代码此代码用的是注解配置方式。一、下载必备jar包我曾在这里下载过jar包来用/aspectj/downloads.php aspectj下载的地方 HYPERLINK /artifact/org.aspectj/aspectjweaver/1.8.7 /artifact/org.aspe

4、ctj/aspectjweaver/1.8.7 aspectjweaver下载的地方我用的是其中这两个包aspectj-1.8.13.jaraspectjweaver-1.8.7.jar当然spring的aop包也得有,我用的是spring-aop-4.3.4.RELEASE.jarspring-aspects-4.3.4.RELEASE.jar当然,如果是maven项目,spring的aop会自动把依赖的jar文件引用过来,更加方便。二、编写目标对象概念说明:java的目标对象实际上是一个类,其中的方法是可以被切入的,称为“连接点”,而已被切入的方法叫做“切入点”。比较典型的目标对象就是将来

5、要写的service层(因service层的方法往往是独立的操作)。package com.qq.service;public interface UserService public void save();public void delete();public void update();public void select();package com.qq.service;public class UserServiceImpl implements UserServicepublic void save() System.out.println(保存用户);public void de

6、lete() System.out.println(删除用户);public void update() System.out.println(更新用户-);/int a = 7/0; /将这句打开,会得到不同的结果public void select() System.out.println(查询用户);三、编写通知java的通知都写在一个类中,其中的方法就是“通知”。可以切入到目标对象。spring支持的通知如下1、前置通知:在目标方法之前调用2、后置通知:(如果出现异常就不调用):在目标方法之后调用3、后置通知:(无论是否出现异常都会调用):在目标方法之后调用4、环绕通知:在目标方法之前

7、、后调用5、异常通知:出现异常时就调用package com.qq.aop.advice;import org.aspectj.lang.ProceedingJoinPoint;/通知类public class TransactionAdvice public void before() System.out.println(前置通知被执行);public void afterReturning () System.out.println(后置通知被执行(出现异常不调用));public void after() System.out.println(后置通知被执行(无论是否出现异常都要调用)

8、);public void afterException() System.out.println(异常通知被执行);public Object around(ProceedingJoinPoint point) throws Throwable System.out.println(环绕 前通知被执行);Object proceed = ceed();/调用目标方法System.out.println(环绕 后通知被执行);return proceed;四、将通知织入到目标对象也就是实施切入。(切入后就形成了切面。spring框架内部运行机制会自行构建所谓的“代理对象”)。先在xml文件加入

9、aop名称空间。再配置目标对象、通知对象、织入配置。共有两种写法方式(1)xml配置(2)注解配置法一:纯xml配置方式 /正因为这里的ref所以使通知对象能起作用法二:注解配置方式这种方式,xml中就不必写节点了。但在xml文件中必须加上这句来开启注解然后主要是在通知类中进行织入的配置1、类上加Aspect注解,2、在类中指定切入点Pointcut(“execution(.)”),标在一个空方法上面3、指定各种通知方法,即在各个方法上标注Before 、After 、Around等等,并添加。示例package com.qq.aop.advice;import org.aspectj.lan

10、g.ProceedingJoinPoint;import org.aspectj.lang.annotation.After;import org.aspectj.lang.annotation.AfterReturning;import org.aspectj.lang.annotation.AfterThrowing;import org.aspectj.lang.annotation.Around;import org.aspectj.lang.annotation.Aspect;import org.aspectj.lang.annotation.Before;import org.a

11、spectj.lang.annotation.Pointcut;/通知类Aspectpublic class TransactionAdvice Pointcut(execution(public void com.qq.service.UserServiceImpl.update()public void pointCut() Before(TransactionAdvice.pointCut()public void before() System.out.println(前置通知被执行);AfterReturning(TransactionAdvice.pointCut()public

12、void afterReturning () System.out.println(后置通知被执行(出现异常不调用));After(TransactionAdvice.pointCut()public void after() System.out.println(后置通知被执行(无论是否出现异常都要调用));AfterThrowing(TransactionAdvice.pointCut()public void afterException() System.out.println(异常通知被执行);Around(TransactionAdvice.pointCut()public Obj

13、ect around(ProceedingJoinPoint point) throws Throwable System.out.println(环绕 前通知被执行);Object proceed = ceed();/调用目标方法System.out.println(环绕 后通知被执行);return proceed;/另外通知类也是一个,如果我们不想在xml中书写,也可以改成用注解的方式,即需要做使用component标注通知类2、在xml配置文件中用 语句把通知类所在包的路径填进去虽然注解的方式看似先进,然而并不见得真正比xml的方式方便。五、测试注意:一定要从容器中拿目标对象,它才能够

14、被切。new出来的对象是无法被切的。import org.springframework.context.support.AbstractApplicationContext;import org.springframework.context.support.ClassPathXmlApplicationContext;import com.qq.service.UserService;import com.qq.service.UserServiceImpl;public class AopTest public static void main(String args) Abstract

15、ApplicationContext context = new ClassPathXmlApplicationContext(classpath:applicationContext.xml);System.out.println(-从容器中拿-);UserService u= (UserService)context.getBean(userService1); /上面这个地方一定是拿到接口UserService强转,如果用往UserServiceImpl强转会报错u.update();System.out.println(打印代理类名=+u.getClass().getName();Sy

16、stem.out.println(打印代理类对象=+u);/下面这句会报错,原因说法是:动态代理的一些原理/UserServiceImpl u2= (UserServiceImpl)context.getBean(userService1);System.out.println(-用new的方式,而不是从容器中拿,就发生不了切入-);/如果用new,UserService u3 = new UserServiceImpl();u3.update();运行结果-从容器中拿-前置通知被执行环绕 前通知被执行更新用户-环绕 后通知被执行后置通知被执行(无论是否出现异常都要调用)后置通知被执行(出现异

17、常不调用)打印代理类名=xy.$Proxy2打印代理类对象=com.qq.service.UserServiceImpl47542153-用new的方式,而不是从容器中拿,就发生不了切入-更新用户-在aspectJ中获取http的session的办法见 HYPERLINK /H12KJGJ/article/details/74859418 /H12KJGJ/article/details/74859418 Springmvc AOP拦截Controller获取session代码如下import org.springframework.web.context.request.RequestCon

18、textHolder;import org.springframework.web.context.request.ServletRequestAttributes;HttpServletRequest request =(ServletRequestAttributes) RequestContextHolder.getRequestAttributes().getRequest(); HttpSession session =request.getSession(); Around方法与“拦截”“不放行”只有Around方法能够达到“拦截住而不放行”的效果。Around会强制要求所修饰的方

19、法含有参数(ProceedingJoinPoint point),因为这个参数就是用于控制是否放行的。ceed()代表放行,有点类似Servlet规范中的Filter的Chain.doFilter(req,resp)。下表来对比一下写法AroundAround(TransactionAdvice.pointCut()public Object around(ProceedingJoinPoint point) throws Throwable System.out.println(环绕 前通知被执行);Object proceed = ceed();/放行,实际是它可以调用目标方法System

20、.out.println(环绕 后通知被执行);return proceed;过滤器Filterpublic class AllFilter implements FilterOverridepublic void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)throws IOException, ServletException System.out.println(时间1= + System.currentTimeMillis();chain.doFilter(request, r

21、esponse); /放行 将请求传递下去System.out.println(时间2= + System.currentTimeMillis();Servlet规范中的这个写法可以计算出请求所耗的整个时间而Before无法终止所切方法的执行,可见 HYPERLINK /question/371919831993534884.html /question/371919831993534884.html。另外,经验在做拦截的Around方法中,返回值我使用过下面的写法return xxx/yyy/zzz ; /情况一:不放行 /也可以尝试返回一个对象return ceed();/情况二:放行对于

22、 情况一,要求这个返回值要能够通过类型转换机制 变成为 控制器方法的返回值类型,如果转换出错,则会报错。同时这也说明,对于情况一,实际上是拦截器的返回值替代了控制器方法的返回值,这就是拦截的意义所在。对于情况二,ceed()也就是允许请求通过的意思,畅通无阻。AspectJ正则表达式(用于匹配“连接点”)表示“切入点”的写法方式很丰富,spring支持AspectJ的很多匹配写法。参见: HYPERLINK /sunlihuo/article/details/52701548 /sunlihuo/article/details/52701548。 AspectJ语法详解:execution,within,this,Aspect 。这篇文章中写了常用的exe

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

最新文档

评论

0/150

提交评论