Codesplitting and server-side rendering with redux - reactjs

I'm codesplitting my React+Redux application as described by Dan Abramov here, and everything appears to work fine. However, I'm also rendering the application on the server. This results in console error documented by this answer. However, I'm not attempting to clean up old stateā€”I'm loading the state as the server computed it. The problem is the state from the server gets loaded into the global state before the codesplitted modules are loaded.
If I understand Dan properly, the error is just a warning, and everything appears to function correctly, but it's really not a pleasant development workflow to see errors on nearly every page load.
Is there anything I can/should be doing differently with my codesplitting code to alleviate this? It's nearly verbatim to Dan's example.

The answer was kind of obvious when it hit me. Just like you send the redux state to the client, you need to tell the client which optional reducers need to be included into the combined reducer on creation.
Based on Dan Abramov's work in the linked answer in my question, I changed store.asyncReducers into an array of paths instead of a map of objects. Then I was able to serialize this array and send it to the front-end where it was able to require the async reducers that the server-side render used.

Related

How can I cache Redux states? (without redux-persist)

Problem
I want to save data in the store with Redux, like tokens and user-related data to be used across the whole application (I'm using React).
The problem is that Redux does not persist in the state when refreshing a page.
Thoughts
I'm not convinced about using redux-persist since the package doesn't seem very active.
I've seen RTK Query, but from what I'm understanding, I still have to make the API call to get the data (even if the actual call is not made and gets the cached data). Seems too much of an overkill.
Maybe I'm missing some core Redux or React concept? It feels a bit crazy for me not to be able to find a go-to package (or any other method) just to save a piece of data and be able to access it across the whole application without resetting on refresh :/
try to save your Redux states in localStorage
Redux-persist doesn't need to be very active - it works for half a decade now and there is just no need for a lot of changes. It works.
It is the to-go-package for that purpose.

Is it necessary to keep all the requests in saga or you can have separate modules for requests not related to redux and saga?

As I understand if we make a request by using redux-saga, the response is going to be stored into the redux store. But it is a bad practice to store all the stuff in the redux store. So is it ok to create separate module with API requests and use them when you do not want to put response in redux store ?
I would appreciate articles on this topic (couldn't find it on my own).
Making requests in a file is totally fine in some cases. Just do it carefully in order to prevent interfering with app performance (if a component is rendered multiple time and you need just one request do it in the parent, etc.)
As for articles I couldn't find any to exactly this topic, but react docs have an example of api calls (please ignore the class one and check the hook example bellow). Now I would recommend you too use a service for this to abstract the fetch logic, but the idea is there and, while this cases shouldn't happen a lot, I don't see any reason to avoid this if you only need some data in a specific component and there is no use in saving it to the state .
EDIT:
You have runSaga which according to docs
Allows starting sagas outside the Redux middleware environment. Useful if you want to connect a Saga to external input/output, other than store actions.
So you don't really need another library. Regarding the architectural problem this is what I was trying to emphasis with the react docs. I don't know if there are any articles in this direction (on a quick search I couldn't find any either), but I think for most of the data you want a reducer to prevent unnecessary reloading of the same data.
However there isn't anything suggesting not to do it as far as I know (neither in docs, articles, etc.). Moreover, in some cases, this can a good thing, and the fact that no docs suggest otherwise is a prove in this direction IMO.
PS: Also a discussion about using saga without redux here

React data flow

I am trying to create a blog application and I am a bit confused on the data flow patterns of React.
Should I be trying to use something like Redux to store all of my posts after fetching the posts? Do I use local storage?
How do I then tell a component to render the 'expanded' version of the post? Is it better to re-use a 'post' component or should I just create two seperate components, one for the title and one for the full post?
I know it's two questions in one, but they kind of go together. Thanks in advance
Here's what I've found out about these topics after 6 months into my self-taught React journey.
In my opinion, React built-in features are more than enough to handle state for a small to medium applications (especially if you're working alone as a single developer).
If you turn to Redux right away, you'll have to learn this whole new pattern of handling state in a single immutable store and how to connect your components to it.
Since you will be most likely fetching data asynchronously, you'll need a helper library to work async on Redux: redux-thunk or redux-saga.
So right from the start, you'll have to add:
redux
react-redux
redux-thunk OR redux-saga
That is a lot of documentation to digest. It's perfectly doable, but I couldn't agree more with this quote:
don't solve problems that you don't have
It will be hard to learn those tools, since you've never faced the problems that they solve. Problems that you don't encounter just yet when you're starting to learn React.
Read this (from Redux creator):
https://medium.com/#dan_abramov/you-might-not-need-redux-be46360cf367
So, my recommendation to you:
Learn basic React (with classes):
https://reactjs.org/docs/getting-started.html
Then learn React Hooks (and you can basically forget about class components):
https://reactjs.org/docs/hooks-intro.html
Build your project using only React at first. And see how it goes. Then you can read more about Redux and what it does, and will be able to make a better choice on if you really need it or not.
From what you've told us about your project:
Keep a state for all your posts in a component high in the tree. Maybe inside the <App/> component itself.
Build your functions to fetch and update post data and update the state with the response.
Render how many components as you wish. Displaying full info about the post inside a BlogPostComponent or simplified version inside a BlogPostThumbnailCard with just the thumbnail and the title, for example.
If you want to be ready for the next versions of React and have a shorter code, you should try the hooks and avoid Classes
https://reactjs.org/docs/hooks-intro.html
You can organize your code as you want, but this is more interesting to have scalability with your components and reuse them with different properties

Flux with Alt - Simultaneous dispatches means wrong design pattern?

I build an app with pure React. Its primary page shows multiple movies (user added). Users can vote and comment on every movie listed. I have a MovieCard component, which is responsible for a single movie. Then in Home I render an array of MovieCard components. Next I decided to implement a call to foreign movie database API, to get relevant movie information. It worked fine. Then I decided to refactor it in Flux pattern, using Alt and following the guidelines of this tutorial. Everything worked well, until I got the the MovieCard. In there, inside componentDidMount I call the action, which sends ajax and retrieves a poster url. And I got this error:
Uncaught Error: Invariant Violation: Dispatch.dispatch(...): Cannot dispatch in the middle of a dispatch.
First, I read this topic. The author of the answer claimed that having each component handles its actions is bad design pattern and is what cause the error. His solution would be to handle ALL actions and stores from the top-most component (App) and pass down as props. My thoughts:
I don't like it, because it means passing down a LOT of data and callbacks and my App.js is going to be overly long and ugly and clouded. Lastly I don't know how this is the "React way", where each component is standalone and can work on it's own, out of App context.
I don't see how it fixes the problem. I want my MovieCard to fire action to get data inside componentDidMount. So even if App is handling the actions, when multiple movies are shown, then multiple actions will be fired, again.
Then I read this topic. I don't think I am using actions wrong. Here is my action:
getMoviePoster(movieName) {
TMDB.getMoviePoster(movieName)
.then(data => this.getMoviePosterSuccess(data))
.catch(err => this.getMoviePosterFail(err));
return true;
}
I followed the pattern, showed in the guide I linked above. There were no errors there.
I read through some other topics, there was something about waitFor token, but I couldn't make much of it. Can anyone please shed some light on the issue, because I am in sort of a hurry. I need it done by Tuesday, and I may have a major refactoring on my hands now... I really don't understand what is the problem here. I know Flux is unidirectional, but I thought that's for one component. I'm not guru here, but I can't really see unidirectional flow for the entire application (even this small). I don't see what's the problem of having multiple instances of the same component doing stuff simultaneously.
EDIT: I read again through Alt docs and getting started guide I don't see anything against multiple dispatches. I read about AltContainer, but i'd like to keep my app and structure simple at the moment. In my action constructor I use this.generateActions; in store - this.bindActions(MovieCardActions), which works very well. Except when I have multiple components mounted at the same time. I still can't get the problem.

How to pass large data inbetween components

I am trying to build an react app where i need to pass a JSON of size more than 4MB in between routes / components.
I tried passing as query params in route, the url changes to blank..How can this be done in react.
It's probably not a direct answer but if you are starting a new app I would recommend you to use Redux with react-redux.
Redux is a predictable state container for JavaScript apps.
It helps you write applications that behave consistently, run in different environments (client, server, and native), and are easy to test. On top of that, it provides a great developer experience, such as live code editing combined with a time traveling debugger.
It's very small library so it's easy to understand how everything works. It might be a good solution to your problem.
Todo app example
You can also check out awesome egghead.io free tutorial - Getting Started with Redux
Here is the answer about the redux benefits by its author Dan Abramov

Resources