왜? 무한루프가 도는지?
질문이 있는데 useEffect에서 [post]로 하면 무한 루프가 돌고 저런식으로 [boardSetData,post.postId,post.nttSj,post.nttCn] 으로 놓으면 무한루프가 돌지 않는데 이유를 알수 있을까요 ...
postId는 글번호 nttSj 제목 , nttCn 제목이며
const boardSetData = useContext(BbsSettingContext);
여기서 boardSetData는 게시판 셋팅 데이터 입니다 .왜 무한 루프가 도는지 알수있을까요 .
게시판 셋팅 , 글제목, 글번호 글내용이 바뀌면 useEffect의 axios가 전송 되어야 하게 할려고 합니다 근데 무한 루프가 도네요 ...
import React, { useState, useEffect, useContext, useRef } from "react";
import { useNavigate } from "react-router-dom";
import axios from "axios";
import { BbsSettingContext } from "../common/Board";
import ToastEditor from "../component/ToastEditor";
import MyButton from "../common/ComButton";
const BoardView = ({ postId }) => {
const titleInputRef = useRef();
const contentsAreaRef = useRef();
const toastEditorRef = useRef(); // ToastEditor의 ref
const [post, setPost] = useState({
nttSj: "",
nttCn: "",
regDate: "",
});
const [boardSetting, setBoardSetting] = useState(null);
const boardSetData = useContext(BbsSettingContext);
const Navigate = useNavigate();
const formatDate = (timestamp) => {
const date = new Date(timestamp);
const options = { year: "numeric", month: "long", day: "numeric" };
return date.toLocaleDateString("ko-KR", options);
};
useEffect(() => {
if (boardSetData) {
setBoardSetting(boardSetData);
axios
.get(`http://localhost:8080/board/${boardSetData.bbsId}/post/${postId}`)
.then((response) => {
setPost({
nttSj: response.data.post.nttSj,
nttCn: response.data.post.nttCn,
regDate: response.data.post.regDate,
});
})
.catch((error) => console.log(error));
}
}, [post]);
return (
<div className="BoardView">
<div className="upInfoArea">
<div type="text" name="boardTitle" className="titleDiv">
{post.nttCn}
</div>
<div type="text" name="regId" className="regIdDIv">
{formatDate(post.regDate)}
</div>
</div>
<div className="contentArea">
<div className="contentsText">{post.nttCn}</div>
</div>
<section>
<div className="btnArea">
<MyButton text={"리스트이동"} onClick={() => Navigate(-1)} />
<MyButton text={"수정하기"} type="positive" />
</div>
</section>
</div>
);
};
export default BoardView;
The infinite loop in your useEffect hook is caused by the way you've set its dependency array and the state update logic inside the hook. Let's break down what's happening:
1.Dependency Array with "[post]": When you use "[post]" as a dependency array, it means the "useEffect" hook will run every time the "post" object changes.
2.State Update Inside "useEffect": Inside this "useEffect", you're making an axios call that eventually updates the "post" state with "setPost".
Here's the cycle that causes the infinite loop:
1."useEffect" runs because post changes.
2.Inside "useEffect", an axios call is made.
3.The axios call completes and updates the "post" state with "setPost".
4.The update of the "post" state triggers the "useEffect" again (because "post" is in the dependency array).
5.This cycle repeats indefinitely.
Dependency Array with [boardSetData, postId, post.nttSj, post.nttCn]: When you change the dependency array to [boardSetData, postId, post.nttSj, post.nttCn], the useEffect only runs when:
1."boardSetData" changes (which presumably doesn't happen often or as a result of the axios call).
2."postId" changes (which likely only happens when navigating to a different post).
3."post.nttSj" (title) changes.
4.post.nttCn (content) changes.
Since the useEffect is not directly updating any of these dependencies, it doesn't trigger itself repeatedly.
Recommendation:
To prevent the infinite loop, ensure that the useEffect hook does not update any of the values in its dependency array. In your case, using [boardSetData, postId, post.nttSj, post.nttCn] is the correct approach because you want the useEffect to run when the bulletin board settings or the specific details of the post change, but not every time the post object is updated in any way. This prevents the axios call from triggering a state update that would cause the useEffect to run again, thereby avoiding the infinite loop.
useEffect 후크의 무한 루프는 종속성 배열과 후크 내부의 상태 업데이트 논리를 설정한 방식으로 인해 발생합니다. 무슨 일이 일어나고 있는지 분석해 보겠습니다.
1.[post]를 사용한 종속성 배열: [post]를 종속성 배열로 사용하면 post 개체가 변경될 때마다 useEffect 후크가 실행된다는 의미입니다.
2.useEffect 내부의 상태 업데이트: 이 useEffect 내부에서는 결국 setPost를 사용하여 게시 상태를 업데이트하는 axios 호출을 만들고 있습니다.
무한 루프를 일으키는 사이클은 다음과 같습니다.
1.게시물이 변경되어 useEffect가 실행됩니다.
2.useEffect 내부에서 axios 호출이 이루어집니다.
3.axios 호출은 setPost를 사용하여 게시 상태를 완료하고 업데이트합니다.
4.post 상태가 업데이트되면 useEffect가 다시 트리거됩니다(post가 종속성 배열에 있기 때문입니다).
5.이 주기는 무한정 반복됩니다.
[boardSetData, postId, post.nttSj, post.nttCn]을 사용한 종속성 배열: 종속성 배열을 [boardSetData, postId, post.nttSj, post.nttCn]으로 변경하면 useEffect는 다음 경우에만 실행됩니다.
1.BoardSetData 변경 사항(아마도 자주 발생하지 않거나 axios 호출의 결과로 발생함)
2.postId 변경(다른 게시물로 이동할 때만 발생할 수 있음)
3.post.nttSj(제목)이 변경됩니다.
4.post.nttCn(콘텐츠)이 변경됩니다.
useEffect는 이러한 종속성을 직접 업데이트하지 않으므로 자체적으로 반복적으로 트리거되지 않습니다.
추천:
무한 루프를 방지하려면 useEffect 후크가 종속성 배열의 값을 업데이트하지 않는지 확인하세요. 귀하의 경우에는 [boardSetData, postId, post.nttSj, post.nttCn]을 사용하는 것이 올바른 접근 방식입니다. 왜냐하면 게시판 설정이나 게시물의 특정 세부 사항이 변경될 때 useEffect를 실행하기를 원하기 때문입니다. 그러나 게시물 개체가 변경될 때마다 실행되는 것은 아닙니다. 어떤 방식으로든 업데이트됩니다. 이는 axios 호출이 useEffect를 다시 실행하게 하는 상태 업데이트를 트리거하는 것을 방지하여 무한 루프를 방지합니다.