React Hook "useMemo" is called conditionally. React Hooks must be called in the exact same order in every component render. Did you accidentally call a React Hook after an early return?
다음과 같은 에러는 useMemo 뿐만 아니라 useEffect 등 hooks를 사용할 때도 동일하게 적용된다.
해당 에러가 뜨는 이유는
난 이렇게 두가지의 내적 외침이 있었다.
그래서 코드를 보며,
내부에 선언된 조건문이 문제일리는 없는데,, 흠..
하며 전에 짰던 코드를 뒤적거렸다.
역시 내부 조건문이 문제일리는 없었다.
그렇다면 어떤 이유에서 해당 에러가 발생했을까?
const Container = () =>{
const { data, error } = useSelector((state) => state.accounts.accounts);
...
if(error){
return(
<ERR>에러가 발생했습니다.</ERR>
)
const TableRenderer = useMemo(()=>{<Table/>},[]);
return (
{TableRenderer}
)
}
}
내 코드는 위와 같은 상황이었다.
위와 같은 상황에서는 에러가 발생한다.
hook이 선언되기 전에
조건절로 Container의 return이 발생하기 때문이다.
Did you accidentally call a React Hook after an early return?
에러 메시지에서도 친절히 안내 해준다.
위 코드는 아래와 같이 바꿔줘야 한다.
const Container = () =>{
const { data, error } = useSelector((state) => state.accounts.accounts);
...
const TableRenderer = useMemo(()=>{<Table/>},[]);
...
if(error){
return(
<ERR>에러가 발생했습니다.</ERR>
)
return (
{TableRenderer}
)
}
}
리액트는 Hook이 호출되는 순서에 의존하기 때문에 Hook의 실행순서가 밀리게 되거나 건너뛰면 버그를 야기한다.
만약 조건부로 Hook을 쓰고 싶다면 Hook 내부에 선언해야 한다.
훅을 일반적인 자바스크립트 함수에서 호출하면 안된다.
대신 리액트 함수 컴포넌트나 커스텀 훅에서는 호출이 가능하다.