인프런 커뮤니티 질문&답변
useEffect 안에 setState 사용 시 뜨는 오류
해결된 질문
작성
·
76
0

모달이 닫힐 때 입력 상태(content, images)를 초기화하기 위해 useEffect에서 isOpen을 의존성으로 두고 setContent, setImages를 호출했는데
이 과정에서 "calling setState synchronously within an effect can trigger cascading renders" 경고가 발생했습니다.
useEffect가 외부 시스템과의 동기화를 위한 용도이기 때문에 생기는 오류인지 궁금합니다! 또한 그렇다면 UI 상태 초기화 목적으로 useEffect에서 state를 변경하는 방식은 권장되지 않는 패턴인가요?
그래서 현재는 onClose, onCancel 등 모달이 닫히는 이벤트 시점마다 직접 setContent(""), setImages([])를 호출하는 방식으로 처리하고 있습니다.
답변 2
1
안녕하세요 다하자님 이정환입니다.
결론부터 말씀드리자면, isOpen을 의존성으로 둔 useEffect 안에서 setContent나 setImages로 상태를 초기화하는 방식 자체가 금지되거나 “무조건 나쁜 패턴”은 아닙니다.
다만 이런 방식은 useEffect의 의존성 배열을 잘못 구성할 경우 렌더링이 연쇄적으로 이어지면서 무한 리렌더에 가까운 상황을 만들 수 있는 여지가 있어요. 예를 들어 아래와 같이 사용하게 될 경우 무한 리렌더링을 발생시킬 수 있습니다.
useEffect(
setState(state + 1);
,[state])deps를 isOpen으로만 정확히 제한하고, effect 안에서 isOpen을 다시 바꾸는 등의 작업만 피하면 실질적으로 문제 없이 동작하니 크게 걱정하시지는 않으셔도 됩니다.
만약 경고 메세지를 제거하고 싶으시다면 eslint.config.js 파일에 다음 rules를 추가하시면 됩니다.
"react-hooks/set-state-in-effect": "off",0
안녕하세요, 인프런 AI 인턴입니다. 다하자님.
useEffect 내부에서 setState를 동기적으로 호출할 때 발생하는 경고는, 종종 무한 루프나 불필요한 렌더링을 유발할 수 있는 상황을 방지하기 위해 나타나는 것입니다. useEffect는 외부 시스템과의 동기화를 목표로 하는 훅으로, 의존성 배열이 변경될 때마다 실행되기 때문에, 그 내부에서 setState를 호출하면 상태 변화가 다시 useEffect를 트리거하여 무한 루프가 발생할 수 있습니다.
이러한 오류는 useEffect가 상태 변경과 관련하여 불필요한 연쇄적 렌더를 일으킬 수 있다는 것을 경고합니다. 따라서 UI 상태 초기화 같은 작업을 위한 목적이라면, 다음과 같은 방법을 고려해볼 수 있습니다:
해결 방안
상태 변경 로직을 특정 이벤트 핸들러 내에서 분리:
- 모달이 닫히는 이벤트(
onClose,onCancel)에서 직접 상태 초기화를 수행하는 방식은 적절합니다. 이렇게 하면useEffect내에서의 상태 변경을 피할 수 있어 적절한 타이밍에 상태를 초기화할 수 있습니다.
- 모달이 닫히는 이벤트(
조건부 로직 추가:
useEffect내에서setState를 사용할 경우, 상태가 변경되어야 하는 명확한 조건을 추가해 unnecessary한setState호출을 피할 수 있습니다.
useEffect사용 시 종속성 관리:useEffect에 의존성 배열을 적절히 설정하여, 특정 상태 변화에만 반응하도록 프로그래밍할 수 있습니다.
관련하여 더 자세히 알고 싶으실 경우 아래 질문들을 확인해 보세요:
- useEffect에서의 setState 사용 시 미치는 영향
- React에서의 상태 관리 및 useEffect 활용 방안
다하자님이 하시는 UI 상태 초기화 방법이 경고 없이 잘 동작한다면, 그것은 적절한 방법으로 보입니다. 모달이 닫힐 때의 시점에만 상태 초기화가 이루어지도록 잘 컨트롤 하셨기 때문에, 이런 상황에서는 useEffect를 사용하지 않는 것이 더 좋은 패턴입니다.
저는 질문자님의 이해를 돕고자 지식공유자님의 기존 답변을 참고하여 유사한 답변 링크를 추천해드리고 있습니다. 현재 베타 기능으로 답변이 만족스럽지 않을 수 있는 점 양해 부탁드립니다. 🙏 추가적으로 궁금한 점이 있으시면, 이어서 질문해 주세요. 곧 지식공유자께서 답변해 주실 것입니다.





넵! 감사합니다