责任链模式的 JS例子

1,575 阅读1分钟

责任链模式的 JS例子

日常中参数/业务逻辑/状态等等需要进行预检或中断执行,这种流式且可中断的代码比较适合责任链模式。这里通过设计一个链式结构处理该类问题。

设计结构

  • 目标任务

最终要执行的任务

  • 添加拦截器

流程中的其他处理任务,如预检等

  • 开始任务

从第一个拦截器开始执行

  • 继续 or 中断 任务

拦截器中进行判断是否继续下一步

JS代码实现

class TaskChain {
  //target:目标任务
  constructor(target) {
    this.target = target
    this.index = 0              //拦截器执行下标
    this.interceptorSize = 0    //拦截器个数
    this.interceptors = []      //拦截器集合
  }
  //添加拦截器
  //interceptor: function(TaskChain) {}
  //调用 TaskChain.process() 继续任务
  addInterceptor(interceptor) {
    this.interceptors.push(interceptor)
    this.interceptorSize++
    return this
  }
  //执行任务
  process() {
    //初始化下标
    this.index = 0
    this.next()
  }
  //继续执行
  next() {
    if (this.index < this.interceptorSize) {
      //获取当前下标的拦截器,之后下标递增,下次即可获取下一个拦截器
      this.interceptors[this.index++](this)
      return
    }
    if (this.target) {
      //执行目标任务
      this.target()
    }
  }
}

使用例子

随意模拟几个拦截任务,可随意增减中间过程,可添加异步中间过程,让代码更好维护,更好阅读

// 随意模拟几个拦截任务
function signin() {
  let name = "xiaobai"
  let password = "123"
  new TaskChain(() => {
    //目标任务
    console.log("登陆成功")
  }).addInterceptor((task) => {
    //预检是否为空
    if (!name || !password) {
      console.log("账户密码不能为空")
      return
    }
    //预检成功,下一步
    task.next()
  }).addInterceptor((task) => {
    //是否存在账号
    if (name !== "xiaobai") {
      console.log("账号不存在")
      return
    }
    //预检成功,下一步
    task.next()
  }).addInterceptor((task) => {
    //是否密码正确
    if (password !== "123") {
      console.log("密码错误")
      return
    }
    //预检成功,下一步
    task.next()
  }).process() //开始任务
}