- 모든 리액트컴포넌트에는 : 라이프사이클(수명주기) 존재
- 컴포넌트수명 :페이지에 렌더링 되기 전인 준비과정에서 시작하여 페이지에서 사라질 때 끈난다.
- 라이프사이클 메소드 : 클래스형 컴포넌트에만 사용가능
- 함수형 컴포넌트에서는 Hooks 사용하여 비슷한 작업을 처리
18. 라이프사이클 메소드
- 총 9가지이다.
- Will 붙은 메소드 : 어떠한 작업을 작동하기 전에 실행되는 메소드
- Did 붙은 메소드 : 어떤 작업을 작동한 후에 실행되는 메소드이다.
- 라이프사이클 3카테고리 1.마운트 2.업데이트 3.언마운트
1.마운트 : 페이지에 컴포넌트가 나타남
2.업데이트 : 컴포넌트 정보를 업데이트(리렌더링)
3.언마운트 : 페이지에서 컴포넌트가 사라짐
(1) 마운트 : DOM이 생성되고 웹브라우저상에 나타나는 것을 말한다.
- 컴포넌트 만들기 > constructor > getDerivedStateFromProps > render > componentDidMount
- constructor : 컴포넌트를 새로 만들 때마다 호출되는 클래스 생성자 메소드이다.
- getDerivedStateFromProps : props에 있는 값을 state에 넣을 때 사용하는 메소드
- render : 준비한 UI를 렌더링
- componentDidMount : 컴포넌트가 웹브라우저상에 나타난 후 호출하는 메소드
(2) 업데이트
- 1. props가 바뀔 때 : 컴포넌트에 전달하는 props값이 바뀌면 컴포넌트 렌더링이 이루어진다.
- 2. state가 바뀔 때 : 컴포넌트 자신이 들고 있는 state가 setState를 통해 업데이트 될 때
- 3. 부모 컴포넌트가 리렌더링 될 때 : 자신에게 할당 된 props가 바뀌지 않아도, 자신이 들고 있는 state가 바뀌지 않아도 부모컴포넌트가 리렌더링 되면 자식컴포넌트 또한 리렌더링 된다.
- this.forceUpdate로 렌더링을 강제로 트리거할 때 컴포넌트가 업데이트 된다.
- 컴포넌트 업데이트할 떄 호출하는 메소드는,
: getDerivedStateFromProps 마운트과정에서도 호출되며, 업데이트가 시작하기 전에도 호출된다. props 변화에 따라 state 값에도 변화를 주고 싶을 때 사용함.
: shouldComponentUpdate 컴포넌트가 리렌더링을 해야할지 말지 결정하는 메소드, 이 메소드는 true 혹은 false 값을 반환하며, true를 반환하면 다음 라이프사이클 메소드를 계속 실행하고, false를 반환하면 작업중지. 즉, 컴포넌트가 리렌더링 되지않는다. 만약 특정함수에서 this.forceUpdate()함수를 호출한다면 이 과정 생략하고 바로 렌더함수를 호출한다.
: render 컴포넌트 리렌더링
: getSnapshotBeforeUpdate 컴포넌트 변화를 DOM에 반영하기 바로 직전에 호출
: componentDidUpdate 컴포넌트의 업데이트 작업이 끝난 후 호출
(3) 언마운트
- 마운트의 반대과정
- 컴포넌트를 DOM에서 제거하는 것
- componentWillUnmount : 컴포넌트가 웹브라우저 상에서 사라지기 전에 호출하는 메소드
19. render()
- 컴포넌트의 모양새 정의, 유일한 필수메소드
- 이 메소드 안에서 this.props 와 this.state에 접근할 수 있고, 리액트 요소를 반환한다. 요소는 div같은 태그가 될 수도 있고 따로 선언한 컴포넌트가 될 수도 있다.
- 아무것도 보이지 않게 하려면 null 값이나 false 를 반환하도록 하면 된다.
- 이벤트 설정이 아닌 곳에서 setState를 사용하면 안되고 브라우저의 돔에 접근해도 안된다.
- DOM 정보를 가져오거나 state에 변화를 줄 때는 componentDidMount에서 처리해야 한다.
20. constructor(){}
- constructor(props) {...}
- 컴포넌트의 생성자 메소드
- 컴포넌트를 만들 때 처음으로 실행된다.
- 초기 state를 정할 수 있다.
21. getDerivedStateFromProps
- props로 받아 온 값을 state에 동기화시킴
- 컴포넌트가 마운트 될 때와 업데이트될 때 호출된다.
static getDerivedStateFromProps(nextProps, prevState) {
if(nextProps.value !== prevState.value) {
return {value: nextProps.value}
}
return null;
}
22. componentDidMount() {}
- 컴포넌트를 만들고 첫 렌더링을 다 마친 후 실행한다. 이 안에서 다른 자바스크립트 라이브러리 또는 프레임워크의 함수를 호출하거나 이벤트 등록, setTimeout, setInterval, 네트워크 요청 같은 비동기 작업을 처리하면 된다.
23. shouldComponentUpdate(nextProps, nextState) {}
- props 또는 state를 변경했을 때 리렌더링을 시작할지 여부를 지정하는 메소드, 반드시 true 또는 false 값을 반환한다. 이 메소드가 false 값을 반환하면 업데이트 과정은 여기서 중지 됨.
- 이 매서드 안에서 현재props와 state는 this.props와 this.state로 접근하고, 새로 설정 될 props 나 state는 nextProps와 nextState로 접근할 수 있다.
- 프로젝트 성능을 최적화할 때 : 상황에 맞는 알고리즘을 작성하여 리렌더링을 방지할 때는 false 값을 반환하게 한다
24. getSnapshotBeforeUpdate 메서드
- 이 메서드는 render에서 만들어진 결과물이 브라우저에 실제 반영되기 직전에 호출
- 반환하는 값은 : componentDidUpdate 에서 세번째 파라미터인 snapshot 값으로 전달 받을 수 있다
- 주로 업데이트하기 직전의 값을 참고할 일이 있을 때 활용된다. (예, 스크롤바 위치 유지)
getSnapshotBeforeUpdate(prevProps, prevState) {
if(prevState.array !== this.state.array) {
const {scrollTop, scrollHeight} = this.list
return {scrollTop, scrollHeight}
}
}
25. componentDidUpdate(prevProps, prevState, snapshot) {}
- 리렌더링 완료 후 실행
- 업데이트가 끝난 직후이므로 돔 관련 처리를 해도 무방하다.
- prevProps 또는 prevState를 사용하여 컴포넌트가 이전에 가졌던 데이터에 접근할 수 있다.
- getSnapshotBeforeUpdate 에서 반환한 값이 있다면 여기서 snapshot 값을 전달 받을 수 있다.
26. componeneWillUnmount() {}
- 컴포넌트를 DOM에서 제거할 때 실행한다.
- componentDidMount 에서 등록한 이벤트, 타이머, 직접생성한 DOM이 있다면 여기서 제거한다.
27. componentDidCatch
- 컴포넌트 렌더링 도중에 에러가 발생했을 떄 애플리케이션이 먹통이 되지 않고 오류UI보여줌
componentDidCatch(error, info) {
this.setState({
error: true
})
console.log({error, info})
}
- error는 : 파라미터에 어떤 에러가 발생했는지 알려주며
- info 파라미터는 : 어디에 있는 코드에서 오류가 발생했는지에 대한 정보를 준다.
- 앞의 코드에서는 그저 콘솔로그만 했지만 나중에 실제 사용할 때 오류가 발생하면 서버 API를 호출하여 따로 수집할 수도 있다.
- 이 메서드 사용시에는 컴포넌트 자신에게 발생하는 에러를 잡아낼 수는 없고 자신의 this.props.children으로 전달되는 컴포넌트에서 발생하는 에러만 잡아낼 수 있다.
import React, {Component} from 'react';
class LifeCycleSample extends Component {
state = {
number: 0,
color: null
}
myRef = null;
constructor(props) {
super(props);
console.log('constructor');
}
static getDerivedStateFromProps(nextProps, prevState) {
console.log('getDerivedStateFromProps')
if(nextProps.color !== prevState.color) {
return {color: nextProps.color}
}
return null
}
componentDidMount() {
console.log('componentDidMount')
}
shouldComponentUpdate(nextProps, nextState) {
console.log('shouldComponentUpdate', nextProps, nextState)
return nextState.number % 10 !== 4
}
componentWillUnmount() {
console.log('componentWillUnmount')
}
handleClick = () => {
this.setState({
number: this.state.number + 1
})
}
getSnapshotBeforeUpdate(prevProps, prevState) {
console.log('getSnapshotBeforeUpdate')
if(prevProps.color !== this.props.color) {
return this.myRef.style.color;
}
}
}
* 라이프사이클 메서드는 컴포넌트 상태에 변화가 있을 때마다 실행하는 메서드이다. 이 메서드들은 서드파티 라이브러리를 사용하거나 돔을 직접 건드려야하는 상황에서 유용하다. 추가로 컴포넌트 업데이트의 성능을 개선할 때는 shouldComponentUpdate가 중요하게 사용됨.