如果未通过身份验证,则重定向并在promise中设置setState

时间:2019-02-01 12:23:45

标签: javascript reactjs

我有:

["[\"manomhae4006\",\"pr3740\"]"]

我有两个问题,第一个是如果用户身份验证失败,如何使用路由器将其重定向回登录名,当前出现错误:import React, {Component} from 'react'; import ReactDOM from 'react-dom'; import PropTypes from "prop-types"; import {Router, Route, Switch} from 'react-router-dom' import { Redirect } from "react-router"; import history from './History'; import Home from '../containers/Home'; import Login from '../containers/LogIn'; import CreateUsers from '../containers/CreateUsers'; import Dashboard from '../containers/Dashboard'; import NavBar from './NavBar'; class App extends Component { constructor(props) { super(props); this.state = { isAuthenticated: false }; fetch("/api/user") .then(function (response) { return response.json(); }) .then(function (res) { console.log(res); if (res.enabled === 1) { this.setState({ isAuthenticated: true }); // Redirect the user only if they are on the login page. history.push("/dashboard"); } else { history.push("/login"); } }); } componentDidMount() { } render() { return ( <Router history={history}> <div> <NavBar /> <Route> <Redirect from="/" to="/login" /> // If not authenticated, how??? </Route> <Route path="/login" component={Login}/> <Route path="/dashboard" component={Dashboard}/> </div> </Router> ) } } ReactDOM.render(<App />, document.getElementById('app'))

的另一个问题是,它不能看到React.Children.only expected to receive a single React element child从:

this

给我.then(function (res) { console.log(res); if (res.enabled === 1) { this.setState({ isAuthenticated: true }); ...

4 个答案:

答案 0 :(得分:1)

尝试逐步解决您的问题

第一个 how can I get it to redirect back to the login using Router if the user failed authentication

我不建议您采用当前的方法,因为每次您进行身份验证(例如来自Facebook,Google的身份验证)时,回调都会再次到达您的 App 组件,再次发出请求,这样使应用程序陷入无限循环。

此外,为了避免产生副作用,所有请求都应在componentDidMount中进行

个人建议:使用终极版在这里。

这是我使用Redux进行客户端身份验证的方式

const AuthenticatedRoutes = ({component: Component, ...props})=> {
  return (
   <Route {...props}  render= {(prop) => {

     return (
       props.prop.isAuthenticated ? <Component {...prop} /> :
      <Redirect to={{
       pathname: "/login",
      }}/>
   )}
  }/>
)}

//These roots can;t be seen by users who are authenticated 
const NotAuthenticatedRoutes = ({component: Component, ...props}) => (
  <Route {...props}  render= {(prop) => {

    return (
     !props.prop.isAuthenticated ? <Component {...prop} /> :
     <Redirect to={{
      pathname: "/",
     }}/>
  )}
 }/>
)

class route extends Component {



    render () {

      return(

        <BrowserRouter>
          <div>
          <Switch>
            <NotAuthenticatedRoutes exact path ="/login"  component={Login} prop={this.props} />
            <AuthenticatedRoutes exact path  ="/"  component={HomeScreen} prop={this.props} />
        </Switch>
          </div>
        </BrowserRouter>
        )
    }
}

const mapStateToProps = state => {
  return {
    isAuthenticated: state.profileInfo.isAuthenticated,
    isLoaded: state.profileInfo.isLoaded,
    googleProfileLoading: state.profileInfo.googleProfileLoading
  }
};

export default connect(mapStateToProps, 
  {
    googleProfile
  })(route)

在这里,如果我的应用程序中的用户状态未设置为已通过身份验证,请在我的登录组件内部,对登录进行API调用,然后设置 Redux状态

第二个:从Win答案中复制此内容,检查您的函数的词法作用域

.then((res) => {
    if (res.enabled === 1) {
        this.setState({
            isAuthenticated: true
        });
    }
});

.then(function(res) => {
    if (res.enabled === 1) {
        this.setState({
            isAuthenticated: true
        });
    }
}).bind(this);

此外,使用ComponentDidMount进行api调用,以避免任何副作用

答案 1 :(得分:0)

第一期: 使用状态触发您的<%users.keys.sort.each do |author| <h1><%= link_to author.username, author %> says: </h1><br> <%users[author].each do |comment|%> <%=comment.body%><br /> <%end%> <%end%> 。提取完成后,我们可以使用响应来更新<Redirect/>状态,以便触发重新渲染。

isAuthenticated
.then((res) => {
    this.setState({
        isAuthenticated: res.enabled === 1,
    });
});

第二期: 因为你创造了响应的新功能,这是不行的,你可以通过改变它变成一个箭头的功能解决了这个让这点对类或绑定render() { return ( <Router history={history}> <div> {this.state.isAuthenticated && <Redirect from="/" to="/login" />} </div> </Router> ) } 这一点。

then

答案 2 :(得分:0)

1)使用isAuthenticated状态进行重定向

 !this.state.isAuthenticated && (<Route>
     <Redirect from="/" to="/login" /> // If not authenticated, how???
 </Route>)

2)使用箭头功能代替,然后将当前上下文中的该功能绑定到回调

.then((res) => {
            console.log(res);
            if (res.enabled === 1) {
                this.setState({
                    isAuthenticated: true
                });
                // Redirect the user only if they are on the login page.
                history.push("/dashboard");
            } else {
                history.push("/login");
            }
        });

答案 3 :(得分:0)

您的初始代码将与较小的更改一样工作。使承诺之前,借此在一个变量中像下面 -

让我=此;

当您答应完成并更新状态时,请按以下方式使用-

me.setState({                         isAuthenticated:true                     });

它将正常工作。