import axios from 'axios'
import NProgress from 'nprogress'
import apiConfig from '../api/config.js'

const { igSuccessUrl } = apiConfig

function pathVariable(url, obj) {
  const prefix = url.indexOf('{')
  if (prefix > -1) {
    const suffix = url.indexOf('}')
    const key = url.substr(prefix + 1, suffix - prefix - 1)
    url = url.replace('{' + key + '}', obj[key])
    return pathVariable(url, obj)
  }
  return url
}

const install = (app, { router, store, opt }) => {
  const config = {
    Global: true,
  }

  const _axios = axios.create(config)
  let ve_loading
  let ve_message = null
  let loadingCount = 0

  function getIsShow(url) {
    for (const s of igSuccessUrl) {
      if (url.indexOf(s) > -1) {
        return true
      }
    }
    return false
  }

  _axios.interceptors.request.use(
    (reqConfig) => {
      NProgress.done()
      if (reqConfig.Global && getIsShow(reqConfig.url) === false) {
        // 可按需开启 loading
      }
      loadingCount++
      const token = store.getters.token
      token && (reqConfig.headers.token = token)
      reqConfig.headers.appId = 'wx628f62793fdf5251'
      return reqConfig
    },
    (error) => Promise.reject(error),
  )

  _axios.interceptors.response.use(
    (response) => {
      loadingCount--
      if (loadingCount <= 0) {
        NProgress.done()
        if (ve_loading) ve_loading.close()
      }
      let type = ''
      if (response.data.code == 0 || response.data.code === 1) {
        type = 'success'
      } else {
        type = 'error'
      }
      if (type === 'error' || getIsShow(response.request.responseURL) === false) {
        if (ve_message) {
          ve_message.close()
          ve_message = null
        }
        if (response.data.msg) {
          console.log(response.data.msg)
        }
      }
      return response.data
    },
    (error) => {
      loadingCount--
      if (loadingCount <= 0) {
        NProgress.done()
        ve_loading && ve_loading.close()
      }
      if (error && error.response) {
        let message = ''
        switch (error.response.status) {
          case 400:
            message = '请求错误'
            break
          case 401: {
            message = '未授权，请登录'
            router.replace({ name: 'DevLogin' })
            break
          }
          case 403:
            message = '没有权限，拒绝访问'
            break
          case 404:
            message = '请求地址出错'
            break
          case 408:
            message = '请求超时'
            break
          case 500:
            message = '服务内部错误'
            break
          case 501:
            message = '服务未实现'
            break
          case 502:
            message = '网关错误'
            break
          case 503:
            message = '服务不可用'
            break
          case 504:
            message = '网关超时'
            break
          case 505:
            message = 'HTTP版本不受支持'
            break
          default:
            break
        }
        if (ve_message) {
          ve_message.close()
          ve_message = null
        }
        if (message) console.error(message)
      }
      return Promise.reject(error)
    },
  )

  const method = {
    post: (url, p, reqConfig) => _axios.post(url, p, reqConfig),
    get: (url, p, reqConfig) =>
      _axios.get(url, Object.assign({}, reqConfig, { params: p })),
    put: (url, p, reqConfig) => _axios.put(url, p, reqConfig),
    delete: (url, p, reqConfig) => _axios.delete(url, reqConfig),
  }

  const api = {}
  const modules = import.meta.glob('../api/modules/*.js', { eager: true })

  Object.entries(modules).forEach(([filePath, mod]) => {
    const fileName = filePath.replace(/.*\/([^/]+)\.js$/, '$1')
    api[fileName] = {}
    const obj = mod.default ?? mod
    Object.keys(obj).forEach((item) => {
      api[fileName][item] = (p, reqConfig = {}) => {
        if (
          VE_ENV.MOCK === 'True' &&
          obj[item].mockCondition &&
          obj[item].mockCondition(p)
        ) {
          return obj[item].mockFun(p)
        }

        if (store.state.app.authkey) {
          if (obj[item].type === 'get') {
            p = p || {}
            p.key = store.state.app.authkey
          } else {
            obj[item].url =
              obj[item].url +
              (obj[item].url.indexOf('?') > -1
                ? '&key=' + store.state.app.authkey
                : '?key=' + store.state.app.authkey)
          }
        }
        return method[obj[item].type](pathVariable(obj[item].url, p), p, reqConfig)
      }
    })
  })

  window[opt] = api
  app.config.globalProperties[opt] = api
}

export default { install }
