codeSandBox로 react를 공부하는 중에 함수형 컴포넌트를 생성하여 컴포넌트가 몇 번 호출되는지 확인하기 위해 console을 찍어보았더니, 2번씩 찍히는 현상을 발견했다.
// index.js
import React, { StrictMode } from "react";
import { createRoot } from "react-dom/client";
import "./styles.css";
import App from "./App";
const root = createRoot(document.getElementById("root"));
root.render(
<StrictMode>
<App />
</StrictMode>
);
state를 props로 전달하는 과정에서 에러가 있는지 확인하기 위해 하위 컴포넌트의 코드를 다르게 작성했다.
// App.js
import { useState } from "react";
function MyButton(props) {
// console이 왜 두 번 찍히지?
console.log(props);
return <button onClick={props.onClick}>{props.count}</button>;
}
export default function App() {
const [count, setCount] = useState(0);
function handleClick() {
setCount(count + 1);
}
return (
<>
<h1>Counter</h1>
<MyButton count={count} onClick={handleClick} />
</>
);
}

// App.js
import { useState } from "react";
function MyButton() {
const [count, setCount] = useState(0);
// console이 왜 두 번 찍히지?
console.log(count, setCount);
function handleClick() {
setCount(count + 1);
}
return (
<>
<p>{count}</p>
<button onClick={handleClick}>click!</button>
</>
);
}
export default function App() {
return (
<>
<h1>Counter</h1>
<MyButton />
</>
);
}

CodeSandbox에서 발생하는 것인지 확인하기 위해 Create React App으로 react 애플리케이션을 생성해서 동일한 방식으로 코드를 작성했다. 결과는 codeSandbox와 동일하게 console이 두 번 찍혔다.

index.js에서 render시 <StrictMode>를 제거하니 콘솔에 기대하던 모습으로 console이 한번만 찍혔다.
react 함수는 버그를 일으키거나 예측이 불가능할 수 있기 때문에 React는 Strict 모드를 지원한다. <StrictMode>와 </StrictMode> 사이에 react 컴포넌트를 작성하면, 오류 검사하기 위해 렌더링 단계에서 의도적으로 함수를 두 번 호출한다고 한다.
React는 사용자의 상호작용이 일어나지 않으면 렌더링 단계에서 어떠한 결과도 변경되지 않는다. 따라서 StrictMode는 초기 렌더링이 끝난 후 함수를 한번 더 호출하여 결과값에 변화가 있는지 확인하고, 그 변화로 오류를 감지할 수 있다.
To help you find accidentally impure code, Strict Mode calls some of your functions (only the ones that should be pure) twice in development. This includes:
- Your component function body (only top-level logic, so this doesn’t include code inside event handlers)
- Functions that you pass to
useState,setfunctions,useMemo, oruseReducer- Some class component methods like
constructor,render,shouldComponentUpdate(see the whole list)Fixing bugs found by double rendering in development - beta.reactjs.org
예를 들어, 순수 함수를 지향하는 React에서 비순수함수로 작성된 컴포넌트가 있다면 Strict Mode가 초기 렌더링이 끝난 이후에 함수를 한번 더 호출하여 동일 컴포넌트임에도 불구하고 반환하는 값이 다르게 나오는 것을 감지 할 수 있다. 순수 함수 검사에 대한 자세한 내용은 React 베타 문서에서 확인할 수 있다.
💡 StrictMode는 개발 환경에서만 이중 호출되고 베포 단계에서는 영향을 끼치지 않으니, 마음 편하게 사용하자. console이 두 번 찍히는 것이 거슬리면 를 제거하면 제거할 수는 있다. 하지만, 개발과정에서 오류를 감지하기 위한 좋은 기능이니 그냥 적용하는 것이 좋은 듯 하다!