0

In my react-redux application, I have an action creator which makes 4 server calls, first three calls are made async and then last one waits on the response of 3rd call.

Lets us say someone changes the route before response of 3rd came, 4th call wont be made. How can I ensure this does not happen?

Either I should not allow route change until actioncreator has done its job (users won't like this). Or, I should allow 4th call to happen even if the route is changed, looks like a reasonable solution from users perspective. I don't know how to code any of the solution, please opine.

Note: Route change can happen from navigation bar on the top.

ThinkGeek
  • 4,749
  • 13
  • 44
  • 91
  • Are you using any library like thunk/saga, etc to make server calls? If not, I would suggest you to have a look at redux saga since it would simplify async calls and your case can be easily solved using saga effects. (although initial learning curve would be a bit tough). – codeslayer1 Sep 14 '17 at 17:11
  • I already use saga, but I am not aware of saga effects. – ThinkGeek Sep 14 '17 at 17:12
  • I am not sure if I understood your question correctly. Do you want to know the code to execute 3 calls in parallel and 4th call to wait for 3rd call to finish? Or do you want to know how to stop your user from changing route when a call is running? (This can be easily prevented by showing a progress dialog to user while your api call is running) – codeslayer1 Sep 14 '17 at 17:21
  • I want to know how to stop user from changing route when a call is running – ThinkGeek Sep 14 '17 at 17:23
  • `function doSomething { dispatch(A()); dispatch(B()); dispatch(C()); dispatch(D()); }` – ThinkGeek Sep 14 '17 at 17:24
  • In that case, you can show a progress dialog or some overlay to the user as soon as your 1st call starts and once all 4 calls are made, you can dismiss the dialog. If you want, I can share the code to implement a non dismissible loading overlay. – codeslayer1 Sep 14 '17 at 17:26
  • That would really help, thanks :). But I am not sure whether it will be a good idea to block user from navigating. Can't we just allow user to navigate to different route and make sure calls are also happening without any side effect? – ThinkGeek Sep 14 '17 at 17:28
  • Let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/154470/discussion-between-lokesh-agrawal-and-codeslayer1). – ThinkGeek Sep 14 '17 at 17:30

2 Answers2

1

Method 1 -

If you want to show a non dismissible overlay to the user while your API call is running, you can do so like this -

//You can pass a prop like isShown to toggle the visibility, Here Modal component is used from **react-bootstrap** library
//backdrop and keyboard false prop means it's non dismissible
<Modal className="loader" show={this.props.isShown} backdrop={false} keyboard={false}>
    <Modal.Body className="text-center">
      <div><img className="loader-image" src="https://d1ykm90fp7q29d.cloudfront.net/assets/images/misc/loader.gif"/>
      </div>
      <br/>
      <h2> Loader text </h2>
    </Modal.Body>
</Modal>

You can create a separate Modal component like above and import it where you want to use it. Visibility can be toggle by any state variable which is accessible in your api call.

Method 2 - Ideally, even if your route changes, it should not effect your action and action creators and your async api calls should run as it is. You may have not implemented the api calls properly. You can use redux saga like this -

Pseudo Code:

//Main saga
function* mainSaga(params){
  const [result1, result2, result3]  = yield all([
    call(apiCall1, params1), //function apiCall1 should call your Api1 
    call(apiCall2, params2),
    call(apiCall3And4, params3And4) //apiCall3And4 is another saga which is implemented below
  ])
}

//apiCall3And4 saga
function* apiCall3And4(params){
  const call3result = yield call(apiCall3, params3);
  if(call3Result != null){
    //call api 4
    yield call(apiCall4, params4);
  }
}
codeslayer1
  • 3,666
  • 3
  • 17
  • 13
0

You can choose one of this:

  • React Router (v4) supports preventing transitions
  • Full client-side React App will do background calculations by default (it's called state of application).

Also you could use server-side rendering to prefetch data from API.

Grzegorz Gajda
  • 2,424
  • 2
  • 15
  • 23
  • React Router (v4) supports preventing transitions, it will just prevent not enforce. – ThinkGeek Sep 14 '17 at 17:22
  • Full client-side React App will do background calculations by default (it's called state of application). I don't know what do you mean by this. – ThinkGeek Sep 14 '17 at 17:22
  • When you switch between routes (using React Router) you still have persisted store. That means, React Router just change rendered DOM and path in navigation, not refresh your whole application. So if you fire Ajax call, it will be fetching in background until guest refresh your application. – Grzegorz Gajda Sep 14 '17 at 17:24
  • I checked this, but this does not happen. If 4th call has not started yet and is waiting on 3d to complete, and I changed the route then 4th call is not made. – ThinkGeek Sep 14 '17 at 17:26