[250123] 그대로 나눴는데 뭐가 문제니?

김경민·2025년 1월 23일

TIL

목록 보기
25/64

어제 React에서 제작해보는 CRUD 기능에 관련하여 제작해 보았습니다. 그런 후 컴포넌트 분리를 하였죠.

이 TIL 글은 그 과정에 일어났던 일을 적습니다.

컴포넌트 분리

오늘은 컴포넌트 분리에 집중을 하였습니다.
App.jsx에 들어있는 컴포넌트들을 파일별로 정리하였습니다.

컴포넌트를 분리하는 이유는 React 프로젝트에서 코드의 재사용성과 가독성을 높이는 작업입니다.

이러한 특성을 살리지 못하는 컴포넌트 분리는 잘못된 분리라고 할 수 있습니다.

직접 겪었던 문제에 대해 몇 가지 적겠습니다.

Props Drilling

컴포넌트를 과도하게 분리하여 불필요한 props를 과다하게 전달하는 프롭스 드릴링 문제입니다.

이는 최상위 부모 컴포넌트에 모든 상태를 관리할 때에 생기는 현상입니다.

App
├── Title (제목 컴포넌트)
└── Content
    ├── CountryInput (국가 이름 입력)
    ├── MedalInput (금메달 입력)
    ├── MedalInput (은메달 입력)
    ├── MedalInput (동메달 입력)
    ├── Buttons (등록 및 업데이트 버튼)
    └── ListCountry
        ├── CountryName (국가 이름 렌더링)
        └── MedalQuantity (메달 수량 렌더링)

첫 컴포넌트 분리 후 구조입니다.
처음 분리를 하였을 때에 Content 내부에 쓰이는 Input들에서 입력된 값을 state로 상태 관리하여 값을 App까지 전달하였습니다.

그런 후 App에서 관리하고 있던 state를 과다 전달하는 프롭스 드릴링이 일어나고 있었습니다.

이를 고치고자 Content 내부에서 Input에 입력된 값을 관리하는 state를 지정하여 상태 관리가 사용되는 해당 컴포넌트에 인자를 종속시켜 불필요한 props 전달을 해소하였습니다.

컴포넌트 분리 실패

위의 구조를 보면 알 수 있듯 App 컴포넌트는 사실상 의미가 없는 컴포넌트 분리입니다.

const App = () => {
return (
<>
  <Title />
  <Content />
</>
)}

이 코드처럼 App 컴포넌트는 props 전달도 없고 한 눈에 프로젝트가 보이지도 않고... 의미 없는 분리이자
Content 컴포넌트 안에 책임을 다 몰아 넣은 대표적인 분리 실패 예시입니다.

이렇게 되면 코드의 재사용성이 없어질 뿐만 아니라, Content 내부에 모든 기능이 몰려 유지보수가 어려워집니다.

하여, 튜터님께 리뷰를 받고 n차 분리에 들어가기 시작합니다.

App
├── Content
│   ├── Input (국가 이름 입력)
│   ├── Input (금메달 입력)
│   ├── Input (은메달 입력)
│   ├── Input (동메달 입력)
│   └── Buttons (등록 및 업데이트 버튼)
└── ListCountry
    ├── CountryName (국가 이름 렌더링)
    ├── MedalQuantity (메달 수량 렌더링)
    └── 삭제 버튼

우선, 컴포넌트를 나눌 이유 없던 제목만 가지고 있던 Title 컴포넌트도 한 줄의 태그로 바꾸고 종류가 여러개 있던 Input 컴포넌트들도 하나의 컴포넌트로 통합 시켜 재사용성을 높였습니다.

그런 후 가장 문제였던 Content 책임 전가 현상은 자식 컴포넌트인 ListCountry를 빼내어 국가 목록을 리스트업하는 작업을 분리 해주었습니다. 그 과정에서 Content와 ListCountry 둘 다 사용하는 국가 목록 객체 배열은 App에서 상태 관리를 해주어 props로 동시에 내려주었습니다.

마무리

이런 과정이 있던 저의 컴포넌트 분리는 마무리가 되었고 최종적으로 이러한 컴포넌트를 유지한 상태로 도전기능 추가까지 완료 되었습니다.

내일은 욕심을 더 부려 객체 내부에 있는 모든 키로 정렬을 할 수 있는 기능을 추가하고, 휴먼 에러로 일어날 잘못된 배열 수정을 Redo, Undo기능까지 구현 해보려고 합니다.

profile
김경민입니다.

0개의 댓글