Bootstrap

Spring之异常抛出增强&&最终增强&&环绕增强&&注解

异常抛出增强

异常抛出增强(afterThrowing):在目标方法抛出异常时织入增强处理

//异常增强:afterThrowing
//运行时异常:RuntimeException
public void afterThrowing(JoinPoint jp, RuntimeException e) {
    log.error("异常抛出增强:" + jp.getSignature().getName() + "方法发生异常:" + e);
}

Application配置文件:

<!--aop:after-throwing:异常增强,在目标方法抛出异常时织入增强处理
       异常抛出增强   e代表收集异常信息的-->
<aop:after-throwing method="afterThrowing" pointcut-ref="pointcut" throwing="e"/>

最终增强

最终增强:无论方法是否抛出,都会在目标方法最后织入增强处理,即:该增强都会得到执行。
类似于异常处理机制中的finally块的作用,一般用于释放资源。

//最终增强
//无论方法是否抛出,都会在目标方法最后织入增强处理,即:该增强都会得到执行。
//类似于异常处理机制中的finally块的作用,一般用于释放资源。
public void afterLogger(JoinPoint jp) {
    log.info("最终增强:" + jp.getSignature().getName() + "方法结束执行。");
}

Application.xml配置文件:

<!--将afterLogger()方法定义为最终增强并引用到pointCut切入点-->
<aop:after method="afterLogger" pointcut-ref="pointcut"/>

环绕增强

环绕增强:目标方法前后都可织入增强处理,功能最强大的增强处理
可获取或修改目标方法的参数,返回值,可对他进行异常处理,甚至可以决定目标方法是否执行。

//环绕增强
//目标方法前后都可织入增强处理
//功能最强大的增强处理
//可获取或修改目标方法的参数,返回值,可对他进行异常处理,甚至可以决定目标方法是否执行。
public Object aroundLogger(ProceedingJoinPoint jp) throws Throwable {
    log.info("环绕增强:调用" + jp.getTarget() + "的" + jp.getSignature().getName()
            + "方法。方法入参:" + Arrays.toString(jp.getArgs()));
    try {
    	Object result = jp.proceed();
        log.info("环绕增强:调用" + jp.getTarget() + "的"
                + jp.getSignature().getName() + "方法。方法返回值:" + result);
        return result;
    } catch (Throwable e) {
        log.error("环绕增强:"+jp.getSignature().getName() + "方法发生异常:" + e);
        throw e;
    } finally {
        log.info("环绕增强:"+jp.getSignature().getName() + "方法结束执行。");
    }
}

Application.xml配制文件:

<!--将aroundLogger()方法定义为环绕增强并引用pointcut切入点-->
<aop:around method="aroundLogger" pointcut-ref="pointcut"/>

常用增强处理类型

增强处理类型 特点
Before 前置增强处理,在目标方法前织入增强处理
AfterReturning 后置增强处理,在目标方法正常执行(不出现异常)后织入增强处理
AfterThrowing 异常增强处理,在目标方法抛出异常后织入增强处理
After 最终增强处理,不论方法是否抛出异常,都会在目标方法最后织入增强处理
Around 环绕增强处理,在目标方法的前后都可以织入增强处理

编写AOP增强类的方法

public class UserServiceLogger {

    private static Logger log = Logger.getLogger(UserServiceLogger.class);
    //定义切入点
    @Pointcut("execution(* org.westos.demo.service.*.*(..))")
    public void pointcut(){}
    /**
     * 切入点 规则
     * public * addNewUser(entity.User): “*”表示匹配所有类型的返回值。
     * public void *(entity.User): “*”表示匹配所有方法名。
     * public void addNewUser(..): “..”表示匹配所有参数个数和类型。
     * * com.service.*.*(..):匹配com.service包下所有类的所有方法。
     * * com.service..*.*(..):匹配com.service包及其子包下所有类的所有方法
     */

    //前置增强
    //JoinPoint:目标方法的类名,方法名,参数列表
    @Before("pointcut()")
    public void before(JoinPoint jp) {
        log.info("前置增强:" + "调用 " + jp.getTarget() + " 的 " + jp.getSignature().
                getName() + " 方法。方法入参:" + Arrays.toString(jp.getArgs()));
    }

    //后置增强
    //JoinPoint:目标方法的类名,方法名 参数列表
    //result:获取目标,方法的返回值
    @AfterReturning(pointcut = "pointcut()",returning = "result")
    public void afterReturning(JoinPoint jp, Object result) {
        log.info("后置增强:" + "调用 " + jp.getTarget() + " 的 " + jp.getSignatu
;