axios 拦截器——基本用法及拦截器代码
之前在开发后台管理系统时,都是跟其他同事一起开发,说实在点,就是在别人开发的基础上写页面。。。
现在想把之前没有关注的点拾起来。。
今天看下axios
拦截器的用法
用vue
写代码在做ajax
请求时,可以用到axios
,具体就相当于请求前进行校验(拦截)
和响应前进行校验(拦截)
.
什么是axios
axios
是一个基于Promise
用于浏览器和 nodejs
的 HTTP
客户端。简单的理解就是ajax的封装
它本身具有以下特征:
- .从浏览器中创建
XMLHttpRequest
- 从
node.js
发出http
请求 - 支持
Promise API
- 拦截请求和响应
- 转换请求和响应数据
- 取消请求
- 自动转换
JSON
数据 - 客户端支持防止
CSRF/XSRF
axios
官网地址:https://www.npmjs.com/package/axios
npm
安装方法:
$ npm install axios
axios
用法
1.在src
目录下创建一个js
文件并引入axios
import axios from 'axios'; //引入axios
//下面的两个不一定要引入,看项目在拦截时需要做什么操作,一般都是需要引入store的,因为可以拿到用户的登录信息
import store from '@/store/index';//引入store
import router from '@/router';//引入router
2.创建一个axios
实例
let instance = axios.create({
headers:{
'content-type':'application/x-www-form-urlencoded'
}
})
3.编写请求拦截器
这个拦截器会在你发送请求之前运行,此处请求拦截器的功能是:每次请求前去判断是否有token
,如果token
存在则在请求头加上这个token
,后台会判断这个token
是否过期。
// http request拦截器
instance.interceptors.request.use(
config=>{
const token = localStorage.getItem('token');//此处用这个localStorage 也可以用store,因为一般登录后都会将登录信息存储到vuex中,但是如果不存储到localsStorage的话,当前页面刷新时,vuex中的内容会消失。
if(token){
config.headers.authorization = token //请求头加上token
}
return config
},err=>{
return Promise.reject(err);
}
)
4.编写响应拦截器
这个拦截器会在拿到后台接口返回的数据后,进行响应处理。比如数据正确返回是code
是200,如果code
是500,则需要拦截一下。
instance.interceptors.response.use(
response = {
//拦截响应,做统一处理
if(response.data.code){
switch(response.data.code){
case 1002:
store.state.isLogin = false;//store中有个isLogin表示登录状态,这个视具体情况而定
router.replace({
path:'login',
query:{
redirect:router.currentRoute.fullPath
}
})
}
}
return response
},
//接口错误状态处理,也就是说无响应时的处理
error =>{
return Promise.reject(error.response.status);//接口返回的错误信息
}
)
5.导出实例
export default instance
6.axios
的使用
在接口对应的js
文件中,使用axios
,比如login.js
登录相关的接口
import axios from './axios'
/* 验证登录 */
export function handleLogin(data){
return axios.post('/user/login',data)
}
在登录页面就可以直接引入login.js
,然后使用handleLogin
即可。
<script>
import loginApi from '@/api/login.js'
export default{
data(){ },
created(){
loginApi({ xxx}).then(res=>{
console.log(res);
}).catch(err=>{
console.log(err);
})
}
}
</script>
下面附录一个我第一份vue
前端工作时,大神的代码:
import axios from 'axios';
import router from '@/router/routers';
import { Notification,MessageBox,Loading} from 'element-ui';
import store from '../store'
import { getToken} from '@/utils/auth'
import Config from '@/setting'
var qs = require('qs')//qs主要是用于处理formData的数据
//创建 axios实例
const service = axios.create({
baseURL:process.env.NODE_ENV ==='production'?process.env.VUE_APP_BASE_API:'/',//api的base_url
timeout:Config.timeout //请求时间
})
let loadingInstance
//request拦截器
service.interceptors.request.use(
config=>{
if(getToken()){
config.headers['Authorization'] = getToken() //让每个请求携带自定义的token,请根据实际情况自行修改
}
config.headers['Content-Type'] = 'application/json'
//这个headers头部的Content-Type:一般都是application/json,但是也有部分接口需要传递的是formData格式的,此时就需要用到qs,为了做区分,在config参数中添加一个type变量来进行判断处理
if(config.type && config.type == 'form'){
config.headers['Content-Type'] = 'application/x-www-form-urlencoded'
if(config.data){
config.data = qs.stringify(config.data);
}
}
if(config.loading){
loadingInstance = Loading.service({ fullscreen:true})
}
return config
},
error =>{
console.log(error);
Promise.reject(error);
}
)
//response拦截器
service.interceptors.response.use(
response =>{
const code = response.status
if(code<200 ||code>300){
Notification.error({
title:response.message
})
if(loadingInstance){
loadingInstance.close();
}
return Promise.reject('error')
}else{
if(loadingInstance){
loadingInstance.close();
}
return response.data
}
},
error =>{
let code = 0
try{
code = error.response.data.status
}catch(e){
if(error.toString().indexOf('Error:timeout') !==-1){
Notification.error({
title:"网络请求超时",
duration:5000
})
return Promise.reject(error)
}
}
if(code){
if(code==401){
MessageBox.confirm(
'登录状态已过期,您可以继续留在该页面,或者重新登录',
'系统提示',
{
confirmButtonText:'重新登录',
cancelButtonText:'取消',
type:'warning'
}
).then(()=>{
store.dispatch('Login').then(()=>{
location.reload();//为了重新实例化vue-router对象
})
})
}else if(code==405){
router.push({ path:'/401'})
}else{
const errorMsg = error.response.data.message
if(errorMsg !== undefined){
Notification.error({
title:errorMsg,
duration:5000
})
}
}
}else{
Notification.error({
title:'接口请求失败',
duration:5000
})
}
return Promise.reject(error)
}
)
export default service
接口文件的内容:
import request from '@/utils/request'
//get请求的写法:
export function getShopList(data, loading) {
// eslint-disable-next-line no-return-assign
return get('api/shop/list', data, loading)
}
//post请求的写法:
export function modifyAdmin(data) {
return request({
url: 'api/shop/modify/admin',
method: 'post',
data
})
}
//formData格式的post请求的写法:
export function verify(data) {
return request({
type: 'form',
url: 'api/shop/verify',
method: 'post',
data
})
}
vue
页面中使用接口的部分内容:
import { verify } from '@/api/shop'
...
methods:{
verify(this.verifyObj).then(res => {
....
}).catch(error => {
...
})
}
还没有评论,来说两句吧...