Vue 用户登入及token 认证

VUE 项目

新建vue 项目(eight)

#创建一个基于webpack模板的新项目
vue init webpack D:\node_workspace\eight
# 切换至项目路径
cd d:D:\node_workspace\eight
# 安装项目依赖文件,并且指定npm 国内镜像(淘宝镜像)
npm install --registry https://registry.npm.taobao.org
# 项目启动
npm run dev 

安装element-ui 

# 切换至项目路径
cd d:D:\node_workspace\eight
# 安装element-ui,临时使用国内的淘宝镜像
npm i element-ui -S --registry https://registry.npm.taobao.org

编辑Vue项目(eight)的main.js ,添加如下代码片段:

import ElementUI from 'element-ui';
import 'element-ui/lib/theme-chalk/index.css';
 
Vue.use(ElementUI);

安装axios

# 切换至项目路径
cd d:D:\node_workspace\eight
# 安装axios, 临时使用国内淘宝镜像
npm i axios -S --registry https://registry.npm.taobao.org

编辑Vue项目(eight)的main.js ,添加如下代码片段:

import axios from '../node_modules/axios'
// 设置后端请求地址
axios.defaults.baseURL='http://192.168.88.1:9090/shiro'
// 设置跨域
axios.defaults.withCredentials = true
Vue.prototype.$axios = axios

安装vuex

# 切换至项目路径
cd d:D:\node_workspace\eight
# 安装axios, 临时使用国内淘宝镜像
npm i vuex -S --registry https://registry.npm.taobao.org

在scr下键store文件夹,并且新增index.js 文件,新增文件内容如下:

import Vue from 'vue'
import Vuex from 'vuex'
Vue.use(Vuex);
 
const store = new Vuex.Store({
 
  state: {
    // 存储token
    token: localStorage.getItem('token') ? localStorage.getItem('token') : ''
  },
 
  mutations: {
    // 修改token,并将token存入localStorage
    changeLogin (state, user) {
      state.token = user.token;
      localStorage.setItem('token', user.token);
    }
  }
});
 
export default store;

在main.js 引入store 存储,并在VUE对象中进行实例化

Vue 项目结构:

VUE 组件定义(login.vue 和home.vue),源码如下:

login.vue


<template>
  <div>
    <input type="text" v-model="loginForm.username" placeholder="用户名"/>
    <input type="text" v-model="loginForm.password" placeholder="密码"/>
    <button @click="login">登录</button>
  </div>
</template>
 
<script>
import { mapMutations } from 'vuex';
export default {
  data () {
    return {
      loginForm: {
        username: '',
        password: ''
      },
      userToken: ''
    };
  },
 
  methods: {
    // 调用store 存储
    ...mapMutations(['changeLogin']),
    login () {
      let _this = this;
      if (this.loginForm.username === '' || this.loginForm.password === '') {
        alert('账号或密码不能为空');
      } else {
        // 发起登入请求
        this.$axios({
          method: 'post',
          url: '/common/login',
          headers: {
		     'Content-Type':'application/json;charset=utf-8' 
	      },
          data:{"username":_this.loginForm.username,"password":_this.loginForm.password},
        }).then(res => {
          console.log('123456');
          console.log(res);
          _this.userToken = res.token;
          // 将用户token保存到vuex中
          _this.changeLogin({ token: _this.userToken });
          // 用户登入成功,自动跳转至系统首页
          _this.$router.push('/home');
          alert('登陆成功');
        }).catch(error => {
          alert('账号或密码错误');
          console.log(error);
        });
      }
    }
  }
};
</script>

home.vue

<template>
    <div>首页</div>
</template>
<script>
export default {
    name: 'home'
}
</script>

Vue 路由配置router/index.js

import Vue from 'vue'
import Router from 'vue-router'
import login from '@/components/login';
import home from '@/components/home';

Vue.use(Router)

const router = new Router({
  routes: [
    {
      path: '/',
      redirect: '/login'
    },
    {
      path: '/login',
      name: 'login',
      component: login
    },
    {
      path: '/home',
      name: 'home',
      component: home
    }
  ]
})
// 导航守卫
// 使用 router.beforeEach 注册一个全局前置守卫,判断用户是否登陆
router.beforeEach((to, from, next) => {
  if (to.path === '/login') {
    next();
  } else {
    let token = localStorage.getItem('token');
    if (token === null || token === '') {
      next('/login');
    } else {
      next();
    }
  }
});
 
export default router;

mian.js(判断异步请求是否需要加入token到header里)

// The Vue build version to load with the `import` command
// (runtime-only or standalone) has been set in webpack.base.conf with an alias.
import Vue from 'vue'
import App from './App'
import router from './router'
import store from  './store'
import ElementUI from 'element-ui';
import 'element-ui/lib/theme-chalk/index.css';
import axios from '../node_modules/axios'
// 设置后端请求地址
axios.defaults.baseURL='http://192.168.88.1:9090/shiro'
// 设置跨域
axios.defaults.withCredentials = true
Vue.prototype.$axios = axios
Vue.use(ElementUI);
Vue.config.productionTip = false

// 添加请求拦截器,在请求头中加token
axios.interceptors.request.use(
  config => {
    if (localStorage.getItem('token')) {
      config.headers.token = localStorage.getItem('token');
    }
    return config;
  },
  error => {
    return Promise.reject(error);
  });

// 添加响应拦截器,移除token
axios.interceptors.response.use(
  response =>{
    return response;
  },
  error=>{
    if(error.response){
      switch(error.response.status){
        case 401:
          localStorage.removeItem('token');
          this.$router.push('/login');
      }
    }
  })
  

/* eslint-disable no-new */
new Vue({
  el: '#app',
  router,
  store,
  components: { App },
  template: '<App/>'
})

效果展示:

后端源码地址:https://github.com/zhouzhiwengang/lease_sys.git

  • 1
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值