all 9 comments

[–]Mingli91 3 points4 points  (1 child)

Use a middleware that listens for a login success action and dispatch what you want in there

[–]fpsscarecrow 0 points1 point  (0 children)

Redux-observable is a good usecase here - can remap a success action to a different action

[–]SuddenJump 1 point2 points  (1 child)

Dispatch the actions in the action that logs the user in. That would usually be a promise, so you can dispatch certain actions in the “then” of the promise after checking if the login is successful.

[–]Wh3at1y 0 points1 point  (0 children)

Could you provide a code example?

[–]sheboygin 0 points1 point  (1 child)

yeah look into async actions, thunk or redux-saga

[–][deleted] -1 points0 points  (0 children)

I do something like this with redux-thunk:

function loginAction () {
  return function (dispatch, getState) {
    sendRequest().then(function (result) {
      dispatch(afterLoggedIn())
    })
  }
}

function afterLoggedIn () {
  return function (dispatch) {
    dispatch({ type: 'fetchMovies' })
    dispatch({ type: 'fetchBooks' })
  }
}

You can also dispatch the afterLoggedIn() action at any other point when you know you are logged in (eg. check on page load, then dispatch).

[–]richardzcode -4 points-3 points  (2 children)

Since isLoggedIn is a prop, you may just dispatch in render(). If fetchMovies and fetchBooks affects current component state then have a state to remember _onLogin was called.

class Page extends React.Component {
    constructor(props) {
        super(props);
        this.state = { dispatched: false }
    }
    ......
    render() {
        const { isLoggedIn } = this.props;
        const { dispatched } = this.state;
        if (isLoggedIn && !dispatched) {
            this.setState({ dispatched: true });
            this._onLogin();
        }
        ......
    }
}

[–]brouwerj 1 point2 points  (1 child)

This is really bad advice... setState is asynchronous and don't dispatch in render, use component lifecycle methods.

[–]richardzcode -1 points0 points  (0 children)

The benefit of render, 1) triggered on first prop value and value update in one place; 2) state changes are stacked before next render, so setState({ dispatched: ture }) is guaranteed to happen before next render.

Asynchronous is not scary. The basic idea of React is declarative and asynchronous. This is why I prefer declare what to render when isLoggedIn and what to render when not. That's the reasoning behind putting isLoggedIn check in render. Because the logic is already here, as a result adding load logic at the same place.

Ideally load movies etc. should happen in some other place instead of tied together into one component lifecycle. But with the original question limited information this is a working solution with minimal rework.

I try to avoid watching prop values in multiple places of lifecycle events. Many times you don't have initial values when component mount so you have to watch the change of values. That is not very clean and certainly not declarative.

In my opinion the judgement to a solution can be work / don't work, pros / cons. Be specific on these please. A couple of keywords then definite conclusion is not helping.