springboot springAOP 理解切面編程

一.什麼是切面編程

切面編程(Aspect Oriented Programming,AOP)

如圖,這個驗證用戶這個子流程就成了一個條線,也可以理解成一個切面,aspect的意思就是方面.實現方式有cglib的動態代理,和jdk靜態代理.

 

更多理解:https://www.cnblogs.com/Wolfmanlq/p/6036019.html

二.一個切面類的demo

package springbootDemo.aop;

import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.springframework.stereotype.Component;

/**
 * @author jiangfeng 2018/7/17 14:57
 * 切面類的demo 參考:https://www.cnblogs.com/liuruowang/p/5711563.html
 *
 * Spring中的AOP代理還是離不開Spring的IOC容器,代理的生成,管理及其依賴關係都是由IOC容器負責,Spring默認使用JDK動態代理,在需要代理類而不是代理接口的時候,
 * Spring會自動切換爲使用CGLIB代理,不過現在的項目都是面向接口編程,所以JDK動態代理相對來說用的還是多一些。
 */
@Component
@Aspect
public class SpringOperator {

	// 切面公式: 表示server包下所有類所有方法都加
	@Pointcut("execution(* springbootDemo.service..*.*(..))")
	public void pointCut(){}

	// joinPoint (連接點):程序執行過程中明確的點,一般是方法的調用. 獲取執行的環境
	@Before("pointCut()")
	public void doBefore(JoinPoint joinPoint){
		System.out.println("AOP Before ..."+joinPoint.toString());
	}

	@After("pointCut()")
	public void doAfter(JoinPoint joinPoint){
		System.out.println("AOP After ..."+joinPoint.toString());
	}

	@AfterReturning(pointcut="pointCut()",returning="returnVal")
	public void afterReturn(JoinPoint joinPoint,Object returnVal){
		System.out.println("AOP AfterReturning Advice:"+joinPoint.toString()+"returnval" + returnVal);
	}


	@AfterThrowing(pointcut="pointCut()",throwing="error")
	public void afterThrowing(JoinPoint joinPoint,Throwable error){
		System.out.println("AOP AfterThrowing ..." +joinPoint.toString()+"error: "+ error);
	}

	@Around("pointCut()")
	public Object  around(ProceedingJoinPoint pjp){
		System.out.println("AOP Aronud before...");
		try {
			Object returnval = pjp.proceed();
			System.out.println("AOP Aronud After...");
			return returnval;
		} catch (Throwable e) {
			e.printStackTrace();
			return null;
		}
	}

}

三. 開發步驟:
   1.新增一個切面類
      springbootDemo.aop.SpringOperator,
      並在類上加上註解:
   @Component // 標識spring組件
   @Aspect   //標識切面類

   2.在類里加入切面公式:
    // 切面公式: 表示server包下所有類所有方法都加
    @Pointcut("execution(* springbootDemo.service..*.*(..))")
    public void pointCut(){}

   3.各種切面方法,加註解:before,after,afterReturning,afterThrowing,around

四.相關知識點:
   (1)Aspect(切面):通常是一個類,裏面可以定義切入點和通知
   (2)JointPoint(連接點):程序執行過程中明確的點,一般是方法的調用
   (3)Advice(通知):AOP在特定的切入點上執行的增強處理,有before,after,afterReturning,afterThrowing,around
   (4)Pointcut(切入點):就是帶有通知的連接點,在程序中主要體現爲書寫切入點表達式
   (5)AOP代理:AOP框架創建的對象,代理就是目標對象的加強。Spring中的AOP代理可以使JDK動態代理,也可以是CGLIB代理,前者基於接口,後者基於子類
   (6) execution 切面公式
    '*'  匹配任意字符,但只能匹配一個元素
    '..' 匹配任意字符,可以匹配任意多個元素,表示類時,必須和*聯合使用
    '+'  必須跟在類名後面,如Horseman+,表示類本身和繼承或擴展指定類的所有類

   Spring中的AOP代理還是離不開Spring的IOC容器,代理的生成,管理及其依賴關係都是由IOC容器負責,Spring默認使用JDK動態代理,在需要代理類而不是代理接口的時候,
   Spring會自動切換爲使用CGLIB代理,不過現在的項目都是面向接口編程,所以JDK動態代理相對來說用的還是多一些。
   (7) 執行順序:
   AOP Aronud before...
   AOP Before ...execution(Tag springbootDemo.service.TagService.getTagById(Long))
   2018-07-17 16:16:10.411  INFO 15180 --- [nio-8088-exec-4] springbootDemo.service.TagService
   AOP Aronud After...
   AOP After ...execution(Tag springbootDemo.service.TagService.getTagById(Long))
   AOP AfterReturning

注意:
around 時,如果原方法有返回值時,必須返回.否則原方法返回值將被吞

參考:https://www.cnblogs.com/liuruowang/p/5711563.html

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章