1

I am troubled with redirect after login. As I know Fetch API has no concept of handling this. I tried to use React-router-dom but it is not working. I don't know what I am doing differently. I am trying to learn basic react, develop an application which is fully authenticated.

I did this

import {  BrowserRouter as Router, Route, Redirect} from 'react-router-dom';
import Dashboard from './Dashboard';

This is the state

this.state = {
redirect: false, 
username: '', 
l_password: ''
}

The Fetch API and setRedirect function

setRedirect =() =>{
        this.setState({
          redirect: true
        });
      }
      handleLogin =(event) =>{
      event.preventDefault();

      fetch('/oauth/token',
         {
            method: "POST",
            headers:{
                'Accept': 'application/json',
                'Content-Type': 'application/x-www-form-urlencoded',
            },
            body:`grant_type=password&username=${this.state.username}&password=${this.state.l_password}&client_id=4&client_secret=LT7raDKvPwIUrDFJBISlhpzAXu6cSYiLBGhrUmTm&scope=*`

         }
      )
      .then(response =>
         response.json()

      )
      .then(responseJson => {
          const returnObj = responseJson;
          console.log(returnObj);
          sessionStorage.setItem('resData', JSON.stringify(returnObj));
          console.log(this.state.redirect);
          if(this.state.redirect === true){
               return (
                   <Router><Route path="/dashboard" component={Dashboard} /></Router>
               );
           }
           else{
            <Redirect to="/" />
           }

      });

        this.setState({
            username: '',
            l_password:''
        });
}

The form

 <Form onSubmit={this.handleLogin}>
                                <Form.Group controlId="formBasicEmail">
                                    <Form.Label>Email address</Form.Label>
                                    <Form.Control type="email" placeholder="Enter email"
                                     autofoccus="true"
                                     autoComplete="new-email"
                                     onChange= {this.ChangeText}
                                     name="username"
                                     value={this.state.username}
                                    />
                                </Form.Group>

                                <Form.Group controlId="formBasicPassword">
                                    <Form.Label>Password</Form.Label>
                                    <Form.Control type="password" placeholder="Password" autoComplete="new-password"
                                     onChange= {this.ChangeText}
                                     name="l_password"
                                     value={this.state.l_password}
                                    />
                                </Form.Group>

                                <Button
                                onClick={this.setRedirect.bind(this)}

                                variant="primary" type="submit" size="lg" block>
                                    Login
                                </Button>
                                <Form.Group controlId="formBasicChecbox">
                                    <Form.Check type="checkbox" label="Remember" />
                                   <a href="#" style={{float:'right', marginTop:-23}}>Forgot Password?</a>
                                </Form.Group>
                                <div id="error"></div>
                                <div className="clear-fix"></div>
                                <hr/>

                            </Form>

What I intend to achieve is to redirect the page to dashboard if redirect is true otherwise the home

enter image description here

4 Answers 4

1

First, import withRouter to your react-router-dom, then add this.props.history.push('/dashboard') to your handleLogin function after you have satisfied the conditions for login.

handleLogin =(event) =>{
      event.preventDefault();

      fetch('/oauth/token',
         {
            method: "POST",
            headers:{
                'Accept': 'application/json',
                'Content-Type': 'application/x-www-form-urlencoded',
            },
            body:`grant_type=password&username=${this.state.username}&password=${this.state.l_password}&client_id=4&client_secret=LT7raDKvPwIUrDFJBISlhpzAXu6cSYiLBGhrUmTm&scope=*`

         }
      )
      .then(response =>
         response.json()

      )
      .then(responseJson => {
          const returnObj = responseJson;
          console.log(returnObj);
          sessionStorage.setItem('resData', JSON.stringify(returnObj));
          ....
          this.props.history.push('/dashboard')

      });


}

At the end of the class, add export default withRouter(name of your class)

For more reading, check out this tutorial. enter link description here

Sign up to request clarification or add additional context in comments.

Comments

0

I guess it's the onclick that fires when it's too late ? Try to set it true at the beginning of your method handleLogin

handleLogin = (event) => {
    event.preventDefault();

    this.setState({
      redirect: true
    });     

    fetch('/oauth/token',... 

Comments

0
class App extends Component {render() {
return (
  <div>
    <NavBar />
    <div className="content">
      <Switch>
        <Route path="/products/:id" component={ProductDetails} />
        <Route
          path="/products"
          render={props => <Products sortBy="newest" {...props} />}
        />
        <Route path="/posts/:year?/:month?" component={Posts} />
        <Redirect from="/messages" to="/posts" />
        <Route path="/admin" component={Dashboard} />
        <Route path="/not-found" component={NotFound} />
        <Route path="/" exact component={Home} />
        <Redirect to="/not-found" />
      </Switch>
    </div>
  </div>
);}}

Check this code. On a project I made, I used react router dom.

import it with the following code :

import { Route, Switch, Redirect } from 'react-router-dom';

I suggest you read more about Routing, Mosh Hamedani does great tutorials on youtube and on his website :)

Comments

0

https://reacttraining.com/react-router/web/api/Redirect

Do not return Route component in your setRedirect function.

Create a Route in your app and set state e.g. shouldRedirect at the end of you setRedirect calls e.g.

.then(responseJson => {
  const returnObj = responseJson;
  console.log(returnObj);
  ...
  setState({shouldRedirect: this.state.redirect})
})

<Router>
  <Route exact path="/" render={() => (
    shouldRedirect ? (
    <Redirect to="/dashboard"/>
    ) : (
    <PublicHomePage/>
    )
  )}/>
</Router>

Also you can check nice working example here: https://reacttraining.com/react-router/web/example/auth-workflow

1 Comment

As I said, you cannot return component from promise, try first very basic example with redirection e.g. just simple redirect when clicking a button (no requests to server and so on) and when it will work, start adding your logic

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.