Just the same as reading some global variable that can be changed so that you also might run into those tearing problems. Most of the time you will add another event listener for example for the changes in the store or for changes to some local storage for example. So everything will work out eventually but there might be certain periods of time where your application displaces this teared state.
Before we go into how you can solve these problems, let's first take a look at the second misconception. One render or on reconciliation phase always leads to exactly one commit phase. By default this might be true. We have this reconciliation process that runs through all of our components inside of our application and then when this is done, when we acknowledge what has to be done, it will switch to the commit phase and run the commit and update the DOM for all of our components. Even when we are using concurrent features, we still have the guarantee that the commit phase is atomic. Even if we have those time splits in the reconciliation phase, we have the guarantee that committing is atomic because React team made the decision that they do not want to display inconsistent data. So, they say, whenever we start updating the DOM, we do everything that we currently have to do to update every place that reads the state so that everything is a consistent state.
But now, there are some situations where the one-to-one mapping between reconciliation and commit phase is no longer true. When you are using React strict mode in development, for example, you already have this change that the reconciliation phase will be run twice and the commit phase will only run once. This already warns you in development when those two reconciliation phases yield different results. Because, as we said earlier, when the input is the same, the output should always also be the same. So the strict mode helps you detect when you are using external values that might change outside React. For example, when you are using math.random, React will detect that different reconciliation phases yield different results and warn you. But now, with those concurrent features, we have those slices in between the reconciliation steps. Between each of those steps, something might happen that might make the commit phase obsolete or change the result of the commit phase because some state changed again.
We can take a look at that in our demo application again. Let's first hide our blocks and tick this Show Commits box, and clear the console. Now, let's show our blocks with a high priority update and then directly after that, we hide them again. After that I click on Hide Blocks. We have to wait for all our components rendering, one, two, three, five seconds each. Then we can see that after that process when the rendering is done, we get those commits for every component, and directly after that we get those unmounts. By default you have this guarantee that you are rendering, and when you are done with reconciliation, then your effects will be called in the commit phase, and the unmounts will be called because our elements are directly hidden again. Now let us try the same thing with a low priority update. We show the blocks with a low priority, and directly after that we hide the blocks. What we can see is that React rendered our first block, the first component. After that it yielded to the browser. The browser handled our event.
Comments