封裝axios

image.png

首先觀察一下項(xiàng)目目錄,本次的主題是封裝一套axios,封裝的內(nèi)容就放在圖中的api目錄下。
一個(gè)完整的axios,首先我們會(huì)想到什么呢?應(yīng)該是路由,對(duì)吧,我們先建一個(gè)路由config.js,來(lái)控制不同環(huán)境的路由設(shè)置。

/**
 * 配置不同環(huán)境接口前綴
 * 如果未配置dev為默認(rèn)配置
 * @param {*} base
 * @example
 * {
 *   dev: 'dev環(huán)境配置信息',
 *   test: 'test環(huán)境配置信息',
 *   prod: '線上環(huán)境配置信息'
 * }
 */
function conf (base = {}) {
  if (process.env.NODE_ENV === 'production') { // 生產(chǎn)環(huán)境下
    let env = process.env.ENV_CONFIG || 'dev'
    return base[env] || base['dev']
  }
  // 開(kāi)發(fā)環(huán)境
  return base['dev']
}

// PORTAL 接口
export const POR_LOGIN_LOGOUT = conf({
  dev: 'http://`````',
  test: 'http://`````',
  prod: 'http://`````'
})

這種設(shè)置很適合一個(gè)項(xiàng)目中分很多模塊,且不同模塊之間的接口不同,如果是項(xiàng)目中大多數(shù)接口地址前綴都相同的話,那其實(shí)還可以簡(jiǎn)化一下路由這塊,視需求來(lái)定。
路由解決了,接下來(lái)當(dāng)然就是建立axios請(qǐng)求啦,讓我們建立一個(gè)request.js文件。

import axios from 'axios'
import store from '@/store'
import {POR_LOGIN_LOGOUT} from './config'
/* eslint-disable */

// portal base
export const porApi = axios.create({
  baseURL: POR_LOGIN_LOGOUT, // api 的 base_url
  timeout: 15000, // request timeout
  headers: {
    'Content-Type': 'application/json'
  }
})
porApi.defaults.headers.get['Content-Type']= 'application/x-www-form-urlencoded'

這樣我們每個(gè)axios請(qǐng)求的基礎(chǔ)api是不是就完成,我們肯定是不想每次都寫(xiě)postget的對(duì)吧,這樣就到了終極的axios封裝問(wèn)題啦,讓我們建一個(gè)request-api.js來(lái)解決這個(gè)問(wèn)題。

/**
 * 公用方法集合
 */
const requestData = (nAxios, methods, url, datas, headers, timeout) => {
  let options = Object.assign({}, {
    url: url,
    method: methods,
    data: datas
  })
  if (headers) {
    options.headers = headers
  }
  if (timeout) {
    options.timeout = timeout
  }
  let listPromise = new Promise((resolve, reject) => {
    nAxios.request(options)
      .then(res => {
        resolve(res)
      }).catch(res => {
        reject(res)
      })
  })
  return listPromise
}
const queryData = (nAxios, url, query) => {
  let tempQuery = ''
  if (url.indexOf('?') === -1) {
    tempQuery = '?'
  }
  for (let key in query) {
    if (query[key] !== null && query[key] !== undefined && query[key] !== '' && query[key].length !== 0) {
      tempQuery += '&' + key + '=' + query[key]
    }
  }
  let listPromise = new Promise((resolve, reject) => {
    nAxios.get(encodeURI(url + tempQuery)).then((rst) => {
      resolve(rst)
    }).catch(error => {
      reject(error)
    })
  })
  return listPromise
}

postget我們都封裝好了,是不是直接調(diào)用就可以啦,我比較推薦的是將接口具體調(diào)用分模塊放在一起,而不是在vue業(yè)務(wù)代碼里寫(xiě)很多接口調(diào)用,所以在我這還有一層就是接口的具體調(diào)用api,因?yàn)槲抑敖ǖ?code>api是porApi,所以我們就以它來(lái)命名接口調(diào)用的js文件吧。

import {porApi} from './request'
import {requestData, queryData} from './request-api'

// 獲取權(quán)限和用戶名
export const getNameDetail = (count) => {
  return requestData(porApi, 'get', `/api/employee/info/query`)
}

在具體的業(yè)務(wù)代碼里,我們只要引入類(lèi)似getNameDetail這樣的方法就好了,返回的是promise,完全可以滿足大部分場(chǎng)景需要。經(jīng)常需要的攔截,我們也可以在request.js
里封裝好,就看具體需要了。

porApi.interceptors.response.use(responseInterceptor, errorResponseInterceptor)
porApi.interceptors.request.use(requestInterceptor, errorRequestInterceptor)

這樣的封裝在我看來(lái)是比較完整的,有些地方也可以視項(xiàng)目情況進(jìn)行刪減,總之,快樂(lè)開(kāi)發(fā)最重要。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書(shū)系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

友情鏈接更多精彩內(nèi)容