Reputation: 101
I realize this question has been asked before and this topic has been widely discussed in the Redux community, but I have not seen it approached by this angle: Error messages.
In most examples using React + Redux + some middleware (redux-promise and redux-thunk), external api calls are done inside the action creator. The result of the API call then affects the application state with a success case or error case.
My counter-argument:
The main interested party in the results of an API call is a component, particularly because it's the one that has to often show an error message to the user. Error messages are best set as component state. It's easier to "clean up" on componentWillMount
. No need to create an action just to clean up an application level error state.
All API call's should be made from a component and it should decide what action creator to call. Action creators then become JUST that, functions that return objects. No side-effects in them.
Again, I stress that this "take" is based on the fact that most of the time, a component will need to handle error messages anyways. So why not call the api and deal with the error right there? Things go ok, call an action creator. Things go bad, show an error. Also, I don't think there will be duplication of API calls across the application. After all, React tries to enforce modularization and top-down flow of data. Two different components really shouldn't be calling the same api. They could call the same action creator though and that's fine. Think sign up and sign in. Different api endpoints. Same final state (authenticated: true
)
Anyway, this is my view on it. I'm hoping that someone with more experience will answer if API calls inside components are a good idea. Thank you.
EDIT: Just created this post on medium, which hopefully explains my argument better
Upvotes: 3
Views: 2214
Reputation: 7209
Kind of too open ended to come up with a "solution" but here's a short answer.
First off, what do you mean it's easier to clean up on componentWillMount
? Many times api calls are done on an already mounted component like a sign up or login component. The API call happens when the button is clicked, not when it's mounted.
Also, the main reason why API calls are done outside React components (assuming you have a data handling framework like redux) is that the library is used as a View layer. A component renders HTML that declaratively reflects the state of your application. When a login API call fails to authenticate, the application state is what changes, and as a result the View. If you start to handle API responses in your component, you may run into issues with out of sync state.
For example, the user logs in 10 times with the wrong credentials and gets "locked out". How do you handle that error? You'll likely add some logic to handle those errors. And what if other parts of the app need to react to this error? Now you start to fire actions based on those errors and essentially go back to making your API calls entirely from an action creator, which happens to live in your component.
Now, this mostly applies to large applications. It's perfectly reasonable to handle API calls in a component if the application is small enough and state management frameworks like redux just add bloat. If it's a large application, however, I still highly recommend keeping API logic in the action creators.
Upvotes: 5