Article

바퀴를 재발명하지 않기

5분
바퀴를 재발명하지 않기

나는 왜 바퀴를 깎고 있었나

프론트엔드 개발자라면 한 번쯤 겪는 강박이 있다. 바로 '최적화''통제권'에 대한 욕망이다.

npm install 한 번이면 해결될 일이지만, 그 거대한 라이브러리가 내 작고 소중한 프로젝트의 번들 사이즈를 부풀리는 것을 참을 수 없다. "나는 딱 요만큼의 기능만 필요한데, 왜 100가지 기능이 들어있는 무거운 라이브러리를 써야 하지?" 그래서 나는 자주 바퀴를 재발명했다.

이유는 그럴듯했다.

  • 필요한 기능만 포함되기 때문에 가볍다.

  • 내 마음대로 커스터 마이징이 가능하다.

  • 밑바닥부터 개발하는 ‘장인정신’이 발휘되는 것 같다.

하지만 최근에 했던 경험을 통해서 이 논리에 치명적인 결함이 있음을 깨달았다.

내가 그 바퀴를 예쁘게 만드는 동안 마차는 멈추고, 바퀴를 다루느라 본질을 잃어버렸기 때문이다. ‘장인정신’이 투철한 가상의 인물 ‘코너씨’를 통해서 이 현상에 대해서 알아보자.

unnamed.jpg

주객전도

바퀴를 직접 깍는 행위의 가장 큰 위험성이 무엇일까?

구현 가능성? 기술적 난이도? 과 같은 단어가 먼저 떠올랐다면,

당신이 ‘집중의 분산’에 대해서 간과하고 있다.

예시 1.

unnamed.jpg

코너씨가 블로그 서비스를 개발한다고 가정해 보자.

블로그의 본질은 무엇일까? ‘컨텐츠’를 쓰고 보여주는 것이다. 그런데 여기서 코너씨가 방문자 통계를 직접 구현해야 겠다고 생각한다면 이야기가 달라진다. 사용자의 유입 경로를 파싱하고, 세션을 관리하고, 통계를 차트로 보여주기 위해서 시간을 쏟게 되어, 정작 컨텐츠가 뒷전이 된다.

통계는 생각보다 고려해야 할 것들이 정말 많다. 유입 경로 하나만 제대로 보여준다고 해도 유의미한 값들을 파싱하기 위해서 예외가 상당히 많고, 봇이나 AI와 같은 유저 에이전트를 분류하는 것도 지속적인 관심과 업데이트가 필요하다. 거의 서비스로 하나 뽑아야 할 정도다.

코너씨가 처음부터 구글 애널리틱스를 도입했다면 모든게 좋았을 텐데, 처음에 이를 직접 구현하니 지속적으로 유지 보수가 필요해져서 정작 다른 부분을 제대로 신경쓰지 못한다. 완전히 지워버리기에는 인간은 나약하기 때문에, 소유 효과매몰비용 오류에 쉽게 빠져버린다.

소유 효과
자신이 어떤 대상을 소유하거나 직접 만들었을 때, 객관적인 가치보다 훨씬 더 높게 평가하는 현상

매몰비용 오류
이미 투입되어서 회수할 수 없는 비용(시간, 돈, 노력)이 아까워서, 앞으로 더 큰 손해가 예상됨에도 불구하고 하던 일을 멈추지 못하고 계속하는 심리적 오류

예시 2.

코너씨가 Svelte 라는 프론트엔드 프레임워크를 보고 나서는 뭔가 영감을 얻었다. React의 문법은 좋았지만 성능이 아쉽다고 생각했었고, Svelte의 철학은 꽤나 맘에 들었지만 선언적인 느낌은 아닌 것 같이 느껴졌다. 언젠가는 React 처럼 선언적이면서 Svelte처럼 획기적인 렌더링 라이브러리를 만들겠다 생각한다.

코너씨가 신규 토이 프로젝트를 시작하는데, 문득 위 렌더링 엔진을 함께 만들게 된다면?

처음에는 획기적인 방식으로 DOM을 관리할 방법을 떠올린다. 아주 멋지게 SOLID 패턴을 따르는 Component 클래스와 해당 클래스로 작성되는 아주 읽기 좋고 아름다운 코드들, 효율적인 렌더링 방식으로 돌아가는 페이지 하나를 만든다. 이 페이지는 단순 랜딩 페이지 느낌이어서 아무런 문제가 없었다.

다음 페이지로 넘어갔더니 여기에는 폼이나 비교적 복잡한 UI가 많이 보인다.

“음… 일단 라우팅 처리를 해야겠다.”

“음… 이벤트 처리도 생각보다 많다.”

“어..? 병렬 폼에 대한 상태 관리가 좀 복잡해진다.”

과연 코너씨는 토이 프로젝트를 끝내고 출시할 수 있을까?

이정도면 렌더링 엔진을 만드는 것이 토이 프로젝트의 주제가 된 것으로 보인다. 정작 렌더링 엔진을 다 구현하고 나면 이미 지쳐서 앱을 출시하는 일은 잊어버리고 말 것이다.

레거시 코드

unnamed.jpg

회사에서 직접 만든 바퀴는 그 자체로 시한폭탄이 될 수 있다.

유명한 오픈소스 라이브러리는 수만 명의 개발자가 검증하고, 문서화가 잘 되어 있다. 문제가 생기면 공식 문서를 보거나 커뮤니티에 물어보면 된다.

하지만 코너씨가 회사에서도 ‘장인정신’을 발휘하며 직접 코드를 양산했다면?

코너씨가 퇴사한 순간, 그 코드는 ‘거대한 똥 레거시’가 되어 버린다. 코너씨의 후임자는 코너씨의 코드를 보면서 코너씨의 의도를 파악하기 위해 코드를 역설계한다. 후임자는 10분이면 끝났을 일을 3일 동안 하다보니, 커밋에 남겨져 있는 코너씨의 메일로 욕설을 한 가득 써서 보내고 싶은 마음이 솓구친다.

이건 최적화가 아니라, 미래의 리소스를 현재로 끌어다 쓴 기술 부채일 뿐이다.

선택과 집중

unnamed.jpg

시간은 무한한 자원이 아니다. 본질적으로 인생이 우리에게 유한하다.

우리에겐 많은 시간이 주어지지 않았기에, 모든 것을 병렬로 처리할 수 없다.

  • 통계 서비스를 만들고 싶은가? 그렇다면 그게 본질이니 직접 만들어라.

  • 렌더링 엔진을 공부하고 싶은가? 그럼 엔진만 만들어라. 그 위에 복잡한 서비스를 올리려 하지 마라.

'최적화'라는 단어에 속지 말자. 진정한 최적화는 코드 몇 줄을 줄이는 것이 아니라, 내가 해결해야 할 '핵심 문제'에 내 모든 에너지를 쏟아붓는 것이다. 나머지는 위임하라. 이미 잘 굴러가는 바퀴가 있다면 기꺼이 가져다 끼워라. 그래야 우리는 더 멀리 갈 수 있다.

물론 호기심을 가지고, 로우 레벨부터 생각하면서 무언가를 해보는 건 아주 아주 아주 좋은 일이라고 생각한다. 내가 말하고 싶은 것은 우리가 어떤 본질에 집중해야 할 시점에 다른 중요하지 않은 것들을 중요하게 생각하는 오류를 저지르지 말자는 것이다. 우리는 바퀴가 아니라 마차를 나아가게 만들어야 한다.