Spring深入探索AOP切面編程
AOP概念的引入
傳統(tǒng)的登錄原理:
如上圖所示這是一個基本的登錄原理圖,但是如果我們想要在這個登錄之上添加一些新的功能,比如權限校驗
那么我們能想到的就有兩種方法:
①:通過對源代碼的修改實現(xiàn)
②:不通過修改源代碼方式添加新的功能 (AOP)
AOP相關的概念
1、AOP的概述
什么是AOP的技術?
在軟件業(yè),AOP為Aspect Oriented Programming的縮寫,意為:面向切面編程
AOP是一種編程范式,隸屬于軟工范疇,指導開發(fā)者如何組織程序結構
AOP最早由AOP聯(lián)盟的組織提出的,制定了一套規(guī)范.Spring將AOP思想引入到框架中,必須遵守AOP聯(lián)盟的規(guī)范
通過預編譯方式或者運行期動態(tài)代理實現(xiàn)程序功能的統(tǒng)一維護的一種技術
AOP是OOP的延續(xù),是軟件開發(fā)中的一個熱點,也是Spring框架中的一個重要內(nèi)容,是函數(shù)式編程的一種衍
生范型
利用AOP可以對業(yè)務邏輯的各個部分進行隔離,從而使得業(yè)務邏輯各部分之間的耦合度降低,提高程序的可
重用性,同時提高了開發(fā)的效率
AOP采取橫向抽取機制,取代了傳統(tǒng)縱向繼承體系重復性代碼(事務管理、安全檢查、緩存)
為什么要學習AOP,可以在不修改源代碼的前提下,對程序進行增強!!
2、AOP的優(yōu)勢
運行期間,不修改源代碼的情況下對已有的方法進行增強
優(yōu)勢:
- 減少重復的代碼
- 提供開發(fā)的效率
- 維護方便
3、AOP的底層原理
JDK的動態(tài)代理技術
1、為接口創(chuàng)建代理類的字節(jié)碼文件
2、使用ClassLoader將字節(jié)碼文件加載到JVM
3、創(chuàng)建代理類實例對象,執(zhí)行對象的目標方法
cglib代理技術
為類生成代理對象,被代理類有沒
Spring的AOP技術-配置文件方式
1、AOP相關的術語
Joinpoint(連接點) 類里面有哪些方法可以增強這些方法稱為連接點
Pointcut(切入點) – 所謂切入點是指我們要對哪些Joinpoint進行攔截的定義
Advice(通知/增強)-- 所謂通知是指攔截到Joinpoint之后所要做的事情就是通知.通知分為前置通知,后置通知,異常通知,最終通知,環(huán)繞通知(切面要完成的功能)
Aspect(切面)-- 是 切入點+通知 的結合,以后咱們自己來編寫和配置的
增強:是對業(yè)務功能的擴充
2、基本準備工作
AspectJ是一個面向切面的框架,它擴展了Java語言。AspectJ定義了AOP語法,AspectJ實際上是對AOP編程思想的一個實踐.
2.1、aop的使用
創(chuàng)建被增強的類:
public class Demo { //要增強,成為---->連接點---->切入點 public void login(){ //int a=10/0; System.out.println("登錄。。。"); } }
將目標類配置到Spring中:
<bean id="demo" class="com.qcby.Demo"/>
定義切面類
package com.notice; import org.aspectj.lang.ProceedingJoinPoint; import org.aspectj.lang.annotation.*; import org.springframework.stereotype.Component; @Component @Aspect //表明我們是通知 public class Power { //前置通知的方法 public void authentication(){ System.out.println("登錄前---權限驗證。。。"); } }
在spring.xml中配置文件中定義切面類:
<bean id="power" class="com.notice.Power"/>
在spring.xml中配置切面:
<aop:config> <!--aspect:前置通知,在登錄前執(zhí)行--> <aop:aspect ref="power"> <!--前置通知:--> <!--method:登錄前執(zhí)行的方法,權限驗證的方法--> <!--pointcut:切入點,之后最終要執(zhí)行的方法--> <!--前置通知:--> <aop:before method="authentication" pointcut="execution(public void com.qcby.Demo.login())"/> </aop:aspect> </aop:config>
測試:
public class DemoTest { @Test public void demo1(){ ApplicationContext ac = new ClassPathXmlApplicationContext("Spring.xml"); Demo demo = (Demo) ac.getBean("demo"); demo.login(); } }
2.2、配置文件的方式的aop5種通知方式
也可以在spring.xml中加入其他通知方式:
<aop:config> <!--aspect:前置通知,在登錄前執(zhí)行--> <aop:aspect ref="power"> <!--前置通知:--> <!--method:登錄前執(zhí)行的方法,權限驗證的方法--> <!--pointcut:切入點,之后最終要執(zhí)行的方法--> <!--前置通知:--> <aop:before method="authentication" pointcut="execution(public void com.qcby.Demo.login())"/> <!--后置通知:當方法執(zhí)行不成功的時候方法不執(zhí)行--> <aop:after-returning method="authenticationEnd" pointcut="execution(public void com.qcby.Demo.login())"/> <!--當切入點(登錄方法)發(fā)生異常的時候執(zhí)行,沒有異常則不執(zhí)行:--> <aop:after-throwing method="findThrowError" pointcut="execution(public void com.qcby.Demo.login())"/> <!--最終通知:無論切入點的方法執(zhí)行成功與否,最終都執(zhí)行的通知(增強)--> <aop:after method="finallyMethod" pointcut="execution(public void com.qcby.Demo.login())"/> <!--環(huán)繞通知:在切面前后執(zhí)行方法--> <aop:around method="round" pointcut="execution(public void com.qcby.Demo.login())"/> </aop:aspect> </aop:config>
3、通知類型注解:用注解的方式加入通知
@Before – 前置通知
@AfterReturing – 后置通知
@Around – 環(huán)繞通知(目標對象方法默認不執(zhí)行的,需要手動執(zhí)行)
@After – 最終通知
@AfterThrowing – 異常拋出通知
package com.notice; import org.aspectj.lang.ProceedingJoinPoint; import org.aspectj.lang.annotation.*; import org.springframework.stereotype.Component; @Component @Aspect //表明我們是通知 public class Power { //增強的方法:權限驗證 //@Before(value="execution(public void com.qcby.Demo.login())") //@AfterReturning(value="execution(public void com.qcby.Demo.login())") //前置通知 @Before(value="execution(public void com.qcby.Demo.login())") public void authentication(){ System.out.println("登錄前---權限驗證。。。"); } //后置通知 @AfterReturning(value="execution(public void com.qcby.Demo.login())") public void authenticationEnd(){ System.out.println("登錄后---權限驗證。。。"); } //發(fā)生異常時通知 @AfterThrowing(value="execution(public void com.qcby.Demo.login())") public void findThrowError(){ System.out.println("登錄發(fā)現(xiàn)異常了"); } //最終通知 @After(value="execution(public void com.qcby.Demo.login())") public void finallyMethod(){ System.out.println("最終都執(zhí)行的通知"); } //環(huán)繞通知 @Around(value="execution(public void com.qcby.Demo.login())") public void round(ProceedingJoinPoint proceedingJoinPoint) throws Throwable { System.out.println("在登錄之前進行了權限驗證"); //之間執(zhí)行登錄的方法 proceedingJoinPoint.proceed(); System.out.println("在登錄之后進行了權限驗證"); } }
到此這篇關于Spring深入探索AOP切面編程的文章就介紹到這了,更多相關Spring AOP內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關文章希望大家以后多多支持腳本之家!
相關文章
JAVA如何把數(shù)據(jù)庫的數(shù)據(jù)處理成樹形結構
本文介紹了JAVA如何把數(shù)據(jù)庫的數(shù)據(jù)處理成樹形結構,文中通過示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下2021-09-09