小蚂蚁 发表于 2021-9-18 17:48:48

spring aop之链式调用的实现

这篇文章主要介绍了spring aop之链式调用的实现,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
概述
aop(aspect orient programming),我们一般称为面向方面(切面)编程,作为面向对象的一种补充,用于处理系统中分布于各个模块的横切关注点,比如事务管理、日志、缓存等等。 spring aop采用的是动态代理,在运行期间对业务方法进行增强,所以不会生成新类,spring aop提供了对jdk动态代理的支持以及cglib的支持。本章我们不关注aop代理类的实现,我简单实现一个指定次序的链式调用。
实现链式调用的
methodinterceptor定义拦截器链,methodinvocation 递归进入下一个拦截器链中。类图如下:

methodinterceptor


public interface methodinterceptor {

object invoke(methodinvocation invocation) throws throwable;
}
methodinvocation


public interface methodinvocation {

object proceed() throws throwable;
}
abstractaspectjadvice
抽象类,实现methodinterceptor


public abstract class abstractaspectjadvice implements methodinterceptor{

private method advicemethod;

private object adviceobject;

public abstractaspectjadvice(method advicemethod, object adviceobject) {
    this.advicemethod = advicemethod;
    this.adviceobject = adviceobject;
}

public method getadvicemethod() {
    return this.advicemethod;
}

public void invokeadvicemethod() throws throwable {
    advicemethod.invoke(adviceobject);
}
}
aspectjbeforeadvice
前置通知


public class aspectjbeforeadvice extends abstractaspectjadvice {

public aspectjbeforeadvice(method method, object adviceobject) {
    super(method, adviceobject);
}

@override
public object invoke(methodinvocation invocation) throws throwable{
    this.invokeadvicemethod();
    object o = invocation.proceed();
    return o;
}
}
aspectjafterreturningadvice
后置通知


public class aspectjafterreturningadvice extends abstractaspectjadvice {

public aspectjafterreturningadvice(method method, object adviceobject) {
    super(method, adviceobject);
}

@override
public object invoke(methodinvocation invocation) throws throwable{
    object o = invocation.proceed();
    this.invokeadvicemethod();
    return o;
}
}
reflectivemethodinvocation
实现methodinvocation,proceed()方法递归实现链式调用。


public class reflectivemethodinvocation implements methodinvocation {

private final object targetobject;

private final method targetmethod;

private final list<methodinterceptor> interceptorlist;

private int currentinterceptorindex = -1;

public reflectivemethodinvocation(object targetobject, method targetmethod, list<methodinterceptor> interceptorlist) {
    this.targetobject = targetobject;
    this.targetmethod = targetmethod;
    this.interceptorlist = interceptorlist;
}

@override
public object proceed() throws throwable {

    if (this.currentinterceptorindex == this.interceptorlist.size() - 1) {
      return invokejoinpoint();
    }

    this.currentinterceptorindex++;

    methodinterceptor interceptor =
      this.interceptorlist.get(this.currentinterceptorindex);
    return interceptor.invoke(this);
}

private object invokejoinpoint() throws throwable {

    return this.targetmethod.invoke(this.targetobject);
}
}
niocoderservice
模拟service类


public class niocoderservice {

public void testaop() {
    system.out.println("http://niocoder.com/");
}
}
transactionmanager
模拟通知类


public class transactionmanager {
public void start() {
    system.out.println("start tx");
}

public void commit() {
    system.out.println("commit tx");
}

public void rollback() {
    system.out.println("rollback tx");
}

}
reflectivemethodinvocationtest
beforeadvice->afterreturningadvice
测试类,测试通知


public class reflectivemethodinvocationtest {

private aspectjbeforeadvice beforeadvice = null;

private aspectjafterreturningadvice afterreturningadvice = null;

private niocoderservice niocoderservice;

private transactionmanager tx;

public void setup() throws exception {
    niocoderservice = new niocoderservice();
    tx = new transactionmanager();
    beforeadvice = new aspectjbeforeadvice(transactionmanager.class.getmethod("start"), tx);
    afterreturningadvice = new aspectjafterreturningadvice(transactionmanager.class.getmethod("commit"), tx);
}

public void testmethodinvocation() throws throwable {
    method method = niocoderservice.class.getmethod("testaop");
    list<methodinterceptor> interceptorlist = new arraylist<>();
    interceptorlist.add(beforeadvice);
    interceptorlist.add(afterreturningadvice);   

    reflectivemethodinvocation mi = new reflectivemethodinvocation(niocoderservice, method, interceptorlist);

    mi.proceed();
}


public static void main(string[] args) throws throwable {
    reflectivemethodinvocationtest reflectivemethodinvocationtest = new reflectivemethodinvocationtest();
    reflectivemethodinvocationtest.setup();
    reflectivemethodinvocationtest.testmethodinvocation();
}
}
输出:

start tx
http://niocoder.com/
commit tx
时序图 beforeadvice->afterreturningadvice


afterreturningadvice->beforeadvice
修改interceptorlist的顺序


public void testmethodinvocation() throws throwable {
    method method = niocoderservice.class.getmethod("testaop");
    list<methodinterceptor> interceptorlist = new arraylist<>();
    interceptorlist.add(afterreturningadvice);
   interceptorlist.add(beforeadvice);

    reflectivemethodinvocation mi = new reflectivemethodinvocation(niocoderservice, method, interceptorlist);

    mi.proceed();
}
输出:

start tx
http://niocoder.com/
commit tx
时序图 afterreturningadvice->beforeadvice


代码下载
github:https://github.com/longfeizheng/data-structure-java/blob/master/src/main/java/cn/merryyou/aop
代码下载
github:https://github.com/longfeizheng/data-structure-java
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持CodeAE代码之家。
原文链接:https://segmentfault.com/a/1190000018206756

http://www.zzvips.com/article/176838.html
页: [1]
查看完整版本: spring aop之链式调用的实现