成人国产在线小视频_日韩寡妇人妻调教在线播放_色成人www永久在线观看_2018国产精品久久_亚洲欧美高清在线30p_亚洲少妇综合一区_黄色在线播放国产_亚洲另类技巧小说校园_国产主播xx日韩_a级毛片在线免费

資訊專欄INFORMATION COLUMN

SpringBoot基礎(chǔ)篇AOP之基本使用姿勢小結(jié)

timger / 3326人閱讀

摘要:通知和切點(diǎn)共同定義了關(guān)于切面的全部內(nèi)容,它是什么時(shí)候,在何時(shí)和何處完成功能引入允許我們向現(xiàn)有的類添加新的方法或者屬性組裝方面來創(chuàng)建一個(gè)被通知對象。這可以在編譯時(shí)完成例如使用編譯器,也可以在運(yùn)行時(shí)完成。和其他純框架一樣,在運(yùn)行時(shí)完成織入。

原文:190301-SpringBoot基礎(chǔ)篇AOP之基本使用姿勢小結(jié)

一般來講,談到Spring的特性,繞不過去的就是DI(依賴注入)和AOP(切面),在將bean的系列中,說了DI的多種使用姿勢;接下來看一下AOP的玩法

I. 背景知識(shí)

在實(shí)際使用之前有必要了解一下什么是AOP,以及AOP的幾個(gè)基本概念

1. advice

before: 在方法執(zhí)行之前被調(diào)用

after: 在方法執(zhí)行之后調(diào)用

after returning: 方法執(zhí)行成功之后

after throwing: 方法拋出異常之后

around: 環(huán)繞,自己在內(nèi)部決定方法的執(zhí)行時(shí)機(jī),因此可以在之前之后做一些業(yè)務(wù)邏輯

2. join point

連接點(diǎn),比如方法調(diào)用,方法執(zhí)行,字段設(shè)置/獲取、異常處理執(zhí)行、類初始化、甚至是 for 循環(huán)中的某個(gè)點(diǎn)

但 Spring AOP 目前僅支持方法執(zhí)行 (method execution)

簡單來說,Spring AOP中,PointCut就是那個(gè)被攔截的方法

3. pointcut

切點(diǎn),用來描述滿足什么規(guī)則的方法會(huì)被攔截

正則表達(dá)式 : @Before("execution(public * com.git.hui.demo.base.bean.*.*(..))")

注解攔截方式 :@Around("@annotation(parameterCheck)")

4. aspect

切面是切點(diǎn)和通知的結(jié)合。通知和切點(diǎn)共同定義了關(guān)于切面的全部內(nèi)容,它是什么時(shí)候,在何時(shí)和何處完成功能

5. introduction

引入允許我們向現(xiàn)有的類添加新的方法或者屬性

6. weaving

組裝方面來創(chuàng)建一個(gè)被通知對象。這可以在編譯時(shí)完成(例如使用AspectJ編譯器),也可以在運(yùn)行時(shí)完成。Spring和其他純Java AOP框架一樣,在運(yùn)行時(shí)完成織入。

簡單來講就是生成一個(gè)代理類,在調(diào)用被攔截的方法時(shí),實(shí)際上執(zhí)行的是代理類,這個(gè)代理類內(nèi)部執(zhí)行切面邏輯

II. 使用說明 1. 基本配置

首先是基本環(huán)境的搭建, 先貼上必要的xml配置, 使用aop需要引入包: spring-boot-starter-aop


    org.springframework.boot
    spring-boot-starter-parent
    2.0.4.RELEASE
     



    UTF-8
    UTF-8
    Finchley.RELEASE
    1.8




    
        org.springframework.boot
        spring-boot-starter-aop
    



    
        
            
                org.springframework.boot
                spring-boot-maven-plugin
            
        
    



    
        spring-milestones
        Spring Milestones
        https://repo.spring.io/milestone
        
            false
        
    
2. 代碼準(zhǔn)備

首先創(chuàng)建一個(gè)被攔截的bean: com.git.hui.boot.aop.demo.DemoBean,如下

@Component
public class DemoBean {

    /**
     * 返回隨機(jī)的字符串
     *
     * @param time
     * @return
     */
    public String randUUID(long time) {
        try {
            System.out.println("in randUUID before process!");
            return UUID.randomUUID() + "|" + time;
        } finally {
            System.out.println("in randUUID finally!");
        }
    }
}

接著在啟動(dòng)類中,執(zhí)行

@SpringBootApplication
public class Application {
    
    public Application(DemoBean demoBean) {
        String ans = demoBean.randUUID(System.currentTimeMillis());
        System.out.println("----- ans: " + ans + "---------");
    }

    public static void main(String[] args) {
        SpringApplication.run(Application.class);
    }
}
3. AOP使用

在實(shí)際使用之前,需要?jiǎng)?chuàng)建一個(gè)切面,用@Aspect聲明,其次切面也需要作為bean托付給Spring容器管理

@Aspect
@Component
public class AnoAspcet {
}
a. before

在方法調(diào)用之前,需要執(zhí)行一些操作,這個(gè)時(shí)候可以使用 @Before 注解來聲明before advice

一種可使用姿勢如下,我們的切點(diǎn)直接在注解中進(jìn)行定義,使用正則表達(dá)式的方式

@Before("execution(public * com.git.hui.boot.aop.demo.*.*(*))")
public void doBefore(JoinPoint joinPoint) {
    System.out.println("do in Aspect before method called! args: " + JSON.toJSONString(joinPoint.getArgs()));
}
b. after

在方法調(diào)用完畢之后,再執(zhí)行一些操作,這個(gè)時(shí)候after就可以派上用場,為了考慮切點(diǎn)的通用性,我們可以考慮聲明一個(gè)切點(diǎn),使用@Pointcut注解

@Pointcut("execution(public * com.git.hui.boot.aop.demo.*.*(*))")
public void point() {
}

使用pointcut的方式也比較簡單,如下

@After("point()")
public void doAfter(JoinPoint joinPoint) {
    System.out.println("do in Aspect after method called! args: " + JSON.toJSONString(joinPoint.getArgs()));
}
c. after returning

在正常返回結(jié)果之后,再次執(zhí)行,這個(gè)也挺有意思的,通常使用這個(gè)advice時(shí),一般希望獲取返回結(jié)果,那么應(yīng)該怎么處理呢?

org.aspectj.lang.annotation.AfterReturning#returning 指定返回結(jié)果對應(yīng)參數(shù)name

返回結(jié)果作為參數(shù)傳入,要求類型一致,否則不生效

/**
 * 執(zhí)行完畢之后,通過 args指定參數(shù);通過 returning 指定返回的結(jié)果,要求返回值類型匹配
 *
 * @param time
 * @param result
 */
@AfterReturning(value = "point() && args(time)", returning = "result")
public void doAfterReturning(long time, String result) {
    System.out.println("do in Aspect after method return! args: " + time + " ans: " + result);
}
d. around

這個(gè)也比較常見,在方法執(zhí)行前后干一些事情,比如常見的耗時(shí)統(tǒng)計(jì),日志打印,安全控制等,很多都是基于around advice實(shí)現(xiàn)的

使用這個(gè)advice需要注意的是傳入?yún)?shù)類型為 ProceedingJoinPoint,需要在方法內(nèi)部顯示執(zhí)行org.aspectj.lang.ProceedingJoinPoint#proceed()來表示調(diào)用方法

@Around("point()")
public Object doAround(ProceedingJoinPoint joinPoint) throws Throwable {
    System.out.println("do in Aspect around ------ before");
    Object ans = joinPoint.proceed();
    System.out.println("do in Aspect around ------- over! ans: " + ans);
    return ans;
}
e. 輸出

執(zhí)行之后輸出如下

do in Aspect around ------ before
do in Aspect before method called! args: [1551433188205]
in randUUID before process!
in randUUID finally!
do in Aspect around ------- over! ans: 6849544b-160e-464c-80bd-641f2651c6c1|1551433188205
do in Aspect after method called! args: [1551433188205]
do in Aspect after method return! args: 1551433188205 ans: 6849544b-160e-464c-80bd-641f2651c6c1|1551433188205
----- ans: 6849544b-160e-464c-80bd-641f2651c6c1|1551433188205---------

從輸出結(jié)果上,可以看到每個(gè)advice的使用范圍,當(dāng)然也帶來了一些疑問

可以存在多個(gè)同類型的advice,攔截同一個(gè)目標(biāo)嗎?(如兩個(gè)around都攔截methodA方法,那么methodA方法被調(diào)用時(shí),兩個(gè)around advice是否都會(huì)執(zhí)行)

多個(gè)advice之間的優(yōu)先級(jí)怎么定義?

aop攔截的目標(biāo)方法有沒有限制(對非public的方法可以攔截么?)

被攔截的方法中存在相互調(diào)用的時(shí)候,會(huì)怎樣?(如methodA,methodB都可以被攔截,且methodA中調(diào)用了methodB,那么在執(zhí)行methodA時(shí),methodB的各種advice是否會(huì)被觸發(fā)?)

基于注解的aop方式可以怎樣用

以上這些問題留在下一篇進(jìn)行介紹

III. 其他 0. 項(xiàng)目

工程:https://github.com/liuyueyi/spring-boot-demo

項(xiàng)目: https://github.com/liuyueyi/spring-boot-demo/tree/master/spring-boot/010-aop

1. 一灰灰Blog

一灰灰Blog個(gè)人博客 https://blog.hhui.top

一灰灰Blog-Spring專題博客 http://spring.hhui.top

一灰灰的個(gè)人博客,記錄所有學(xué)習(xí)和工作中的博文,歡迎大家前去逛逛

2. 聲明

盡信書則不如,以上內(nèi)容,純屬一家之言,因個(gè)人能力有限,難免有疏漏和錯(cuò)誤之處,如發(fā)現(xiàn)bug或者有更好的建議,歡迎批評指正,不吝感激

微博地址: 小灰灰Blog

QQ: 一灰灰/3302797840

3. 掃描關(guān)注

一灰灰blog

知識(shí)星球

文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請注明本文地址:http://systransis.cn/yun/19468.html

相關(guān)文章

  • 慕課網(wǎng)_《SpringBoot進(jìn)階Web進(jìn)階》學(xué)習(xí)總結(jié)

    摘要:時(shí)間年月日星期日說明本文部分內(nèi)容均來自慕課網(wǎng)。慕課網(wǎng)教學(xué)示例源碼個(gè)人學(xué)習(xí)源碼第一章課程介紹課程介紹本課程緊接著小時(shí)學(xué)會(huì)課程,請先看入門課。異常返回通知在連接點(diǎn)拋出異常后執(zhí)行。 時(shí)間:2017年3月19日星期日說明:本文部分內(nèi)容均來自慕課網(wǎng)。@慕課網(wǎng):http://www.imooc.com教學(xué)示例源碼:https://github.com/zccodere/s...個(gè)人學(xué)習(xí)源碼:htt...

    lifefriend_007 評論0 收藏0
  • SpringBoot高級(jí)MongoDB修改基本使用姿勢

    摘要:原文高級(jí)篇之修改基本使用姿勢本篇依然是中的一篇,主要介紹的更新,主要內(nèi)容如下常見類型成員的修改數(shù)組類型成員的增刪改類型成員的增刪改基本使用首先是準(zhǔn)備好基本環(huán)境,可以參考博文高級(jí)篇之基本環(huán)境搭建與使用高級(jí)篇之查詢基本使用姿勢在開 原文: 190218-SpringBoot高級(jí)篇MongoDB之修改基本使用姿勢 本篇依然是MongoDB curd中的一篇,主要介紹document的更新,...

    lauren_liuling 評論0 收藏0
  • 【好好面試】學(xué)完Aop,連動(dòng)態(tài)代理的原理都不懂?

    摘要:總結(jié)動(dòng)態(tài)代理的相關(guān)原理已經(jīng)講解完畢,接下來讓我們回答以下幾個(gè)思考題。 【干貨點(diǎn)】 此處是【好好面試】系列文的第12篇文章。文章目標(biāo)主要是通過原理剖析的方式解答Aop動(dòng)態(tài)代理的面試熱點(diǎn)問題,通過一步步提出問題和了解原理的方式,我們可以記得更深更牢,進(jìn)而解決被面試官卡住喉嚨的情況。問題如下 SpringBoot默認(rèn)代理類型是什么 為什么不用靜態(tài)代理 JDK動(dòng)態(tài)代理原理 CGLIB動(dòng)態(tài)代理...

    Keven 評論0 收藏0

發(fā)表評論

0條評論

最新活動(dòng)
閱讀需要支付1元查看
<