우리 팀은 컴포넌트를 만들어서 조합하는 방식인 컴포넌트 주도 개발 방식을 택했는데, 나에게 주어진 첫번째 컴포넌트는 사용자의 짧은 답변을 받는 부분에서 사용될 Input 컴포넌트였다.

공통 컴포넌트를 처음 만들어보면서 겪었던 과정을 적어보며 공통 컴포넌트는 어떻게 구성하면 좋을지에 대해 적어보려고 한다.

내가 처음에 만들었던 Input 컴포넌트는 아래와 같이 사용했어야 했다.

      <Input
        value={value}
        setValue={setValue}
        onChange={handleInputChange}
        placeholder="내용을 입력하세요."
        errorMessage="* 오류입니다."
        maxTextLength={15}
        isError={isError}
        setIsError={setIsError}
      />

우리 프로젝트에서 대부분 input이 글자 수를 체크하는 과정을 포함하고 있었기 때문에, Input 컴포넌트 안에 제한 글자 수를 지정하는 maxTextLength와 글자 수를 체크할 수 있는 함수 handleInputChange를 기본으로 지정해뒀다. 그리고 지정해둔 글자 수가 넘어가면 글자 수를 잘라야 했기 때문에 set 함수인 setValue를 받아왔고, 유효성 검사 등 다른 에러 처리를 위해 errorMessage, isError, setIsError 까지 받아왔다.

지금보니 굉장히 복잡하다고 느껴지지만, 그때는 어찌저찌 만들어 냈으니까 이게 된 건가보다! 생각하고 PR을 올렸는데, 그대로 웹 오빠들한테 뚜까 맞았다.

이 Input 컴포넌트가 왜 문제인지? 피드백을 정리해보자면,

1️⃣ Input 컴포넌트 내부에서 value 값을 지정하고 관리하는 로직은 🙅🏻‍♂️

input에 공통 컴포넌트 value와, 외부에서 사용하는 부분에서 지정해주는 value가 있다는 것은 하나의 input에 주어지는 상태가 2개인 것은 문제가 생길 수 있다. 하나의 value로 관리가 될 수 있도록 수정해야 한다.

2️⃣ set 함수를 직접 받아서 Input 컴포넌트에서 조작하는 과정도 🙅🏻‍♀️

set 함수를 직접 전달한다는 것은, Input 컴포넌트에게 데이터 변경 주도권을 넘긴다는 뜻. 컴포넌트는 독립적이고 재사용성있게 만들어야 한다고 주구장창 들어왔는데, 컴포넌트가 다른 컴포넌트에게 종속된다는 건 컴포넌트가 컴포넌트답지 못하게 되니까 set 함수를 직접 넘겨주기보단, 그 함수를 감싸는 함수를 만들어서 넘겨주는 방식으로 수정해야 한다.