1. 程式人生 > >Spring AOP demo 和獲取被CGLIB代理的物件

Spring AOP demo 和獲取被CGLIB代理的物件

本文分為兩部分:1)給出Spring AOP的一個例子(會使用CGLIB代理);2)給出獲取被CGLIB代理的原始物件。

1、Spring AOP Demo

1.1新增maven依賴

<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-core</artifactId>
    <version>4.0.5.RELEASE</version>
</dependency>
<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-beans</artifactId>
    <version>4.0.5.RELEASE</version>
</dependency>
<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-context</artifactId>
    <version>4.0.5.RELEASE</version>
</dependency>
<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-aop</artifactId>
    <version>4.0.5.RELEASE</version>
</dependency>
<dependency>
    <groupId>org.aspectj</groupId>
    <artifactId>aspectjweaver</artifactId>
    <version>1.8.1</version>
</dependency>

1.2新增測試類

public class SpringAopTest {

    public static class Car {
        public void go() {
            System.out.println("go go go!");
        }
    }

    public static class CarLogger {

        public void beforeRun() {
            System.out.println("car is going to run");
        }

        public void afterRun() {
            System.out.println("car is running");
        }
    }

    public static void main(String[] args) {
        ApplicationContext context = new ClassPathXmlApplicationContext("spring-aop-test.xml");
        Car car = (Car) context.getBean("car");
        System.out.println(car.getClass());
        car.go();
    }
}
1.3新增spring配置檔案

放置在classpath的根目錄下,額,放在resources目錄下也就行了。

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.0.xsd">

    <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:p="http://www.springframework.org/schema/p" xmlns:context="http://www.springframework.org/schema/context" xmlns:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-2.5.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd" >
        <bean id="car" class="com.SpringAopTest.Car"/>
        <bean id="logger" class="com.SpringAopTest.CarLogger" />
        <aop:config>
            <aop:aspect ref="logger">
                <aop:pointcut expression="execution(* com.SpringAopTest.Car.go(..))" id="go"/>

                <aop:before pointcut-ref="go" method="beforeRun" />
                <aop:after pointcut-ref="go" method="afterRun" />
            </aop:aspect>
        </aop:config>
    </beans>

</beans>

1.4執行main函式

得到如下結果:

car is going to run
go go go!
car is running
吶,你看go go go!前後都有後新增的動作吧。

2、獲取被CGLIB代理的物件

我們先通過debug看一下被代理物件被藏在哪裡了抓狂


好,看完了,我們來寫一下程式碼,如下:

import java.lang.reflect.Field;

import org.springframework.aop.framework.AdvisedSupport;
import org.springframework.aop.support.AopUtils;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

/**
 * Created by qm on 17/2/15.
 */
public class SpringAopTest {

    public static class Car {
        public void go() {
            System.out.println("go go go!");
        }
    }

    public static class CarLogger {

        public void beforeRun() {
            System.out.println("car is going to run");
        }

        public void afterRun() {
            System.out.println("car is running");
        }
    }

    public static Object getTarget(Object beanInstance) {
        if (!AopUtils.isAopProxy(beanInstance)) {
            return beanInstance;
        } else if (AopUtils.isCglibProxy(beanInstance)) {
            try {
                Field h = beanInstance.getClass().getDeclaredField("CGLIB$CALLBACK_0");
                h.setAccessible(true);
                Object dynamicAdvisedInterceptor = h.get(beanInstance);

                Field advised = dynamicAdvisedInterceptor.getClass().getDeclaredField("advised");
                advised.setAccessible(true);

                Object target = ((AdvisedSupport) advised.get(dynamicAdvisedInterceptor)).getTargetSource().getTarget();
                return target;
            } catch (NoSuchFieldException e) {
                e.printStackTrace();
            } catch (IllegalAccessException e) {
                e.printStackTrace();
            } catch (Exception e) {
                e.printStackTrace();
            }

        }
        return null;

    }

    public static void main(String[] args) {
        ApplicationContext context = new ClassPathXmlApplicationContext("spring-aop-test.xml");
        Car car = (Car) context.getBean("car");
        Object target = getTarget(car);
        System.out.println(target == car);
        System.out.println(car.getClass());
        System.out.println(target.getClass());
        car.go();
    }
}





相關推薦

Spring AOP demo 獲取CGLIB代理物件

本文分為兩部分:1)給出Spring AOP的一個例子(會使用CGLIB代理);2)給出獲取被CGLIB代理的原始物件。 1、Spring AOP Demo 1.1新增maven依賴 <dependency> <groupId>org.sp

【轉載】Spring AOP詳解 、 JDK動態代理CGLib動態代理

rto 工廠 第一個 lec 僅支持 sel clas sleep gpo 原文地址:https://www.cnblogs.com/kukudelaomao/p/5897893.html AOP是Aspect Oriented Programing的簡稱,面向切面

設計模式:代理模式是什麼,Spring AOP它有關係?

接著學習設計模式系列,今天講解的是代理模式。 定義 什麼是代理模式? 代理模式,也叫委託模式,其定義是給某一個物件提供一個代理物件,並由代理物件控制對原物件的引用。它包含了三個角色: Subject:抽象主題角色。可以是抽象類也可以是介面,是一個最普通的業務型別定義。 RealSubject:具體主題角色,也

spring aop概念以及jdk的動態代理

  AOP(Aspect-Oriented Programming),又稱為面向切面程式設計。作為一種程式設計思想,AOP是 OOP(Object-Oriented Programing面向物件程式設計)一種 補充和完善。   AOP相關的術語   1.0 關注點   關注點就是所關注的

spring aop原理實現

一、aop是什麼 1.AOP面向方面程式設計基於IoC,是對OOP的有益補充; 2.AOP利用一種稱為“橫切”的技術,剖解開封裝的物件內部,並將那些影響了 多個類的公共行為封裝到一個可重用模組,並將其名為“Aspect”,即方面。所謂“方面”,簡單地說,就是將那些與業務無關,卻為業務模組所共同呼叫的 邏輯

Spring AOP切點通知

前言 Spring切面由切點和通知組成。Spring AOP是基於代理的,包括JDK動態代理或者CGLIB動態代理,只支援方法級別的連線點,因此Spring AspectJ風格切點表示式僅僅是AspectJ的子集。表示式之間可以用&&、||、!表示與或非、如

Java AOP & Spring AOP 原理實現

1 定義介面,並建立介面實現類 public interface HelloWorld { void printHelloWorld(); void doPrint(); } public class HelloWorldImpl1 implements HelloWorld {

利用spring aop攔截並獲取@ResponseBody資料

攔截請求有很多種方法,最簡單的用攔截器,但是攔截器並不能獲取返回的資料(比如@ResponseBody),上網找了一段時間,可以利用spring的AOP特性攔截並獲取,還能修改返回的資料。 準備

Spring aop 配置註解及詳解

Spring aopaop:(Aspect Oriented Programming)面向切面程式設計,縱向重複,橫向抽取 代理: 生活中的例項:找明星拍戲,上綜藝。拍戲   直接找明星,說明明星太小。如果明星有點名氣,那就不能直接訪問了,必須先通過先訪問明星的經紀人,然後由

[spring][aop]@Pointcut@Value

https://blog.csdn.net/u013378306/article/details/86668304 各個符號,更詳細 定義在service包和所有子包裡的任意類的任意方法的執行:execution(* com.xyz.service...(..)) 第一個表示匹配任意的方法返回值, .

java中代理,靜態代理,動態代理以及spring aop代理方式,實現原理統一彙總 SpringAOP的兩種代理方式(Java動態代理CGLIB代理

若代理類在程式執行前就已經存在,那麼這種代理方式被成為 靜態代理 ,這種情況下的代理類通常都是我們在Java程式碼中定義的。 通常情況下, 靜態代理中的代理類和委託類會實現同一介面或是派生自相同的父類。 一、概述1. 什麼是代理我們大家都知道微商代理,簡單地說就是代替廠家賣商品,廠家“委託”代理為

Spring 學習筆記(六)AOP 之思想概念作用、JDK代理Cglib子類代理

概念 AOP為Aspect Oriented Programming的縮寫,意味:面向切面程式設計。 與IOC一樣,是一種思想。 作用 對業務邏輯進行分離,降低耦合度,提高程式的重用性,提高開發效率。 JDK動態代理(介面代理) 弱點:JDK動態代理

Spring AOP之---基於JDK動態代理CGLib動態代理AOP實現

AOP(面向切面程式設計)是OOP的有益補充,它只適合那些具有橫切邏輯的應用場合,如效能監測,訪問控制,事物管理,日誌記錄等。至於怎麼理解橫切邏輯,敲完例項程式碼也就明白了。 為什麼要使用AOP,舉個栗子:需要監測一些方法的執行所消耗的時間,在每個方法開始

Spring AOP 代理實現的兩種方式: JDK動態代理 Cglib框架動態代理

1.JDK動態代理 JDK API 內建 ---- 通過 Proxy類,為目標物件建立代理 (必須面向介面代理 ),此文中介面為UserDao,實現類為UserDaoImpl. public class UserDaoImpl implements UserDao {

Spring AOP中的JDKCGLib動態代理哪個效率更高?

一、背景 今天有小夥伴面試的時候被問到:Spring AOP中JDK 和 CGLib動態代理哪個效率更高? 二、基本概念 首先,我們知道Spring AOP的底層實現有兩種方式:一種是JDK動態代理,另一種是CGLib的方式。 自Java 1.3以後

Spring AOP底層實現- JDK動態代理CGLIB動態代理

Spring AOP是執行時織入的,那麼執行時織入到底是怎麼實現的呢?答案就是代理物件。 代理又可以分為靜態代理和動態代理。 靜態代理:由程式設計師建立或特定工具自動生成原始碼,再對其編譯。在程式執行前,代理類的.class檔案就已經存在了。

spring aop原理 JDK動態代理CGLIB動態代理

lan ble -- 自定義 and ets spec gen ase Spring的兩大特性是IOC和AOPIOC負責將對象動態的註入到容器,從而達到一種需要誰就註入誰,什麽時候需要就什麽時候註入的效果。理解spring的ioc也很重要。但是今天主要來和大家講講aop。A

spring AOP 動態代理 jkd動態代理cglib動態代理 hibernate使用cglib延遲載入

spring 的AOP 實現 可以使用jdk的動態代理,也可以使用cglib的動態代理 先說下兩者區別: 靜態代理:代理之前就已經知道了代理者和被代理者 動態代理:代理之前並不清楚,在執行時使用反射機制動態生成代理類的位元組碼 無需我們手動編寫它的原始碼

SpringAOP兩種代理機制對比(JDKCGLib動態代理

Sprign 動態代理機制 Spirng的AOP的動態代理實現機制有兩種,分別是: 1)JDK動態代理: 具體實現原理: 1、通過實現InvocationHandlet介面建立自己的呼叫處理器 2、

CgLib動態代理學習【Spring AOP基礎之一】

div 目前 .get 不知道 ctu get() 內容 想要 外部依賴   如果不了解JDK中proxy動態代理機制的可以先查看上篇文章的內容:Java動態代理學習【Spring AOP基礎之一】   由於Java動態代理Proxy.newProxyInstance()的