【问题标题】:PrivateRouter does not work as well in React JSPrivateRouter 在 React JS 中不能正常工作
【发布时间】:2018-07-23 14:04:48
【问题描述】:

我刚开始学习 React JS。在我的项目中,我需要创建两条路由,一条用于经过身份验证的用户,一条用于重定向到登录页面。

我使用 React Router 创建了这个结构。这是路由的容器:

export const history = createHistory();

class AppContainer extends Component {

componentDidMount(){
    this.props.checkUserExist();
}


render() {

    return (
        <Router history={history}>
            <Switch>
                <PrivateRoute path="/" component={Welcome} exact={true}/>
                <PrivateRoute path="/friends"  component={Friends}/>
                <PublicRoute path="/login"  component={Login}/>
                <PrivateRoute path="/loves" component={Loves}/>
                <Route component={NotFoundPage}/>
            </Switch>
        </Router>
    );
}

}


  const mapDispatchToProps = (dispatch) => {
    return {    
     checkUserExist: () => dispatch(checkUser())     
    };
};

export default connect(undefined,mapDispatchToProps)(AppContainer);

这些是行动:

export const checkUser = () => (dispatch) => {

dispatch({
    type: CHECKING_USER,
    payload: {
       loading:true,
       isAuth:false
    }
});

from(axios.get('https://mysite.private.com/userExist', {
    withCredentials: true
})).subscribe((result) => {

    console.log('result:', result);

    result.data == null
        ? dispatch({
            type: USER_NOT_EXIST,
            payload: {
                isAuth: false,
                loading:false
            }
        })

        : dispatch({
            type: USER_EXIST,
            payload: {
                isAuth: true,
                user:result.data,
                loading: false
            }
        });

}, (error) => dispatch({
    type: USER_CHECKING_ERROR,
    payload: {
        loading: false,
        isAuth:false,
        error
    }
 }));
};

和减速器:

const user = (state = {}, action) => {

switch (action.type) {

    case CHECKING_USER:

        return{
            ...state,
            ...action.payload
        };

    case USER_EXIST:

        return {
            ...state,
            ...action.payload
        };
    case USER_NOT_EXIST:

        return {
            ...state,
            ...action.payload
        };

    case USER_CHECKING_ERROR:
        return {
            ...state,
            ...action.payload
        }


    default:
        return state;
 }
};

export default user;

在 Redux 中。

这最后是PrivateRoute的声明:

import React from 'react';
import { connect } from 'react-redux';
import { Route, Redirect } from 'react-router-dom';


export const PrivateRoute = ({
     isAuthenticated, 
     component: Component, 
     ...rest 
    }) => (

    <Route {...rest} component={(props) => (
        isAuthenticated ? (
            <div><Component {...props} /></div>
        ) : (
            <Redirect to="/login" />
        )
    )}/>

);

const mapStateToProps = (state) => ({
    isAuthenticated: state.user.isAuth
});


export default connect (mapStateToProps)(PrivateRoute);

PublicRoute:

import React from 'react';
import { connect } from 'react-redux';
import { Route, Redirect } from 'react-router-dom';


export const PublicRoute = ({
     isAuthenticated, 
     component: Component, 
     ...rest 
    }) => (

    <Route {...rest} component={(props) => (
        isAuthenticated ? (
            <Redirect to="/" />
        ) : (
            <Component {...props} />
        )
    )}/>

);

const mapStateToProps = (state) => ({
    isAuthenticated: state.user.isAuth
});


export default connect (mapStateToProps)(PublicRoute);

错误是这样的:当你加载时,例如'/friends',它先到Login组件,然后到'/',所以在Welcome组件中。这可能是因为它在 checkUserExist() 完成之前呈现。

我的问题是:有没有办法避免它?也许使用超时或等待 ajax 调用完成。

感谢您的回答。

【问题讨论】:

    标签: javascript reactjs redux react-router react-redux


    【解决方案1】:
    import React from 'react';
    import { connect } from 'react-redux';
    import { Route, Redirect } from 'react-router-dom';
    
    
    export const PublicRoute = ({
         isAuthenticated, 
         component: Component, 
         ...rest 
        }) => {
    
        isAuthenticated ? localStorage.setItem("red", "") : localStorage.setItem(history.location.pathname) ;
        return (<Route {...rest} component={(props) => (
            isAuthenticated ? (
                <Redirect to="/" />
            ) : (
                <Component {...props} />
            )
        )}/>);
    
    };
    
    const mapStateToProps = (state) => ({
        isAuthenticated: state.user.isAuth
    });
    
    
    export default connect (mapStateToProps)(PublicRoute);
    
    
    export const history = createHistory();
    
    class AppContainer extends Component {
    
    componentDidMount(){
        this.props.checkUserExist();
    }
    
    redirectMe = () => {
        const redirect= localStorage.getItem("red");
        localStorage.getItem("red", "");
        if(redirect !== "")
            return <Redirect to={redirect} />
    }
    
    render() {
        redirectMe()
        return (
            <Router history={history}>
                <Switch>
                    <PrivateRoute path="/" component={Welcome} exact={true}/>
                    <PrivateRoute path="/friends"  component={Friends}/>
                    <PublicRoute path="/login"  component={Login}/>
                    <PrivateRoute path="/loves" component={Loves}/>
                    <Route component={NotFoundPage}/>
                </Switch>
            </Router>
        );
    }
    
    }
    
    
      const mapDispatchToProps = (dispatch) => {
        return {    
         checkUserExist: () => dispatch(checkUser())     
        };
    };
    
    export default connect(undefined,mapDispatchToProps)(AppContainer);
    

    我做了什么??

    我在私有路由中添加了一个条件,即如果用户未通过身份验证并且查找私有路由,则调用的 url 存储在 localstorage 中。

    由于 AppRouter 每次都会渲染,因此如果找到任何 url,它将检查 localstorage,它将移动到该 url 并清除本地存储。

    注意:如果这不起作用,则在 state 中创建一个变量并在 AppRouter.js 中连接该 state 变量,而不是在那里设置 localstorage set state。

    【讨论】:

      猜你喜欢
      • 2017-11-25
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2022-09-27
      • 2021-12-15
      • 2016-11-30
      • 1970-01-01
      相关资源
      最近更新 更多