컴포넌트가 렌더링 될 때 특정 작업을 수행할 수 있게 해주는 Hooks인 useEffect에 대해 알아봅시다.


useEffect에서는 총 3개의 LifeCycle API를 구현할 수 있습니다. 그 3개의 메소드는 componentDidMount, componentDidUpdate, componentWillUnmount 입니다. Counter 프로젝트에서 useEffect를 어떻게 사용하는지 알아봅시다. App 컴포넌트를 아래와 같이 수정해주세요.

import React, { useState, useEffect } from "react";
import CountButton from "./components/CountButton";
import Number from "./components/Number";
import styled from "styled-components";

const Wrapper = styled.div`
  margin: 0 auto;
  display: flex;
  flex-direction: column;
  align-items: center;
  width: 100px;
  margin-top: 100px;
`;

const ButtonWrapper = styled.div`
  width: 100%;
  display: flex;
  justify-content: space-between;
  margin-bottom: 50px;
`;

const App = () => {
  const [ number, setNumber ] = useState(0);

  useEffect(() => {
    console.log("useEffect -> componentDidMount");

    return () => {
      console.log("useEffect -> componentWillUnmount");
    }
  }, []);

	useEffect(() => {
		console.log(`componentDidUpdate (number) -> ${number}`);
	}, [number]);

  useEffect(() => {
    console.log("useEffect -> componentDidUpdate");
  });

  return (
    <Wrapper>
      <ButtonWrapper>
        <CountButton onClick={() => setNumber(number + 1)} text="+" />
        <CountButton onClick={() => setNumber(number - 1)} text="-" />
      </ButtonWrapper>
      <Number number={number} />
    </Wrapper>
  );
}

export default App;

이렇게 수정하고 난 다음 브라우저에서 콘솔창을 열고, 버튼을 눌러보세요. 아래와 같이 로그가 출력될 것입니다.

useEffect는 하나의 컴포넌트에서 여러 개 사용 가능합니다.

먼저 첫 번째 useEffect를 살펴보겠습니다. 해당 Hooks에서는 첫 번째 인자로 함수를 받았고, 두 번째 인자로 빈 배열을 받았습니다. 여기서 첫 번째 인자값인 함수는 당연히 특정 시기에 실행될 함수를 말하는 것입니다. 하지만 두 번째 인자값인 빈 배열은 컴포넌트가 처음 렌더링 될 때만 실행하라는 의미를 가집니다. 따라서 이 useEffect는 componentDidMount와 동일한 기능을 가진 것입니다. 그런데 아랫줄에 return 구문이 있습니다. 해당 Hooks에서 두 번째 인자값으로 빈 배열을 받을 때, return 구문의 함수는 componentWillUnmount와 동일한 기능을 가집니다.

두 번째 useEffect를 살펴보겠습니다. 첫 번째 useEffect와의 차이점은 두 번째 인자값으로 비어있지 않은 배열을 받는다는 점입니다. 배열 안에는 state, props 등과 같은 값이 들어올 수 있습니다. 여기서는 number 값을 넣어줬습니다. 만약 배열 안에 어떤 변수가 들어있다면, 해당 useEffect는 그 변수의 값이 변경될 때 함수를 실행시킵니다. 따라서 number값을 변경했을 때, 콘솔창에 기록이 남는 것입니다.

마지막으로 세 번째 useEffect를 살펴보겠습니다. 이 Hooks는 두 번째 인자값이 없습니다. 두 번째 인자값이 없다는 것은 컴포넌트가 업데이트될 때 실행하라는 의미를 가집니다. 따라서 컴포넌트가 리렌더링 될 때 언제든 함수가 실행됩니다.