首页 > 解决方案 > 登录表单无法使用基于用户角色的身份验证和重定向呈现

问题描述

我正在开发一个小项目,它是一个具有管理员角色和仪表板的简单页面。我使用 JWT 令牌进行用户身份验证和授权。我的问题是,当没有具有 user.role 的令牌时,我的 Login.js 表单无法呈现所以我的代码如下所示: Login.js

import React, { Component } from 'react';
import { Redirect } from 'react-router-dom';
import axios from 'axios';

import { API_URL } from '../../../config';

import { authenticateUser, isAuthUser } from '../../../utils/utils';
import Layout from '../../layout/MainLayout/Layout';
import Button from '../../common/Buttons/Button';

class Login extends Component {
  state = {
    formData: {
      email: '',
      password: '',
    },
    userRedirect: false,
  };

  signIn = (user) => {
    const config = {
      headers: {
        'Content-Type': 'application/json',
      },
    };

    console.log('user axios', user.role);
    axios
      .post(`${API_URL}/login`, user, config)
      .then((res) => authenticateUser(res.data));
    this.setState({
      formData: { email: '', password: '' },
      userRedirect: true,
    });
  };

  onChange = (e) => {
    const { formData } = this.state;
    //assign form data to new variable
    let newFormData = { ...formData };
    newFormData[e.target.name] = e.target.value;
    this.setState({
      formData: newFormData,
    });
  };

  onSubmit = (e) => {
    const { password, email } = this.state.formData;
    e.preventDefault();
    this.signIn({ email, password });
  };

  formRender = (email, password) => (
    <form onSubmit={this.onSubmit}>
      <div className='form-group'>
        <label className='text-muted'>Email</label>
        <input
          type='email'
          name='email'
          value={email}
          onChange={this.onChange}
          className='form-control'></input>
      </div>
      <div className='form-group'>
        <label className='text-muted'>Password</label>
        <input
          type='password'
          name='password'
          minLength='6'
          value={password}
          onChange={this.onChange}
          className='form-control'></input>
      </div>
      <Button type='submit'>Login</Button>
    </form>
  );

  redirectUser = () => {
    const { userRedirect } = this.state;
    const { user } = isAuthUser();
    if (userRedirect === true) {
      console.log('user role', user.role);
      console.log('auth fuc', isAuthUser());
      if (user.role === 2308) {
        return <Redirect to='/admin/dashboard' />;
      } else {
        return <Redirect to='/users/me' />;
      }
    }
  };

  render() {
    const { email, password } = this.state.formData;
    return (
      <Layout title='Login Form' description='Login to your account'>
        {this.formRender(email, password)}
        {this.redirectUser()}
      </Layout>
    );
  }
}

export default Login;

登录表单正在工作。当我试图获得我的角色时,一切都变得一团糟。但是我已经完成了一些控制台日志,并且redirectUser有一个 user.role 应该基于正在登录的用户。

我在 utils.js 中有两个函数,用于检查用户是否经过身份验证以及本地存储中是否存在 JWT:


export const authenticateUser = (data) => {
  if (typeof window !== 'undefined') {
    localStorage.setItem('jwt', JSON.stringify(data));
  }
};

//check if user is auth and there is jwt item in localstorage. menu render
export const isAuthUser = () => {
  if (typeof window == 'undefined') {
    return false;
  }
  if (localStorage.getItem('jwt')) {
    return JSON.parse(localStorage.getItem('jwt'));
  } else {
    return false;
  }
};

我确实明白了,我的错误来自

 <Layout title='Login Form' description='Login to your account'>
        {this.formRender(email, password)}
        {this.redirectUser()}
      </Layout>

this.redirectUser()让我这个角色未定义。但我不知道如何让这个工作。从控制台日志我得到用户角色。

感谢帮助

标签: javascriptnode.jsreactjs

解决方案


似乎当您没有令牌时,localStorage您正在从boolean. 这就是我的意思:

redirectUser = () => {
  const { userRedirect } = this.state;
  const { user } = isAuthUser();        // isAuthUser() returns false when there is no jwt in the localStorage
  if (userRedirect === true) {
    console.log("user role", user.role);
    console.log("auth fuc", isAuthUser());
    if (user.role === 2308) {
      return <Redirect to="/admin/dashboard" />;
    } else {
      return <Redirect to="/users/me" />;
    }
  }
};

你至少应该在解构之前检查你的结果。尝试这个:

redirectUser = () => {
  const { userRedirect } = this.state;
  const authData = isAuthUser();

  if (authData === false) {      // if jwt is not in localStorage

    return <Redirect to="/sign-in-path-in-your-app" />;

  } else if (userRedirect === true) {
    const { user } = authData;   // perform destructuring because here authData is not false but an object
    console.log("user role", user.role);
    console.log("auth fuc", isAuthUser());
    if (user.role === 2308) {
      return <Redirect to="/admin/dashboard" />;
    } else {
      return <Redirect to="/users/me" />;
    }
  }
};

推荐阅读