需要用的基本的jar包:

aopalliance-1.0.jar
aspectj-1.6.8.jar
aspectjweaver-1.6.8.jar
commons-logging-1.1.3.jar
spring-aop-4.0.0.RELEASE.jar
spring-aspects-4.0.0.RELEASE.jar
spring-beans-4.0.0.RELEASE.jar
spring-context-4.0.0.RELEASE.jar
spring-core-4.0.0.RELEASE.jar
spring-expression-4.0.0.RELEASE.jar

1:基于注解的日志通知和验证通知:

定义接口:

 package com.yinfu.spring.aop.impl;

 public interface ArithmeticCalculator {

     public int add(int i,int j);
public int sub(int i,int j);
public int mul(int i,int j);
public int div(int i,int j);
}

定义实现类:

 package com.yinfu.spring.aop.impl;

 import org.springframework.stereotype.Component;

 @Component("arithmeticCalculator")
public class ArithmeticCalculatorImpl implements ArithmeticCalculator { @Override
public int add(int i, int j) { int result = i+j;
return result;
} @Override
public int sub(int i, int j) {
int result = i-j;
return result;
} @Override
public int mul(int i, int j) {
int result = i*j;
return result;
} @Override
public int div(int i, int j) {
int result = i/j;
return result;
} }

定义spring的配置文件:applicationContext.xml:

 <?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:aop="http://www.springframework.org/schema/aop"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-4.0.xsd
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.2.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.0.xsd"> <!-- <bean id="helloWorld" class="com.yinfu.spring.beans.HelloWorld">
<property name="name" value="fuck"></property>
</bean> -->
<!-- 配置自动扫描包 -->
<context:component-scan base-package="com.yinfu.spring.aop.impl"></context:component-scan> <!-- 使AspectJ注解起作用:自动为匹配的类生成代理对象 -->
<aop:aspectj-autoproxy></aop:aspectj-autoproxy> </beans>

定义切面类:

 package com.yinfu.spring.aop.impl;

 import java.util.Arrays;
import java.util.List; import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.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.aspectj.lang.annotation.Pointcut;
import org.springframework.core.annotation.Order;
import org.springframework.stereotype.Component; /**
* 把此类声明为一个切面
* 首相把该类放到IOC容器中,然后在声明为切面
* @Aspect声明此类是一个切面
* @Order声明切面的优先级,值越小优先级越高
* @author lusong
*
*/
@Order(1)
@Aspect
@Component
public class LoggingAspect { //定义一个方法用于声明切入点表达式,因为表达式都相同,可以进行封装不过方法内不需要添加其他代码
//使用@Pointcut声明切入点表达式
/**
* 此时下面的通知注解都可以将value值写成此方法名 如:@Before("declareJoinPointException()")即可
*/
@Pointcut("execution(public int com.yinfu.spring.aop.impl.ArithmeticCalculatorImpl.*(int, int))")
public void declareJoinPointException(){} //1.前置通知:声明该方法是一个前置方法,在指定目标方法之前执行
/**
* before中写的是aspectj的表达式
* public int可以用*代替,代表:任意修饰符和任意返回值
* com.yinfu.spring.aop.impl代表包名
* ArithmeticCalculatorImpl代表类名,可以用*代替,代表该包下的任意类
* add代表方法名,可以用*好代替,代表该类下的任意方法
* (int,int)参数类型,可以用..代替
* @param joinPoint 链接点利用此链接点可以得到代理对象中的方法名称和参数等细节
*/
@Before("execution(public int com.yinfu.spring.aop.impl.ArithmeticCalculatorImpl.*(int, int))")
public void beforeMethod(JoinPoint joinPoint ){
String methodName = joinPoint.getSignature().getName();
List<Object> args = Arrays.asList(joinPoint.getArgs());
System.out.println("this method "+methodName+" begin"+args);
}
//2.后置通知:在目标方法执行后(无论是否发生异常),执行的通知
//后置通知中还不能访问目标方法执行的结果
@After("execution(public int com.yinfu.spring.aop.impl.ArithmeticCalculatorImpl.*(int, int))")
public void afterMethod(JoinPoint joinPoint ){
String methodName = joinPoint.getSignature().getName();
System.out.println("this method "+methodName+" end");
} //3返回通知:在目标方法正常执行后,执行的通知
//返回通知是可以访问到方法的返回值的
@AfterReturning(value="execution(public int com.yinfu.spring.aop.impl.ArithmeticCalculatorImpl.*(int, int))",returning="result")
public void afterReturning(JoinPoint joinPoint ,Object result){
String methodName = joinPoint.getSignature().getName();
System.out.println("this method "+methodName+" end with "+result);
} //4.异常通知:在目标方法出现异常时会执行代码
//可以访问异常对象,指定异常类型,当出现指定的异常时才会执行代码
//也就是Exception可以换成NullPoinException异常,当出现空指针异常的时候才会执行异常通知,其他异常不执行
@AfterThrowing(value="execution(public int com.yinfu.spring.aop.impl.ArithmeticCalculatorImpl.*(int, int))",throwing="ex")
public void afterThrowing(JoinPoint joinPoint ,Exception ex){
String methodName = joinPoint.getSignature().getName();
System.out.println("this method "+methodName+" throw with "+ex);
} //5.环绕通知
//环绕通知携带ProceedingJoinPoint类型的参数
//环绕通知类似于动态代理的全过程,ProceedingJoinPoint类型的参数可以决定是否执行目标方法
//环绕通知必须有返回值,返回值即为目标方法的返回值
@Around("execution(public int com.yinfu.spring.aop.impl.ArithmeticCalculatorImpl.*(int, int))")
public Object aroundMethod(ProceedingJoinPoint pjp){
Object result = null;
String methodName = pjp.getSignature().getName();
Object[] args = pjp.getArgs();
//执行目标方法
try {
//前置通知
System.out.println("this aroundMethod "+methodName+" begin with "+Arrays.asList(args));
result = pjp.proceed();
//返回通知
System.out.println("this aroundMethod "+methodName+" resutn with "+result);
} catch (Throwable e) {
//异常通知
System.out.println("this aroundMethod "+methodName+" throw with "+e);
}
//后置通知
System.out.println("this aroundMethod "+methodName+" end ");
return result;
} }

2.基于配置文件的日志通知和验证通知:

将类中的注解全部去掉,其他不变

此时的配置文件applicationContext.xml 这样写即可:

 <?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:aop="http://www.springframework.org/schema/aop"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-4.0.xsd
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.2.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.0.xsd"> <!-- 配置方法对象bean -->
<bean id="arithmeticCalculator" class="com.yinfu.spring.aop.impl.ArithmeticCalculatorImpl"></bean>
<!-- 配置切面bean -->
<bean id="loggingAspect" class="com.yinfu.spring.aop.impl.LoggingAspect"></bean>
<!-- 配置AOP切面 -->
<aop:config>
<!-- 配置切点表达式 -->
<aop:pointcut expression="execution(public int com.yinfu.spring.aop.impl.ArithmeticCalculatorImpl.*(int, int))" id="pointcut"/>
<!-- 配置切点及通知 -->
<aop:aspect ref="loggingAspect" order="1">
<aop:before method="beforeMethod" pointcut-ref="pointcut"/>
<aop:after method="afterMethod" pointcut-ref="pointcut"/>
<!-- 这里的returning值必须与切面类中定义的值是一样的 -->
<aop:after-returning method="afterReturning" pointcut-ref="pointcut" returning="result"/>
<!-- 这里的throwing值必须与切面类中定义的值是一样的 -->
<aop:after-throwing method="afterThrowing" pointcut-ref="pointcut" throwing="ex"/>
<aop:around method="aroundMethod" pointcut-ref="pointcut"/>
</aop:aspect>
</aop:config> </beans>

AOP切面通知的更多相关文章

  1. 【spring】aop切面通知,日志处理

    1.spring的切面编程 概念原理可以看这里:http://blog.csdn.net/moreevan/article/details/11977115 2.所需要的jar包 maven引入jar ...

  2. Spring AOP(通知、连接点、切点、切面)

    一.AOP术语 通知(Advice)  切面的工作被称为通知.通知定义了切面是什么以及何时使用.除了描述切面要完成的工作,通知还解决了何时执行这个工作的问题.5种通知类型: 前置通知(Before): ...

  3. spring aop环绕通知

    [Spring实战]—— 9 AOP环绕通知   假如有这么一个场景,需要统计某个方法执行的时间,如何做呢? 典型的会想到在方法执行前记录时间,方法执行后再次记录,得出运行的时间. 如果采用Sprin ...

  4. Spring切面通知执行的顺序(Advice Order)

    问题描述 如果在Spring的程序中同时定义了环绕通知(Around)和前置通知(Before)..那么,有以下问题: 1.怎么让两个切面通知都起作用 2.或者让两者切面按自己指定的顺序进行执行? 3 ...

  5. Spring MVC通过AOP切面编程 来拦截controller 实现日志的写入

    首选需要参考的是:[参考]http://www.cnblogs.com/guokai870510826/p/5977948.html    http://www.cnblogs.com/guokai8 ...

  6. Spring基础篇——Spring的AOP切面编程

    一  基本理解 AOP,面向切面编程,作为Spring的核心思想之一,度娘上有太多的教程啊.解释啊,但博主还是要自己按照自己的思路和理解再来阐释一下.原因很简单,别人的思想终究是别人的,自己的理解才是 ...

  7. Springboot项目使用aop切面保存详细日志到ELK日志平台

    上一篇讲过了将Springboot项目中logback日志插入到ELK日志平台,它只是个示例.这一篇来看一下实际使用中,我们应该怎样通过aop切面,拦截所有请求日志插入到ELK日志系统.同时,由于往往 ...

  8. Spring中AOP切面编程学习笔记

    注解方式实现aop我们主要分为如下几个步骤: 1.在切面类(为切点服务的类)前用@Aspect注释修饰,声明为一个切面类. 2.用@Pointcut注释声明一个切点,目的是为了告诉切面,谁是它的服务对 ...

  9. SpringBoot 通过自定义注解实现AOP切面编程实例

    一直心心念的想写一篇关于AOP切面实例的博文,拖更了许久之后,今天终于着手下笔将其完成. 基础概念 1.切面(Aspect) 首先要理解‘切’字,需要把对象想象成一个立方体,传统的面向对象变成思维,类 ...

随机推荐

  1. OO第三单元总结——JML

    目录 写在前面 JML理论基础 JML工具链 JMLUnitNG的使用 架构设计 Bug分析 心得体会 写在前面 OO的第三单元学习结束了,本单元我们学习了如何使用JML语言来对我们的程序进行规格化设 ...

  2. com.mysql.jdbc.exceptions.jdbc4.MySQLSyntaxErrorException: Unknown error 1054

    com.mysql.jdbc.exceptions.jdbc4.MySQLSyntaxErrorException: Unknown error 1054 这个错误困扰了我一个下午  插入数据总是错误 ...

  3. Java日志框架-Logback手册中文版以及官方配置文档教程

    Logback手册中文版:(链接: https://pan.baidu.com/s/1bpMyasR 密码: 6u5c),虽然版本有点旧,但是大体意思差不多,先用中文版了解个大概,然后一切最新的配置以 ...

  4. Spring Boot中验证码实现kaptcha

    要生成验证码网上的方案比较多,基本是基于两大类:1为自定义生成,操作用Image类,2为kaptcha生成,有模糊算法. 当然也可以直接交由前端进行处理 1.基于kaptcha 首先不要怀疑的是报名是 ...

  5. oracle字段的所有类型

    字段类型    中文说明    限制条件    其它说明 CHAR    固定长度字符串    最大长度2000    bytes VARCHAR2    可变长度的字符串    最大长度4000   ...

  6. TDBXJSONStream(BERLIN新增)的使用

    DELPHI 10.1 BERLIN新增TDBXJSONStream类,用于方便地将数据序列为JSON,和将JSON还原出来数据. DATASNAP远程方法也相应地增加了支持返回TDBXJSONStr ...

  7. Apache 处理svg工具包Apache(tm) Batik SVG Toolkit

    Apache™ Batik SVG Toolkit¶ Overview¶ Batik is a Java-based toolkit for applications or applets that ...

  8. Meteor第一个应用程序

    这一个小教程将教你如何建立你的第一个 Meteor 应用程序. 步骤 1 - 创建App 要创建应用程序,我们将从命令提示符窗口运行 meteor create 命令.该应用程序的名称是 meteor ...

  9. A Single Channel with Multiple Consumers RabbitMQ

    http://stackoverflow.com/questions/30696351/a-single-channel-with-multiple-consumers-rabbitmq up vot ...

  10. 最齐全的站点元数据meta标签的含义和使用方法

    最齐全的站点元数据meta标签的含义和使用方法 随着HTML5的流行和Web技术的不断演变,Meta标签队伍也越来越壮大,从Windows XP的IE6到现在Windows 7.Windows 8的I ...