验证Vuex + Axios错误的URL请求状态404

时间:2019-01-23 21:11:58

标签: javascript authentication vue.js axios vuex

我正在尝试使用正在使用的API进行身份验证,但是当我尝试登录时会收到以下响应: “无法加载资源:服务器以状态404(未找到)[http://localhost:8080/localhost:5000/api/login]进行了响应”

我认为问题出在axios,因为它使用我的本地Vue应用adress + apiAdress来执行请求。

main.js:

import axios from 'axios'
Vue.use(axios)
axios.defaults.baseURL = process.env.VUE_APP_API; //(http://localhost:5000/api

modules / auth.js:

import { AUTH_REQUEST, AUTH_ERROR, AUTH_SUCCESS, AUTH_LOGOUT } from '../actions/auth'
import { USER_REQUEST } from '../actions/user'
import axios from 'axios'

const state = { token: localStorage.getItem('user-token') || '', status: '', hasLoadedOnce: false }

const getters = {
  isAuthenticated: state => !!state.token,
  authStatus: state => state.status,
}

const actions = {
  [AUTH_REQUEST]: ({commit, dispatch}, user) => {
    return new Promise((resolve, reject) => {
     commit(AUTH_REQUEST)
  axios({url: '/login', data: user, method: 'POST'})
  .then(resp => {
    localStorage.setItem('user-token', resp.token)
    // Here set the header of your ajax library to the token value.
    axios.defaults.headers.common['Authorization'] = resp.token
    commit(AUTH_SUCCESS, resp)
    dispatch(USER_REQUEST)
    resolve(resp)
  })
  .catch(err => {
    commit(AUTH_ERROR, err)
    localStorage.removeItem('user-token')
    reject(err)
  })
})
},
}

const mutations = {
  [AUTH_REQUEST]: (state) => {
  state.status = 'loading'
  },
  [AUTH_SUCCESS]: (state, resp) => {
    state.status = 'success'
    state.token = resp.token
    state.hasLoadedOnce = true
  },
  [AUTH_ERROR]: (state) => {
  state.status = 'error'
  state.hasLoadedOnce = true
  },
  [AUTH_LOGOUT]: (state) => {
    state.token = ''
  }
}

export default {
 state,
 getters,
 actions,
 mutations,
}

Login.vue:

  methods: {
    login() {
      const { username, password } = this
      this.$store.dispatch(AUTH_REQUEST, { username, password }).then(() => {
      this.$router.push('/')
   })
    },

1 个答案:

答案 0 :(得分:0)

您完全不需要在main中定义axios。

而且,axios不是vue插件,因此Vue.use(axios)什么也不做。

在您的auth.js中,您可以创建一个实例

const axios = require('axios');

const axiosInstance = axios.create({
  baseURL: process.env.VUE_APP_API
});

在您的操作中,使用axios实例代替axios

const actions = {
  [AUTH_REQUEST]: ({commit, dispatch}, user) => {
    return new Promise((resolve, reject) => {
     commit(AUTH_REQUEST)
  axiosInstance({url: '/login', data: user, method: 'POST'})
  .then(resp => {
    localStorage.setItem('user-token', resp.token)
    // Here set the header of your ajax library to the token value.
    axios.defaults.headers.common['Authorization'] = resp.token
    commit(AUTH_SUCCESS, resp)
    dispatch(USER_REQUEST)
    resolve(resp)
  })
  .catch(err => {
    commit(AUTH_ERROR, err)
    localStorage.removeItem('user-token')
    reject(err)
  })
})

但是,这可能会导致在创建实例后更新标头的问题,因此您可能需要使用一些巧妙的方法来解决此问题。

一种方法是使用函数而不是值,该方法在您每次调用时都会使用本地存储中的数据

const axiosInstance = axios.create({
  baseURL: process.env.VUE_APP_API,
  headers: {
    Authorization: {
      toString () {
        return `Bearer ${localStorage.getItem('user-token')}`
      }
    }
  }
})

另一种方法是每次拨打电话时都会创建一个新请求

const actions = {
  [AUTH_REQUEST]: ({ commit, dispatch }, user) => {
    return new Promise((resolve, reject) => {
      const axiosInstance = axios.create({
        baseURL: process.env.VUE_APP_API
      });
      commit(AUTH_REQUEST)
      axiosInstance({
          url: '/login',
          data: user,
          method: 'POST'
        })
        .then(resp => {
          localStorage.setItem('user-token', resp.token)
          // Here set the header of your ajax library to the token value.
          axios.defaults.headers.common['Authorization'] = resp.token
          commit(AUTH_SUCCESS, resp)
          dispatch(USER_REQUEST)
          resolve(resp)
        })
        .catch(err => {
          commit(AUTH_ERROR, err)
          localStorage.removeItem('user-token')
          reject(err)
        })
    })
  },
  [SECURE_REQUEST]: ({ commit, dispatch }, user) => {
    return new Promise((resolve, reject) => {
      const axiosInstance = axios.create({
        baseURL: process.env.VUE_APP_API,
        headers: {
          'Authorization': 'Bearer ' + localStorage.getItem('user-token')
        }
      });
      commit(SECURE_REQUEST)
      axiosInstance({
          url: '/getData',
          data: user,
          method: 'POST'
        })
        // ...
    })
  },
}

另一个选项(这是我最近使用的选项)是使用devServer.proxy配置。这要求您使用Vue-Cli-3。它还假定最终的静态捆绑包将与您的API在同一服务器上运行,这可能对您不起作用。

另外,请查看以下解决方案:https://github.com/axios/axios/issues/1383#issuecomment-405900504