React history.push() not rendering new component

前端 未结 5 1132
梦谈多话
梦谈多话 2021-01-02 09:31

I have a React.js project with a simple sign in function. After the user is authorized, I call history.push method which changes the link in the address bar but does not ren

相关标签:
5条回答
  • 2021-01-02 09:32

    You need to apply withRouter to use this.props.history.push('/page') in every component that use "push"

    import { withRouter } from 'react-router-dom';
    .....
    export default
            withRouter(MoneyExchange);
    

    this is important when using push.

    0 讨论(0)
  • 2021-01-02 09:33

    Not Working on this one ->

    handleSubmit(event) {
    
        event.preventDefault();
    
        this.setState({ isLoading: true })
    
        const { username, password } = this.state;
        this.props.onLoginRequest(username, password, this.props.history).then(result => {
          console.log("Success. Token: "+result.token); //I do get "success" in console
          this.props.history.push('/servers') //Changes address, does not render /servers component
        });
    
      }
    
    const mapActionsToProps = {
      onLoginRequest: authorization
    }
    

    Because in this handleSubmit method you are calling this.props.history.push() inside a promise so the this is pointing to the Promise's instance not your current class instance.

    Try this One ->

     handleSubmit(event) {
    
        event.preventDefault();
        const { history: { push } } = this.props;
        this.setState({ isLoading: true })
    
        const { username, password } = this.state;
        this.props.onLoginRequest(username, password, this.props.history).then(result => {
          console.log("Success. Token: "+result.token); //I do get "success" in console
          push('/servers') //Changes address, does not render /servers component
        });
      }
    
    const mapActionsToProps = {
      onLoginRequest: authorization
    }
    

    Now In this Statement ->

     handleSubmit(event) {
    
        event.preventDefault();
    
        this.setState({ isLoading: true })
    
        const { username, password } = this.state;
        this.props.onLoginRequest(username, password, this.props.history).then(result => {
          console.log("Success. Token: "+result.token);
          //this.props.history.push('/servers')
        });
        this.props.history.push('/servers')
      }
    

    You are correctly calling this.props.history.push() since it is out of the promise and referring to the Current Class instance.

    0 讨论(0)
  • 2021-01-02 09:35

    Try to use custom history and Router instead of BrowserRouter. After installing history:

    yarn add history
    

    Create a custom browser history:

    import { createBrowserHistory } from "history";
    
    export default createBrowserHistory();
    

    Use Router instead of BrowserRouter in your setup:

    import history from "your_history_file";
    
    ReactDOM.render(
      <Provider store={createStore(mainReducer, applyMiddleware(thunk))}>
        <Router history={history}>
          <Main />
        </Router>
      </Provider>,
      document.getElementById('root')
    );
    

    or if you don't want to use a custom history file and import from there you can crate it directly in your index.js:

    import { createBrowserHistory } from "history";
    
    const history = createBrowserHistory();
    
    ReactDOM.render(
      <Provider store={createStore(mainReducer, applyMiddleware(thunk))}>
        <Router history={history}>
          <Main />
        </Router>
      </Provider>,
      document.getElementById('root')
    );
    
    0 讨论(0)
  • 2021-01-02 09:39

    If anyone is interested - this was happening because the app was rendering before the history was pushed. When I put the history push into my action but just before the result is converted into JSON, it started working since now it pushes history and only then renders the App.

    export const authorization = (username, password, history) => (dispatch) =>
      new Promise ((resolve, reject) => {
        fetch(url, {
          method: 'POST',
          headers: {
            'Content-Type': 'application/json'
          },
          body: JSON.stringify({
            username: username,
            password: password,
          })
        }).then( response => {
          if (response.ok) {
    
              //################################
              //This is where I put it
    
              history.push("/servers");
    
              //################################
    
              response.json().then( result => {
                dispatch(logUserIn(result.token));
                resolve(result);
            })
          } else {
            let error = new Error(response.statusText)
            error.response = response
            dispatch(showError(error.response.statusText), () => {throw error})
            reject(error);
          }
        });
      });
    
    0 讨论(0)
  • 2021-01-02 09:40

    First, create a history object used the history package:

    // src/history.js
    import { createBrowserHistory } from 'history';
    export default createBrowserHistory();
    

    Then wrap it in in Main Router Component.

        import { Router, Route, Link } from 'react-router-dom';
        import history from './history';
    
        ReactDOM.render(
            <Provider store={store}>
              <Router history={history}>
                <Fragment>
                  <Header />
                  <Switch>
                    <SecureRoute exact path="/" component={HomePage} />
                    <Route exact path={LOGIN_PAGE} component={LoginPage} />
                    <Route exact path={ERROR_PAGE} component={ErrorPage} />
                  </Switch>
                  <Footer />
                </Fragment>
          </Router>
        </Provider>)         
    

    Here, After dispatching the request, redirecting to home page.

        function requestItemProcess(value) {
            return (dispatch) => {
                dispatch(request(value));
                history.push('/');
            };
    
        }   
    

    should be helpful :)

    0 讨论(0)
提交回复
热议问题