[React]LifeCycle(생명 주기)

이해용·2022년 10월 10일
0
post-thumbnail

LifeCycle(생명주기)

모든 리액트 컴포넌트에는 라이프사이클(수명 주기)이 존재합니다. 컴포넌트의 수명은 페이지에 렌더링되기 전인 준비 과정에서 시작하여 페이지에서 사라질 때 끝납니다.

리액트 프로젝트를 진행하다 보면 가끔 컴포넌트를 처음으로 렌더링할 때 어떤 작업을 처리해야하거나 컴포넌트를 업데이트하기 전후로 어떤 작업을 처리해야 할 수도 있고, 또 불필요한 업데이트를 방지해야 할 수도 있습니다.

이때는 컴포넌트의 라이프사이클 메서드를 사용합니다. 참고로 라이프사이클 메서드는 클래스형 컴포넌트에서만 사용할 수 있습니다. 함수 컴포넌트에서는 사용할 수 없는데요. 그 대신에 Hooks 기능을 사용하여 비슷한 작업을 처리할 수 있습니다.

라이프사이클 메서드의 이해

라이프사이클 메서드의 종류는 총 아홉 가지입니다. Will 접두사가 붙은 메서드는 어떤 작업을 작동하기 에 실행되는 메서드이고, Did 접두사가 붙은 메서드는 어떤 작업을 작동한 에 실행되는 메서드입니다.

이 메서드들은 우리가 컴포넌트 클래스에서 덮어 써 선언함으로써 사용할 수 있습니다.

라이프사이클은 총 세 가지, 마운트, 업데이트, 언마운트 카테고리로 나눕니다.

  1. 나타날 때 (Mounting)
  2. 업데이트 될 때 (Updating)
  3. 사라질 때 (Unmounting)

출처: http://projects.wojtekmaj.pl/react-lifecycle-methods-diagram/

마운트

DOM이 생성되고 웹 브라우저상에 나타나는 것을 마운트(Mount)라고 합니다. 이때 호출하는 메서드는 다음과 같습니다.

Mount → constructor → getDerivedStateFromProps → render → componentDidMount

  • constructor: 컴포넌트를 새로 만들 때마다 호출되는 클래스 생성자 메서드입니다.
// Class
class Example extends React.Component {
    constructor(props) {
        super(props);
        this.state = { count: 0 };
}

// Hooks
const Example = () => {
    const [count,setCount] = useState(0);
}
  • getDerivedStateFromProps: props에 있는 값을 state에 넣을 때 사용하는 메서드입니다.
// Class
class Example extends React.Component {
  static getDerivedStateFromProps(nextProps, prevState) {
    if (nextProps.value !== prevState.value) {
      return { value: nextProps.value }
    }
    return null
  }
}
  • render: 우리가 준비한 UI를 렌더링하는 메서드입니다.
// Class
class Example extends React.Component {
  render() {
    return <div>컴포넌트</div>
  }
}

// Hooks
const example = () => {
  return <div>컴포넌트</div>
}
  • componentDidMount: 컴포넌트가 웹 브라우저상에 나타난 후 호출하는 메서드입니다.
// Class
class Example extends React.Component {
    componentDidMount() {
        ...
    }
}

// Hooks
const Example = () => {
    useEffect(() => {
        ...
    }, []);
}

업데이트

컴포넌트는 다음과 같은 총 네 가지 경우에 업데이트 합니다.

  1. props가 바뀔 때
  2. state가 바뀔 때
  3. 부모 컴포넌트가 리렌더링될 때
  4. this.forceupdate로 강제로 렌더링을 트리거할 때

이렇게 컴포넌트를 업데이트할 때는 다음 메서드를 호출합니다.

출처: https://thebook.io/080203/ch07/01-02/

컴포넌트는 다양한 이유로 업데이트 될 수 있습니다. 첫째, 부모 컴포넌트에서 넘겨주는 props가 바뀔 때 입니다. 컴포넌트에 전달하는 props의 값이 바뀌면 컴포넌트 렌더링이 이루어집니다. 둘째, 컴포넌트 자신이 들고 있는 state가 setState를 통해 업데이트 될 때입니다. 셋째, 부모 컴포넌트가 리렌더링될 때 입니다. 자신에게 할당된 props가 바뀌지 않아도, 또는 자신이 들고 있는 state가 바뀌지 않아도, 부모 컴포넌트가 리렌더링되면 자식 컴포넌트 또한 리렌더링됩니다.

  • getDerivedStateFromProps: 이 메서드는 마운트 과정에서도 호출되며, 업데이트가 시작하기 전에도 호출됩니다. props의 변화에 따라 state 값에도 변화를 주고 싶을 때 사용합니다.

  • shouldComponentUpdate: 컴포넌트가 리렌더링을 해야 할지 말아야 할지를 결정하는 메서드입니다. 이 메서드에서는 true 혹은 false 값을 반환해야 하며, true를 반환하면 다음 라이프사이클 메서드를 계속 실행하고, false를 반환하면 작업을 중지합니다. 즉, 컴포넌트가 리렌더링되지 않습니다. 만약 특정 함수에서 this.forceupdate() 함수를 호출한다면 이 과정을 생략하고 바로 render 함수를 호출합니다.

// Class
class Example extends React.Component {
  shouldComponentUpdate(nextProps) {
    return nextProps.value !== this.props.value
  }
}

// Hooks
const Example = React.memo(() => {
      ...
  },
  (prevProps, nextProps) => {
    return nextProps.value === prevProps.value
  }
)
  • render: 컴포넌트를 리렌더링합니다.

  • getSnapshotBeforeUpdate: 컴포넌트 변화를 DOM에 반영하기 바로 직전에 호출하는 메서드입니다.

class Example extends React.Component {
  getSnapshotBeforeUpdate(prevProps, prevState) {
    if (prevProps.list.length < this.props.list.length) {
      const list = this.listRef.current
      return list.scrollHeight - list.scrollTop
    }
    return null
  }
}
  • componentDidUpdate: 컴포넌트의 업데이트 작업이 끝난 후 호출하는 메서드입니다.
// Class
class Example extends React.Component {
    componentDidUpdate(prevProps, prevState) {
        ...
    }
}

// Hooks
const Example = () => {
    useEffect(() => {
        ...
    });
}

언마운트

마운트의 반대 과정, 즉 컴포넌트를 DOM에서 제거하는 것을 언마운트(Unmount)라고 합니다.


출처: https://thebook.io/080203/ch07/01-04/

  • componentWillUnmount: 컴포넌트가 웹 브라우저상에서 사라지기 전에 호출하는 메서드입니다.
// Class
class Example extends React.Component {
    coomponentWillUnmount() {
        ...
    }
}

// Hooks
const Example = () => {
    useEffect(() => {
        return () => {
            ...
        }
    }, []);
}

reference
https://ko.reactjs.org/docs/react-component.html
리액트를 다루는 기술
https://thebook.io/080203/
https://kyun2da.dev/react/%EB%A6%AC%EC%95%A1%ED%8A%B8-%EB%9D%BC%EC%9D%B4%ED%94%84%EC%82%AC%EC%9D%B4%ED%81%B4%EC%9D%98-%EC%9D%B4%ED%95%B4/

profile
프론트엔드 개발자입니다.

0개의 댓글