interceptor.ts 2.6 KB
Newer Older
1 2 3 4 5 6 7
import {
  isArray,
  isFunction,
  isPlainObject,
  isString,
  remove,
} from '@vue/shared'
fxy060608's avatar
fxy060608 已提交
8 9

import {
fxy060608's avatar
fxy060608 已提交
10
  HOOKS,
fxy060608's avatar
fxy060608 已提交
11 12 13 14 15 16
  Interceptor,
  scopedInterceptors,
  globalInterceptors,
  Interceptors,
} from '../../helpers/interceptor'

fxy060608's avatar
fxy060608 已提交
17
import { defineSyncApi } from '../../helpers/api'
fxy060608's avatar
fxy060608 已提交
18 19

import {
fxy060608's avatar
fxy060608 已提交
20 21
  API_ADD_INTERCEPTOR,
  API_REMOVE_INTERCEPTOR,
fxy060608's avatar
fxy060608 已提交
22
  AddInterceptorProtocol,
23
  RemoveInterceptorProtocol,
fxy060608's avatar
fxy060608 已提交
24 25
} from '../../protocols/base/interceptor'

fxy060608's avatar
fxy060608 已提交
26 27 28 29
function mergeInterceptorHook(
  interceptors: Interceptors,
  interceptor: Interceptor
) {
30
  Object.keys(interceptor).forEach((hook) => {
fxy060608's avatar
fxy060608 已提交
31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46
    if (isFunction(interceptor[hook as HOOKS])) {
      interceptors[hook as HOOKS] = mergeHook(
        interceptors[hook as HOOKS],
        interceptor[hook as HOOKS]
      )
    }
  })
}

function removeInterceptorHook(
  interceptors: Interceptors,
  interceptor: Interceptor
) {
  if (!interceptors || !interceptor) {
    return
  }
fxy060608's avatar
fxy060608 已提交
47 48 49 50 51
  Object.keys(interceptor).forEach((name) => {
    const hooks = interceptors[name as HOOKS]
    const hook = interceptor[name as HOOKS]
    if (isArray(hooks) && isFunction(hook)) {
      remove(hooks, hook)
fxy060608's avatar
fxy060608 已提交
52 53 54 55 56 57 58 59 60 61 62 63
    }
  })
}

function mergeHook(
  parentVal: Function[] | undefined,
  childVal: Function[] | Function | undefined
) {
  const res = childVal
    ? parentVal
      ? parentVal.concat(childVal)
      : isArray(childVal)
64 65
      ? childVal
      : [childVal]
fxy060608's avatar
fxy060608 已提交
66 67 68 69 70 71 72 73 74 75 76 77 78 79
    : parentVal
  return res ? dedupeHooks(res) : res
}

function dedupeHooks(hooks: Function[]) {
  const res: Function[] = []
  for (let i = 0; i < hooks.length; i++) {
    if (res.indexOf(hooks[i]) === -1) {
      res.push(hooks[i])
    }
  }
  return res
}

fxy060608's avatar
fxy060608 已提交
80
export const addInterceptor = defineSyncApi(
fxy060608's avatar
fxy060608 已提交
81
  API_ADD_INTERCEPTOR,
fxy060608's avatar
fxy060608 已提交
82
  (method: string | Interceptor, interceptor: Interceptor | undefined) => {
83
    if (isString(method) && isPlainObject(interceptor)) {
fxy060608's avatar
fxy060608 已提交
84 85 86 87 88 89 90 91 92 93
      mergeInterceptorHook(
        scopedInterceptors[method] || (scopedInterceptors[method] = {}),
        interceptor
      )
    } else if (isPlainObject(method)) {
      mergeInterceptorHook(globalInterceptors, method as Interceptor)
    }
  },
  AddInterceptorProtocol
)
fxy060608's avatar
fxy060608 已提交
94

fxy060608's avatar
fxy060608 已提交
95
export const removeInterceptor = defineSyncApi(
fxy060608's avatar
fxy060608 已提交
96
  API_REMOVE_INTERCEPTOR,
fxy060608's avatar
fxy060608 已提交
97
  (method: string | Interceptor, interceptor: Interceptor | undefined) => {
98
    if (isString(method)) {
fxy060608's avatar
fxy060608 已提交
99 100 101 102 103 104 105 106 107 108 109 110
      if (isPlainObject(interceptor)) {
        removeInterceptorHook(scopedInterceptors[method], interceptor)
      } else {
        delete scopedInterceptors[method]
      }
    } else if (isPlainObject(method)) {
      removeInterceptorHook(globalInterceptors, method)
    }
  },
  RemoveInterceptorProtocol
)

fxy060608's avatar
fxy060608 已提交
111
export const interceptors = {}