1

Weird behavior in React.js. When I am passing some randomly generated value in props. It is giving a different output in console logs.

While I debug it is again going back to App.js (Parent) and check its value but consoles are just 2, not 4.

What I am missing in react lifecycle or something here?

// App.js
function App() {
  const rand = Math.random();
  console.log(rand);
  return (
    <div className="App">
      <Board rand={rand} />
    </div>
  );
}

export default App;
// Board.js
function Board({ rand }){
    console.log(rand);
    return(
        <div className="Board"></div>
    );
}
export default Board;

Here is the github repo: git@github.com:senseihimanshu/minesweeper.git

Please check App.js and Board.js for further clarification and verify in console of dev tools that both the array are not same... This is the problem.

Himanshu Sharma
  • 511
  • 5
  • 12
  • You are console logging as an unintentional side-effect instead of when the components ***actually*** render to the DOM. Use an `useEffect` to correctly log passed/updated prop values. You are also generating the random value in `App` as an unintentional side-effect. What are you really trying to do? – Drew Reese Feb 21 '21 at 19:59
  • Can't reproduce - can you clarify the problem please? https://stackblitz.com/edit/react-c2w4ay?file=src%2FApp.js – Randy Casburn Feb 21 '21 at 20:01
  • Can you please explain the term unintentional side-effect? And life-cycle in this case. @DrewReese – Himanshu Sharma Feb 21 '21 at 20:04
  • Sure. Study this [Lifecycle Diagram](https://projects.wojtekmaj.pl/react-lifecycle-methods-diagram/). The entire function body of a functional component is the "render" function. When you do a side-effect like compute a random number or console log in the body you are doing so during the "Render Phase" which ***should not*** be conflated with the component being rendered to the DOM during the "Commit Phase". React may "render" the component any number of times to compute the "diff" from the last result rendered to the DOM. – Drew Reese Feb 21 '21 at 20:08
  • @RandyCasburn I understand. But it's happening in my case. https://codesandbox.io/s/red-fog-34gef see a similar type of code the nested board array is different in this case – Himanshu Sharma Feb 21 '21 at 20:09
  • Can you just update your question with the code you have issue with, and clarify *what* the issue is? – Drew Reese Feb 21 '21 at 20:12
  • Trying to understand this: "_But it's happening in my case._" - So you see the odd behavior in the StackBlitz that uses the exact code you provided in the question? – Randy Casburn Feb 21 '21 at 20:31
  • @DrewReese RandyCasburn This behavior is in my system environment as well. I have updated the question for your ref. – Himanshu Sharma Feb 22 '21 at 06:59
  • @RandyCasburn you can change array with [Math.random()] in App.js and you will get same beavior. – Himanshu Sharma Feb 22 '21 at 07:01
  • 2
    I looked into it a little bit , here are my conclusions 1. React.StrictMode is affecting this behaviour somehow (https://codesandbox.io/s/elegant-ellis-glhq7?file=/src/index.js) , the logs are always different , but the rendered number is same, strict mode is enabled here. 2. In this example (stackblitz.com/edit/react-c2w4ay?file=src%2FApp.js ) , strict mode is not anabled and everything is working as expected. Strict mode should behave like this , and I still don't understand the behaviour. Opened and issue here : https://github.com/facebook/react/issues/20857 – sidhant manchanda Feb 22 '21 at 08:49
  • Does this help answer your question? https://stackoverflow.com/questions/61053432/react-usestate-cause-double-rendering – Drew Reese Feb 22 '21 at 16:30

1 Answers1

3

React.StrictMode renders 2 times to detect side effects in development mode

React 17 swallows some console.logs during second render , this happens only when strict mode is enabled https://github.com/facebook/react/issues/20090#issuecomment-715926549

Code ref: https://github.com/facebook/react/blob/7cb9fd7ef822436aef13c8cbf648af1e21a5309a/packages/react-reconciler/src/ReactFiberClassComponent.old.js#L170

how to Solve https://github.com/facebook/react/issues/20090#issuecomment-715927125

The view will be consistent though, better use a useEffect and calculate the value once on render.