前后端分离鉴权:token和axios请求响应拦截器

      发布在:Notes, 前端技术, 服务器笔记, 网络日记      评论:0 条评论

首先来看一下设计思路
后端使用的是laravel5.5,搭配jwt-auth来做CORS跨域,每个请求前端都需要在请求头里带token,并且存储到本地localStoragetoken在服务端默认八小时过期,到还剩2小时的时候后端会在这段时间内的请求响应头里返回新的token,前端拿到新的token更新本地token
整体流程看起来不复杂,并且项目里本身就在使用axios 设置拦截器起来还是轻松的

// main.js
import Vue from 'vue'
import App from './App'
import router from './router'
import store from './store'

import axios from 'axios'
Vue.prototype.$axios = axios

Vue.config.productionTip = false;

import MetaInfo from 'vue-meta-info'
Vue.use(MetaInfo);

/* eslint-disable no-new */
new Vue({
  el: '#app',
  router,
  store,
  components: { App },
  template: '<App/>',
  created(){
    //axios请求响应拦截器
    this.$axios.interceptors.request.use(//拦截请求
      config=>{
        //console.log(this.$store.state.token)
        if(localStorage.getItem('token')){//查询本地是否存在token
          config.headers.Authorization = localStorage.getItem('token')//在请求头里设置token
        }
        return config
      },
      err=>{
        return Promise.reject(err);
      }
    ),
    this.$axios.interceptors.response.use(//拦截响应
      response=>{
        var token = response.headers.authorization
        if(token){//查询响应头里是否存在token
          this.$store.dispatch('refreshToken', token)//存在则调用store替换本地token 可以根据自己的业务 更简单的做法是直接在这里替换localStorage的token
        }
        return response
      },
      error=>{
        console.log(error)
        return Promise.reject(error)
      }
    )
  }
})

需要注意的是,在加入了Authorization的请求头以后,我们发出的http请求就不再属于简单请求并且自定义请求头,浏览器会在真正的请求之前做一次option请求,来询问实际发送的请求是否是安全的/可用的
另外后端在响应头里返回token时,可能会存在前端能在浏览器里的network里看到Authorization,但是响应拦截器里获取不到response.headers.authorization的情况,这个原因是W3C制定的跨域规则中,只允许后端和浏览器之间得到允许的数据,所以需要后端设置header
add_header 'Access-Control-Allow-Origin' '*';
当然了 *号部分可以是填上某个专有的,比如我只想要Authorization可以获取到,那么这里就可以只填这项,具体的可以看一下MDN上对于Access-Control-Allow-Origin的解释:点这里查看

Responses