更新時間:2020-12-10
許多小伙伴在接觸了vue之后虐呻,肯定知道在vue項目開發(fā)過程中都會有一個配置文件掸掏,沒錯就是vue.config.js(vue-cli3+)船殉,在這個文件里可以配置很多東西,比如說接口代理炕桨、跨域之類的饭尝,所以很多剛接觸vue的小伙伴很難分清接口代理和api封裝。
簡單來說献宫,api封裝就是將接口統(tǒng)一管理钥平,但是要將接口統(tǒng)一管理,需要調(diào)用axiso的一些方法姊途,因此我們在開始api 之前要先將axiso進行封裝(將axiso的功能整合涉瘾,方便自己調(diào)用)
此外axiso封裝后,可以根據(jù)不同的環(huán)境捷兰,切換接口地址立叛,這一點非常實用。
廢話不多說贡茅,axiso封裝 → http.js
import axios from 'axios';
import QS from 'qs';
import router from './router' // 配合路由守衛(wèi)秘蛇,進行攔截
import store from './store' // 多用于token存取
/**
環(huán)境的切換
*/
if (process.env.NODE_ENV === 'development') { //開發(fā)環(huán)境
axios.defaults.baseURL = '……'; //測試接口
} else if (process.env.NODE_ENV === 'test') { //測試環(huán)境
axios.defaults.baseURL = '……'; //測試接口
} else if (process.env.NODE_ENV === 'production') { //線上環(huán)境
axios.defaults.baseURL = '……'; //測試接口
}
// 請求超時時間 10S
axios.defaults.timeout = 10000;
// 請求頭
axios.defaults.headers.post['Content-Type'] = 'application/x-www-form-urlencoded;charset=UTF-8';
/**
* http request 請求攔截,一般用于token 驗證
*/
axios.interceptors.request.use(
config => {
if(store.state.token){ // 判斷token 是否存在友扰,如果存在拼到請求地址后邊
let reg = new RegExp('"',"g"); //刪除請求地址中的 "
// 在請求地址中加上 token
config.url = `${config.url}?token=${store.state.token}`.replace(reg,"");
}
return config;
},
error => {
console.log('請求攔截器彤叉!');
return Promise.reject(error);
}
);
/**
* http response 響應(yīng)攔截
*/
axios.interceptors.response.use(
/**
* 如果返回的狀態(tài)碼為200,說明接口請求成功村怪,可以正常拿到數(shù)據(jù)
* 否則的話拋出錯誤
*/
response => {
if (response.status === 200) {
return Promise.resolve(response);
} else {
return Promise.reject(response);
}
},
/**
* 服務(wù)器狀態(tài)碼不是200的的情況
* 這里可以跟你們的后臺開發(fā)人員協(xié)商好統(tǒng)一的錯誤狀態(tài)碼
* 然后根據(jù)返回的狀態(tài)碼進行一些操作,例如登錄過期提示浮庐,錯誤提示等等
* 下面列舉幾個常見的操作甚负,其他需求可自行擴展
*/
error => {
if (error.response.status) {
switch (error.response.status) {
/**
* 401: 未登錄
* 未登錄則跳轉(zhuǎn)登錄頁面柬焕,并攜帶當前頁面的路徑
* 在登錄成功后返回當前頁面,這一步需要在登錄頁操作梭域。
*/
case 401:
router.replace({
path: '/',
query: {
redirect: router.currentRoute.fullPath
}
});
break;
/**
* 403 token過期
* 登錄過期對用戶進行提示
* 清除本地token和清空vuex中token對象
* 跳轉(zhuǎn)登錄頁面
*/
case 403:
console.log('登錄過期斑举,請重新登錄');
// 清除token
localStorage.removeItem('token');
store.commit('loginSuccess', null); // 不太懂的話可不對狀態(tài)碼進行操作
// 跳轉(zhuǎn)頁面,并將要瀏覽的頁面通過fullPath傳過去病涨,登錄成功后可跳轉(zhuǎn)至需要訪問的頁面
setTimeout(() => {
router.replace({
path: '/',
query: {
redirect: router.currentRoute.fullPath
}
});
}, 1000);
break;
/**
* 404請求不存在
*/
case 404:
console.log('請求網(wǎng)絡(luò)請求不存在');
break;
/**
* 其他錯誤富玷,直接拋出錯誤提示
*/
default:
console.log(error.response.data.message);
}
return Promise.reject(error.response);
}
}
);
/**
* get方法,對應(yīng)get請求
* @param {String} url [請求的url地址]
* @param {Object} params [請求時攜帶的參數(shù)]
*/
export function get(url, params) {
return new Promise((resolve, reject) => {
axios.get(url, { params: params }) .then(res => {
resolve(res.data);
}).catch(err => {
reject(err.data)
})
});
}
/**
* post方法既穆,對應(yīng)post請求
* @param {String} url [請求的url地址]
* @param {Object} params [請求時攜帶的參數(shù)]
* @param {String} type [參數(shù)類型赎懦,默認表單數(shù)據(jù),可能為json]
*/
export function post(url, params) {
if(type){ // 傳輸方式為json
let headers = {'Content-Type': 'application/json;'};
if(type == 'DATA' || type == 'data'){ // 有文件傳輸
headers = {'Content-Type': 'multipart/form-data;'};
}
return new Promise((resolve, reject) => {
axios({
headers,
method: 'POST',
url,
data:params
}).then(res => {
resolve(res.data);
}).catch(err => {
reject(err.data);
});
});
}else{ // 傳輸方式為表單
return new Promise((resolve, reject) => {
axios.post(url, QS.stringify(params)).then(res => {
resolve(res.data);
}).catch(err => {
reject(err.data);
});
});
}
}
這是一個非常簡單的分裝幻工,可以簡單的使用post/get請求励两,axiso的封裝遠不止如此,比如響應(yīng)攔截囊颅、錯誤處理等当悔。
接下來接口管理 → api.js
//引入http.js
import { get, post } from './http.js'
export const apiConfig = {
// 編寫接口
getTest:par => post('/test', par), //這樣就寫好了一個接口,可以使用了
}
在組件內(nèi)使用封裝后的接口
<script>
//引入api.js
import {apiConfig} from '../../../api/api'
export default {
name:'testCom',
methods:{
// 獲取數(shù)據(jù)
getData(par){
apiConfig.getTest({'name':par}).then(res => {
console.log(res);
})
}
},
mounted(){
this.getData('小明') //鉤子函數(shù)中調(diào)用方法獲取數(shù)據(jù)
},
}
</script>
PS:在實際的工作或?qū)W習(xí)中踢代,并不一定只有這一種方式盲憎,方法的編寫和調(diào)用也不要照抄照搬,在這里只是分享一個可行的思路胳挎,以至于其它的就要靠小伙伴自己研究了饼疙,此外,雖然此文以 vue 舉例說明串远,但是主要對于axios 的封裝宏多,并不僅限于此,例如在 react 項目中也同樣適用哦~
另外附贈目錄截圖澡罚,以免有的小伙伴不知道文件建在那里伸但,產(chǎn)生疑惑。