责任链模式解析FilterChain

分析:

过滤器链的调用过程

A过滤器调用chain.doFilter此时会进入到下一个过滤器

B过滤器继续调用chain.doFilter会继续进入下一个过滤器

当所有过滤器都执行完成后,会进入目标方法。

既然chain.doFilter能进入下一个过滤器,那本质上就是方法的调用压栈和弹栈,一个方法的调用入口会执行完成所有的方法栈后才完成。

所以chain内肯定知道下一个filter是哪个,同时chain肯定保存了最终的目标执行对象。

基于以上分析,chain内部维护了一个过滤器集合,并知道下一个过滤器是哪个。

复制代码
运行结果:
    首先,任何编程语言在调用一个方法,都会层层调用多层方法栈。
     A
        B
            C
                D
                    E....
   其实,责任链设计模式无非就是通过代码解耦,将复杂的逻辑线性化。将一个一个的调用串行化。
   FilterChain将责任链的执行权交给每个过滤器,由过滤器决定是否执行下一个过滤器。
java 复制代码
@Data
@Builder
public class HttpServletRequest {

    private String method;
    private String uri;

}
java 复制代码
public class TargetController {

    public void target() {
        System.out.println("执行了最终的目标方法");
    }

}
java 复制代码
public interface Filter {

    void doFilter(FilterChain filterChain, HttpServletRequest request) throws Exception;

}
java 复制代码
public class AuthFilter implements Filter {

    @Override
    public void doFilter(FilterChain filterChain, HttpServletRequest request) throws Exception {
        System.out.println("auth filter before");
        filterChain.doFilter(request);
        System.out.println("auth filter after");
    }

}
java 复制代码
public class LogFilter  implements Filter{
    @Override
    public void doFilter(FilterChain filterChain, HttpServletRequest request) throws Exception {
        System.out.println("log filter before ");
        filterChain.doFilter(request);
        System.out.println("log filter after ");
    }
}
java 复制代码
@Data
@Builder
public class FilterChain {

    private Integer index;

    private List<Filter> filters;

    //执行最终目标方法的对象
    private Object target;

    //执行最终的目标方法
    private Method method;

    //执行最终目标方法的
    private Object[] args;


    public void doFilter(HttpServletRequest request) throws Exception {
        //获取当前要执行的过滤器
        if (index == null){
            index = 0;
        }
        if (filters == null || filters.size() <= 0){
            return;
        }
        if (index >= filters.size()){
            //执行最终的目标方法
            method.invoke(target,args);
            return;
        }
        //获取过滤器
        Filter filter = filters.get(index++);
        filter.doFilter(this,request);
    }

}
java 复制代码
public class Test {

    public static void main(String[] args) throws Exception {

        FilterChain filterChain = FilterChain.builder()
                .filters(
                        Arrays.asList(new AuthFilter(), new LogFilter())
                )
                .index(0)
                .target(new TargetController())
                .method(TargetController.class.getMethod("target"))
                .args(null)
                .build();

        filterChain.doFilter(new HttpServletRequest("GET","/test"));

    }

}
相关推荐
逆境不可逃8 天前
【从零入门23种设计模式13】行为型之责任链模式
算法·leetcode·游戏·设计模式·责任链模式
what丶k9 天前
深入浅出责任链模式:解耦流程的优雅设计之道
java·责任链模式
sanshizhang9 天前
设计模式-责任链模式
java·设计模式·责任链模式
JTCC9 天前
Java 设计模式西游篇 - 第七回:责任链模式过难关 通关文牒层层批
java·设计模式·责任链模式
fdc20171 个月前
解耦的艺术:用责任链模式构建可插拔的文件处理流水线
c#·.net·责任链模式
YigAin1 个月前
Unity23种设计模式之 责任链模式
设计模式·责任链模式
柏木乃一1 个月前
进程间通信IPC(3)system V标准下基于责任链模式的消息队列,基于建造者模式的信号量
linux·c++·消息队列·建造者模式·责任链模式·信号量·进程间通信ipc
书院门前细致的苹果1 个月前
设计模式大全:单例、工厂模式、策略模式、责任链模式
设计模式·责任链模式·策略模式
苏渡苇1 个月前
优雅应对异常,从“try-catch堆砌”到“设计驱动”
java·后端·设计模式·学习方法·责任链模式
短剑重铸之日1 个月前
《设计模式》第十篇:三大类型之行为型模式
java·后端·设计模式·责任链模式·访问者模式·行为型模式