Lifecycle 기본 순서
- constructor
- render
- componentDidMount
- (fetch 완료)
- (setState)
- render
- componentDidUpdate (5번에서 setState 되었기 때문에 컴포넌트 업데이트 발생)
- componentWillUnmount
부모 API에서 받은 데이터를 자식에게 props로 전달하여 자식 내부에서 데이터에 접근하여 사용하는 경우
부모 - 자식 Lifecycle 순서
- 부모 constructor
- 부모 render
- 자식 constructor
- 자식 render
- 자식 componentDidMount
- 부모 componentDidMount
- 부모 fetch 완료
- 부모 render
- 자식 render
- 자식 componentDidUpdate
- 부모 componentDidUpdate
너무 많이 봐서 이제는 안나오면 서운하기까지한 그 에러....🥲
말그대로 undefined
에 대하여 map 함수를 실행하려 했다는 소리다. 받아온 data를 배열에 넣어주고 그 배열에 대해 map 함수를 실행하려고 했는데 왜 이런 error가 발생한 것일까...?
분명 배열에 data를 넣어줬다고 생각했는데 왜 map 함수가 실행되는 순간에는 해당 값이 비어있었을까...?
Lifecycle을 다시한번 확인해보자
- constructor
- render
- componentDidMount (fetch -> setState)
- render
- componentDidUpdate (3번에서 setState 되었기 때문에 컴포넌트 업데이트 발생)
다음과 같이 Lifecycle에서는 두번의 render가 실행된다. fetch 함수 실행전에 첫번째 render 함수가 실행되고, 두번째 render 함수는 fetch 함수 실행 후에 호출이 된다.
이 때문에 fetch 함수 실행전 state 안에 데이터가 없는 상태라면 첫번째 render 함수가 실행될 때 서버에서 받아온 데이터를 저장해줄 아무것도 없는 빈배열에 map 함수를 실행시키고 있으므로 타입 에러를 발생시키게 되는 것이다.
이런 경우라면 별도의 조건을 추가해서 state 안에 데이터가 저장되어 있지 않은 경우 렌더링이 되지 않도록 코드를 작성해서 에러를 방지할 수 있다.
조건부 렌더링을 구현하기 위해서는 삼항 연산자
혹은 && 연산자
를 사용할 수 있다.
삼항 연산자
- true/false 에 따라 각기 다른 UI를 렌더링 할때 사용<div> {isLogin ? ( <div> <p>{name}님 환영합니다!</p> <p>현재 보유중인 포인트는 {point}원 입니다.</p> </div> ) : null} </div>
삼항 연산자의 경우 false 일 경우의 값을 반드시 할당해 주어야 하므로 null 값을 입력해 주었다.
&& 연산자
- 조건이 true 일때만 특정 UI를 렌더링하고 false 일때는 아무것도 렌더링 하지 않도록 할때 사용<div> {isLogin && ( <div> <p>{name}님 환영합니다!</p> <p>현재 보유중인 포인트는 {point}원 입니다.</p> </div> )} </div>
&& 연산자를 활용해 줄 경우 true인 경우만 렌더링 하겠다는 의도를 전달하면서 동시에 false 일 경우의 값을 생략할 수 있어서 가독성이 좋아진다.