1. 程式人生 > >(二)Spring AOP原始碼-1.概述與設計原理-02設計原理

(二)Spring AOP原始碼-1.概述與設計原理-02設計原理

AOP實現的關鍵在於自動建立AOP代理,AOP代理可分為靜態代理和動態代理。

靜態代理與動態代理

靜態代理主要在虛擬機器啟動時通過改變目標物件位元組碼的方式完成對目標物件的增強。以靜態代理為基礎實現的AOP技術的代表為AspectJ。AspectJ在編譯期間生成代理物件,因此也稱為編譯時增強。

動態代理不會去修改位元組碼,而是在執行時在記憶體中臨時生成AOP物件。這個AOP物件包含了目標物件的全部方法,並且在特定的切點做了增強處理,並回調原物件的方法。以動態代理為基礎實現的AOP技術則以Spring AOP為代表。Spring AOP的原始碼中用到了兩種動態代理:JDK動態代理和CGLIB動態代理。

AspectJ

AspectJ 是一個基於Java語言的AOP框架,提供了強大的AOP功能,其他很多AOP框架都借鑑或採納其中的一些思想。

JDK動態代理和CGLIB動態代理

JDK動態代理通過反射來接收被代理的類,並且要求被代理的類必須實現一個介面。JDK動態代理的核心是InvocationHandler介面和Proxy類。如果被代理的類沒有實現介面,那麼Spring AOP會選擇使用CGLIB來。

CGLIB(Code Generation Library),是一個程式碼生成的類庫,可以在執行時動態的生成某個類的子類。CGLIB動態代理底層則是藉助ASM(Java位元組碼生成框架)來實現的。CGLIB實現的基礎是繼承,因此如果某個類被標記為final,那麼它是無法使用CGLIB做動態代理的。

AOP預設使用哪種動態代理方式

預設使用JDK動態代理來建立AOP代理。當需要代理的類沒有實現介面的時候,Spring會使用CGLIB。當然,也可強制使用CGLIB。

如何強制使用CGLIB

<aop:config>裡面有一個”proxy-target-class”屬性,這個屬性值如果被設定為true,那麼基於CGLIB動態代理將起作用。這個屬性值預設為false。

Spring AOP設計原理

在前面的內容中,提到的最多的一個詞就是“代理”。事實上,JDK動態代理就實現了設計模式中的代理模式。關於代理模式可以參考我之前寫的一篇文章設計模式(12)-代理模式
MarkdownPhotos/master/CSDNBlogs/DesignPatterns/proxy.png
圖中的RealSubject就是被代理的類,Proxy是生成的代理類。Proxy對RealSubject的request方法進行了增強處理,即preRequest方法和afterRequest方法。