vue 登录注册页面

625 阅读2分钟

样式中也可以使用@符,切记在前面加上~

//其中assets是存放共用的文件
background: url(~@/assets/images/icons.png) no-repeat -10px -201px;

注册业务|登录业务

🌟登录

//actions

async userLogin({commit},data){
        let result = await reqUserLogin(data);
        // 服务器下发token,用户唯一标识符(uuid)
        // 将来经常通过带token找服务器要用户信息进行展示
        // console.log(result);
        if(result.code == 200){
            // 用户登录成功且获取到token
            commit('USERLOGIN',result.data.token);
            // 持久化存储token
            setToken(result.data.token);
            return 'ok';
        }else{
            return Promise.reject(new Error('faile'));
        }
    },
//utils

export const setToken = (token)=>{
    localStorage.setItem('TOKEN',token);
}
export const getToken =()=>{
    return localStorage.getItem('TOKEN');
}
// 清除本地token
export const removeToken = ()=>{
    localStorage.removeItem('TOKEN');
}

🌟退出登录

// 退出登录 actions

   async userLogout({commit}){
    // 向服务器发送请求清空token
        let result = await reqLogout();
        if(result.code == 200){
            // action不能操作state,提交mutation修改state
            commit('CLEAR');
            return 'ok';
        }else{
            return Promise.reject(new Error('faile'));
        }

    },
//mutaions

    // 仓库中想关用户信息清空,本地存储的信息清空
    CLEAR(state){
        state.token = '';
        state.userInfo = {};
        removeToken();
    }


//js

async logout(){
      // 退出登录需要做的事:1.发请求通知服务器退出登录【清除一些数据:token】
      // 2.清除项目当中的数据【userInfo、token】
      try {
       await this.$store.dispatch('userLogout');
       // 退出登录后回到首页
       this.$router.push('/home');
      } catch (error) {
      }
    }

💁🏼‍♀️遇到的问题1:当用户注册完成,用户登录[用户名+密码]向服务器发请求,(组件派发请求'userlogin')登录成功获取token存储于仓库当中,(非持久化)路由跳转到home首页。 在首页当中mounted派发action(getuserInfo)获取用户信息,一级动态展示header组件内容。 一刷新home首页,获取不到用户信息,(token:vuex非持久化存储)

💁🏼‍♀️遇到的问题2:多个组件当中都要获取用户信息,需要在每个组件的mounted中触发this.$store.dispatch('getUserInfo')

💁🏼‍♀️遇到的问题3:用户已经登录了就不应该再回登录页。

💁🏼‍♀️遇到的问题4:用户可以输入URL进行路由跳转,这应该禁止。

解决方法:使用导航守卫

导航:表示路由正在发送改变,进行路由跳转 守卫:守护判断身份是否符合条件

全局守卫:只要发送路由的变化,守卫就能监听到

路由独享守卫:

组件内守卫:

登陆页面时如果有token则表示已登录:进入判断是否进入login页面,如果不是则全页放行,判断是否获取用户信息,如果没有获得则派发action进行捞数据,如果捞数据失败则说明token失效则重新登录并且跳转到登录页面;如果没有token则表示没有登录,进入游客状态

// 全局守卫:前置守卫(在路由跳转之前进行判断)
router.beforeEach(async (to,from,next)=>{
    // to:可以获取到你要跳转到那个路由信息
    // from:可以获取到你从那个路由得来的信息
    // next:放行函数 next()放行
    // next('/login')放行到指定的位置
    // next(false):中断当前的导航,如果浏览器的URL改变了(可能是用户手动或者浏览器后退按钮)
    // 那么URL地址会重置到from路由对应的地址
    // next();//测试
    // 引入store 判断用户是否登录过了(token是否有),未登录一定不会有token
    
    console.log(store.state.user.token);
    
    let token = store.state.user.token;
    let name = store.state.user.userInfo.name;

    if(token){
        // 用户登录过了后不能再去login页面
        if(to.path == '/login' || to.path == '/register'){
            next('/home');
        }else{
            // 如果有用户信息就放行
            if(name){
                next();
            }else{
                try {
                // 没有用户信息就重新派发action让仓库存储用户的信息再跳转
                await store.dispatch('getUserInfo');
                next();
            } catch (error) {
                // token失效了获取不到用户数据了
                // 清空token
                store.dispatch('userLogout');
                // 跳到登陆页
                next('/login');
                }
            }
        }
    }else{
        // 没有登录的话不能去交易相关的,不能去支付相关的,不能去个人中心
        //记录要去的地址
        let topath = to.path;
        if(topath.indexOf('/trade')!=-1 || topath.indexOf('/pay')!=-1 || topath.indexOf('/shopcart')!=-1){
            // 优化:用户没有登录时想去的地方保存下来后登录后再进行跳转
            //利用query获取路由信息
            next('/login?redirect='+topath);
        }else{
            // 去的不是则放行
            next();
        }
        next();
    }

});

🌟退出登录


//此时的登录页面会根据用户点击过的topath去执行登录结束后的跳转。

 async  userLogin(){
      try {
        // 登录成功
      const {phone,password} = this;
      (phone&&password)&& await this.$store.dispatch('userLogin',{phone,password});
      //如果query有值就把路由信息赋给topath,没有则跳转至/home
      let topath = this.$route.query.redirect||'/home';
      // 跳转
      this.$router.push(topath);
      } catch (error) {
        alert(error.mess);
      }
      }
    }

🌟独享路由守卫

 {   
 //在单独的路由上实现
            path:'/trade',
            name:'trade',
            component:Trade,
            meta:{show:true},
            beforeEnter:(to,from,next)=>{
                if(from.path == '/shopcart'){
                    next();
                }else{
                //阻断当前的路由导航跳转
                    next(false);
                }
            }
        },