When reading the redux docs I found this:
Still, you should do your best to keep the state serializable. Don't put anything inside it that you can't easily turn into JSON.
So my question is, what's the benefit of keeping state serializable? Or, what difficulties I may have if I put non-serializable data into store?
And I believe this is not unique to redux - Flux, even React local state suggest the same thing.
To make me clear here is an example. Suppose the store structure is like this.
{
books: {
1: { id: 1, name: "Book 1", author_id: 4 }
},
authors: {
4: { id: 4, name: "Author 4" }
}
}
This should all looks good. However when I try to access "the author of Book 1", I have to write code like this:
let book = store.getState().books[book_id];
let author = store.getState().authors[book.author_id];
Now, I'm going to define a class:
class Book {
getAuthor() {
return store.getState().authors[this.author_id];
}
}
And my store will be:
{
books: {
1: Book(id=1, name="Book 1")
},
...
}
So that I can get the author easily by using:
let author = store.getState().books[book_id].getAuthor();
The 2nd approach could make the "book" object aware of how to retrieve the author data, so the caller does not need to know the relation between books and authors. Then, why we are not using it, instead of keeping "plain object" in the store just as approach #1?
Any ideas are appreciated.
Redux state has to be serializable all the time. Object serialization is the process of converting an object's state to a string from which it can later be restored. So, if you are trying to store a inside the Redux state, you need to serialize them before persisting.
As an app gets large and complex, you might want to store large, bulky data inside your Redux store and access it inside a component. A Redux store doesn't have a limit on the amount of data stored, so you can pretty much use it to store almost anything, including bulky JSON data, data in table form, etc.
Store: It is an object which provides the state of the application. This object is accessible with help of the provider in the files of the project. The only way to change the state inside it is to dispatch an action on it.
Hydrating the state after the store was created, can be achieved by creating a main reducer that can bypass the top level reducers, and replace the whole state. Reducers are functions that get the current state, combine it with the payload of an action, and return a new state.
Directly from the redux FAQs:
Can I put functions, promises, or other non-serializable items in my store state?
It is highly recommended that you only put plain serializable objects, arrays, and primitives into your store. It's technically possible to insert non-serializable items into the store, but doing so can break the ability to persist and rehydrate the contents of a store, as well as interfere with time-travel debugging.
If you are okay with things like persistence and time-travel debugging potentially not working as intended, then you are totally welcome to put non-serializable items into your Redux store. Ultimately, it's your application, and how you implement it is up to you. As with many other things about Redux, just be sure you understand what tradeoffs are involved.
Further reading:
Adding to what @Timo said , If you want to setup relation between 2 states in your state tree and use computed values, reselect
is the best suitable fit for that scenario. It allows to creareselectors
which can be used to define computed states. In your case author
can be created using a selector on top of book
. https://github.com/reactjs/reselect
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With