home

패키지 사용에 대한 고찰

글 분류
main
키워드
attitude
생성일
2025/01/04 04:26
최근 수정일
2025/02/16 11:03
작성중

0. 들어가기전에

기능구현과 문제해결은 개발자들의 숙명이다. 개발자 존재자체의 근간이며 존재 이유이다. 이말은 모든 개발자들이 동의할 것이다. 우리는 기능구현 과 문제해결을 위해 패키지를 많이 사용하는데 이 패키지 대한 서로다르면서 연관되어있는 여러개의 고찰들이 담긴 글이다. 이 글에서 다루는 내용은 크게 아래와 같다.
패키지 사용 이유와 패키지 사용의 수치심
패키지 사용의 기준
패키지 이해의 필요성
Ghost Package
패키지 선택의 기준

1. 패키지 사용의 이유

타협

개발 과정에서 패키지 사용은 단순히 선택이 아니라, 필연적인 “타협”이라고 생각한다. 개발자는 항상 여러 제약사항과 싸워야 한다. 이러한 제약사항은 프로젝트의 마감 기한(Due Date)이나, 조직 구성원 및 개발 환경과 같은 외부적 요인일 수 있다. 이러한 현실적 제약 속에서 개발자는 효율적으로 목표를 달성하기 위해 패키지를 사용하게 된다.

효율성

패키지 사용으로 인해 발생하는 효율성이라는 장점도 절대 무시할 수 없다. 필자는 개발하며 자주 되뇌이는 말이 있는데, 바로 “내가 고민했던 건 99% 누군가 고민했던 문제다.”이다. 이는 패키지 선택 시 특히 자주 떠오르는 생각이다.
잘 만들어진 패키지는 내가 고민했던, 고민하고 있는 부분들에 대한 문제가 해결되어 있으며, 아마도 본인이 “미래에 고민할” 부분들에 대한 점들도 대부분 해결되어 있다. 이는 프로덕트 개발에 엄청난 효율성을 가져다주며, 개발자에게 많은 시간을 절약해 준다.

그럼에도 불구하고

개발자들 사이에는 “패키지를 사용하지 않고 직접 만들었다”는 개발자에게 묵묵히 동경하는 문화가 존재한다. 물론, 그들의 높은 기술력과 결단력은 충분히 존경받을 만하다. 그러나 적절한 선택 과정을 거쳐 패키지를 사용했다면, 그것이 부끄럽거나 수치스럽게 느껴질 이유는 없다.
제일 먼저 “패키지 사용 수치심”에 대해 다뤄보겠다.

2. 패키지 사용 수치심

많은 사람들이 문제 해결과 요구 사항 구현의 편의를 위해 React, Next.js와 같이 기능구현을 위한 패키지 뿐 만 아니라, DX(Developer Experience)를 향상시키는 ESLint 같은 도구를 즐겨 사용한다. 그러나 특히 프론트엔드 개발자들 사이에서 이러한 패키지 사용에 대해 부끄러움을 느끼는 경우를 자주 목격할 수 있다. 이는 빠르고 역동적으로 변화하는 웹 프론트엔드 환경에서 다음과 같은 이유로 인해 발생한다고 생각된다:
당장의 패키지 사용이 기술 부채로 이어질 것이라는 두려움
범용성을 위해 필요하지 않은 기능(예외처리)까지 포함하여 최종 번들 크기를 증가시켜 사용자 만족도를 저하시킬 가능성
완전히 이해하지 못한 기술을 사용하면서 느끼는 불안감
필자 역시 과거에 패키지를 사용할 때 이와 비슷한 ‘수치심’ 같은 감정을 느낀 적이 있다. 이러한 감정은 시간이 지나면서 많이 완화되었지만, 여전히 패키지를 선택할 때마다 위에서 언급한 복합적인 이유들로 인해 비슷한 감정을 느끼곤 한다.

Zero Package Policy - 과한 패키지 사용 수치심

완전한 패키지 없는 독립 개발(Zero Package Policy)을 목표로 모든 기능을 직접 구현하는 개발자는 극히 드물다. 대부분의 개발자는 문제를 해결하거나 기능을 구현하기 위해 이미 만들어진 오픈소스 패키지를 사용한다. 이는 단순히 시간을 절약하기 위한 것이 아니라, 현대 소프트웨어 개발의 기본적인 방식이다. 예를 들어, 아무리 “Vanilla” 스타일로 개발한다고 해도, 최소한 번들러(Webpack, Vite 등)React와 같은 필수 도구를 사용하는 경우가 대부분이다.
패키지 사용에 대한 지나친 수치심에서 비롯된 절대적인 “Zero Package Policy”는 지양해야 한다. 현실적인 관점에서 생각해보면, 지금 마주한 문제는 분명 과거에 다른 누군가도 직면했던 문제일 가능성이 높다. 게다가, 본인이 작성한 코드보다 더 많은 예외 처리를 포함하고, 성능적으로도 더 나은 솔루션을 제시할 가능성이 높은 오픈소스 패키지나 라이브러리를 활용하는 것이 합리적이다. 물론 특정 상황에서는 본인이 더 짧고 성능이 좋은 코드를 작성할 수도 있다. 그러나 그 코드가 조금이라도 더 일반적인 케이스에 사용되어야 한다면, 결국 높은 확률로 다시 작성하거나 수정해야 하는 상황이 발생할 것이다.
이러한 의견은 개인의 경력이나 뛰어난 개발 실력을 과시하려는 의도에서 비롯된 것이 아니다. 이는 개발자들이 마주하는 평균적인 현실에 근거한 이야기다. 물론 뛰어난 개발자라면 모든 것을 스스로 구현할 수 있을 것이다. 그러나 개발에는 항상 “시간”이라는 제한이 존재하며, 정해진 시간 안에 할 수 있는 일은 한정적이다.
취미로 패키지를 개발하는 것은 전혀 다른 이야기다. 이런 문제 해결을 위한 오픈소스 패키지를 만드는 일은 매우 추천할 만하다. 오픈소스 프로젝트에 이용자가 생기는 순간, 개발자는 높은 품질의 무료 개발 피드백과 교육 기회를 얻게 된다. 더불어, 본인이 고민했던 문제를 다른 사람들이 쉽게 해결하도록 돕는 과정에서 큰 “성취감”이라는 추가적인 perk도 존재한다.

통제되지 않은 패키지 사용의 위험성: 이해하지 못한 흑마법 (패키지 사용 수치심의 부재)

무질서하고 통제되지 않은 패키지 사용은 분명히 문제가 된다. 패키지도 결국 개발자가 만든 산물이기 때문에 고유의 문제와 이슈를 포함하고 있으며, 사용자의 개발 환경에 따라 예상치 못한 문제를 발생시킬 가능성이 있다.
특히, 패키지의 기본적인 작동 방식과 사용법을 이해하지 않고 사용하는 것은 개발자에게 “이해하지 못한 흑마법”과 같은 상황을 초래한다. 마치 “그냥 해줘”라고 말하면 결과만 나오는 마법 같은 존재로 의존하게 되는 것이다. 그러나 이러한 방식의 사용은 자신이 직면한 문제에 대한 깊은 이해를 희생하는 대가로 결과물을 얻는, 일종의 “등가교환”에 불과하다. 패키지를 통해 기능을 구현하거나 문제를 해결하는 순간에는 이러한 대가를 체감하지 못할 수 있다. 하지만 그 대가는 언젠가 반드시 치르게 된다. 이는 예상치 못한 유지보수의 어려움, 패키지의 작동 방식에 대한 부족한 이해로 인한 문제 해결의 비효율성 등 다양한 형태로 개발자에게 영향을 미칠 수 있다.

수치심 필터링

패키지 사용과 관련한 극단적인 태도는 모두 위험하다. 지나치게 많은 패키지를 무분별하게 사용하는 것도, 모든 패키지를 배제하려는 “Zero Package Policy”도 개발 과정에 심각한 문제를 초래할 수 있다. 전자는 기술 부채와 유지보수 복잡성을 증가시키고, 후자는 제한된 시간과 자원 속에서 비효율적인 개발을 강요한다.
개발에서 중요한 것은 극단적인 방향이 아닌, 상황과 요구에 맞는 균형점을 찾는 것이다. 적절한 패키지 사용은 반복 작업을 줄이고, 문제를 효율적으로 해결하며, 개발 시간을 단축시킨다. 하지만 이 과정에서 자신이 사용하는 도구와 기술에 대한 기본적인 이해를 갖추고, 필요 이상의 의존성을 배제하려는 노력이 함께해야 한다.
이처럼 개발자는 수치심이나 편견에 휘둘리지 않고, 패키지 사용에 있어 “Golden Middle”을 찾아야 한다. 이는 무조건 적인 편리함에 의존 또는 모든 것을 자력으로 해결하려는 태도 대신, 실질적인 문제 해결과 프로젝트 목표를 중심에 두고 판단하는 태도를 의미한다.
너무 과한 패키지 사용에 대한 수치심은 개발자가 기능 구현을 위해 패키지를 추가하는 것을 주저하게 만들 수 있다. 반면, 패키지 사용에 대한 수치심의 완전한 부재는 프로젝트의 복잡성을 증가시키고, 유지보수 측면에서 심각한 문제를 초래할 가능성이 있다. 이러한 양극단의 문제를 해결하기 위해서는 적절한 수준의 “수치심 필터링”이 필요하다.
다음 단락에서는, 수치심 필터링을 위한 패키지 사용의 기준에 대해서 다뤄보겠다.

3. 패키지 사용의 기준 체크리스트

패키지에 대한 고찰의 첫 번째 주제로, 패키지 선택 기준에 대해 논의한다. 개발자는 패키지 사용 여부와 관련해 명확한 기준을 확립할 필요가 있다. 여기서 강조하는 기준은 단순히 “어떤 패키지를 사용할 것인가?”라는 선택의 문제가 아닌 , “이 문제해결(또는 기능구현)에 패키지 사용이 필요한가?”라는 본질적인 판단을 의미한다.
이 체크리스트는 조직 구성원을 설득하기 위한 것이 아니라, 개발자가 스스로 고민하고 판단하기 위한 용도이다. 이는 개발자가 사용하는 데 필요한 기준과 조직 구성원이 사용 여부를 판단하는 기준이 다르기 때문이다. 조직의 구성원들과 함께 고민하기 위한 체크리스트는 7. 패키지 품평회에서 자세히 다룰 예정이다.
패키지 사용 여부에 대한 기준은 절대적인 규칙이 아니며, 개인, 조직, 프로젝트의 성격에 따라 달라질 수 있다. 이러한 다양성을 고려하여, 최대한 General하게 적용 가능한 기준을 제시하고자 한다.

General 하게 사용되는 코드인가?

프로젝트에 실제 사용처가 매우 적은 패키지를 프로젝트 의존성에 추가할 경우, 빠른 해결이라는 장점이 있다. 이는 단기적으로 이용자들의 문제를 빠르게 해결한다는 이점이 있지만, 장기적으로는 프로젝트 유지보수 관점에서 패키지 사용법과 기본 동작 방식에 대한 이해에 소요되는 시간, 번들 용량 증가 등의 단점들을 상쇄하지 못하는 케이스가 대부분이다.
Specific한 문제를 직접 해결하기 위해 코드를 작성하는 경우, General한 상황과 비교했을 때 예외 처리나 요구 사항이 많지 않다. 따라서 실제 코드 작성에 소요되는 시간도 비교적 짧으며, 코드의 양도 줄어드는 편이다.
여기서 전제는 “내가 작성한 코드가 남이 작성한 코드보다 이해하기 쉽다”는 점이다. 이로 인해 패키지 사용이나 기본적인 동작 방식에 대한 이해에 걸리는 시간보다 코드 작성 시간이 더 짧아질 수 있다. 필자가 강조하고 싶은 점은 “생각보다 코드를 직접 작성하는 데 많은 시간이 걸리지 않는다”는 것이다.
개인적인 경험에 따르면, General하게 사용되지 않고 Specific한 상황을 해결하기 위한 코드는 대부분 필자가 직접 작성할 수 있는 코드였다. 이러한 코드는 생각보다 어렵지 않으므로 두려워할 필요가 없다.

긴급하게 해결해야 할 이슈인가?

운영에 중대한 영향을 미쳐 정상적인 운영이 불가능한 수준의 문제 발생 시, 이상적인 패키지가 아니더라도 임시 패치 형태로 문제를 해결할 수 있다.
이러한 문제는 최우선적으로 처리해야 하므로, 신속한 패치를 위해 추가되는 패키지는 Ghost 패키지 형태를 띨 수밖에 없다. 이는 문제 해결에만 초점을 맞추고, 앞서 언급된 모든 검토 과정을 생략한 결과이다. 그러나 이러한 패키지는 추후 가능한 한 빠르게 “이상적인 해결책”으로 교체해야 한다.
사람마다 망각 속도는 다르지만, 결과적으로 인간은 망각하게 된다. 이렇게 해결된 이슈 중 “잊혀진 Ghost Package”는 점차 누적되어 프로젝트의 유지보수성을 저하시킬 수 있다.

패키지에 대한 기본적인 이해를 했는가?

패키지를 사용하는 데 있어 해당 패키지의 기본적인 작동 방식, 개발 배경 및 목적, 그리고 사용법에 대한 명확한 이해를 가지는 것은 중요하다. 이러한 이해가 부족한 상태에서 패키지를 도입하거나 사용하는 것은 단기적으로는 문제를 해결할 수 있어 보일지라도, 장기적으로는 코드의 복잡성을 증가시키고 기술 부채를 야기할 가능성이 높다.
패키지가 제공하는 기능과 한계를 이해하지 못한 채 사용하게 되면, 필요 이상으로 의존도가 높아지거나, 문제 해결 과정에서 예상치 못한 장애물을 만날 수 있다. 따라서 패키지를 사용하기 전 충분한 학습과 검토가 선행되어야 하며, 이를 통해 코드의 유지 보수성과 확장성을 확보할 수 있다.
이러한 이유로, 패키지를 사용하기 전에 해당 패키지에 대한 기본적인 이해가 충분히 이루어졌는지 여부를 반드시 확인해야 한다. 이는 문제 해결 과정에서 불필요한 리스크를 줄이고, 효율적이고 안정적인 코드 작성을 위한 필수적인 과정이다.
패키지에 대한 기본적인 이해는 단순히 패키지 사용 여부를 결정하는 기준으로서 중요할 뿐만 아니라, 개발과 패키지 사용은 밀접하게 연결되어 있어 개발자로서 반드시 갖춰야 할 기본 소양이다. 이에 대해서는 다음 챕터에서 더욱 자세히 다룰 예정이다.

4. 사용중이거나 사용예정인의 패키지 이해

개발자들에게 있어 사용하는 패키지에 대한 명확하고 깊은 이해는 필수적인 요소로 간주된다. 오늘날의 소프트웨어 개발 환경에서는 생산성과 효율성을 높이기 위해 다양한 패키지와 라이브러리를 사용하는 것이 일반적이지만 많은 개발자들이 특정 패키지를 사용하는 이유를 깊이 고민하지 않고, 단순히 주변에서 권장하거나 관습적으로 사용되는 것을 기준으로 채택하는 경우가 흔하다.
필자가 가장 많이 마주치는 상황 중 하나는 패키지가 해결하고자 하는 문제를 정확히 파악하지 않은 채 사용하는 것이다. 이는 패키지의 의도된 목적과는 다른 방식으로 사용되는 상황을 초래할 수 있다. 이러한 오용은 예상치 못한 오류를 발생시키거나, 패키지의 성능을 저하시킬 수 있으며, 결과적으로 프로젝트의 품질과 안정성에도 부정적인 영향을 미친다. 특히, 패키지가 제공하는 기능을 정확히 이해하지 못하고 억지로 요구사항에 맞추려 할 경우 코드의 복잡성이 증가하고 유지보수성이 떨어질 가능성이 크다.
이와 같은 문제를 미연에 방지하기 위해서는 현재 사용 중이거나 사용 예정인 패키지에 대한 충분한 이해가 필수적이다. 이를 위해 여러가지 방법들이 있지만 크게 3가지 방법에 대해 다뤄보겠다.
예를 들어 React를 사용하더라도 화면을 변경하는데는 크게 두가지 방법이 있다. 변경하고자 하는 DOM의 ref를 따서 변화주기, useState를 이용하여 화면에 변화주기이다. 무조건 하나의 방법이 옳은건 아니지만 대부분의 상황에서 대부분의 개발자들(React 메인테이너들 또한)은 useState로 변경하는것을 추천한다. 왜 useState를 사용해야하는지에 대한 이유를 정확히 파악하게되면 본인이 작성하는 코드에 대해 이해도 또한 높아지고 ref를 따서 DOM에 변화를 주는 방법과 같은 escape hatch는 언제 어디서 사용해야할지에 대하여 쉽게 판단 할수 있게된다.
필자는 패키지 사용 시 이해해야할 항목들은 크게 3가지로 규정지었다.

패키지 제작자들의 제작 이유 및 패키지의 역사

How A Small Team of Developers Created React at Facebook | React.js: The Documentary
React is easily one of the single most popular libraries in use today. Given that it was made within a juggernaut like Facebook, you might have assumed it was always destined for success. But what if we told you that React’s first brush with the public sphere was anything but glamorous? React.js: The Documentary brings you the full story behind the early days of React, focusing on the dedicated group of developers who helped bring it to the world stage. This story is told by an all-star cast of developers like Tom Occhino, Christopher Chedeau, Pete Hunt, Sebastian Markbåge, Dan Abramov, and many more. Check out the home for untold developer stories around open source, careers and all the other cool stuff developers are doing at cult.honeypot.io. Honeypot is a developer-focused job platform, on a mission to get developers great jobs. Wanna see what we're all about? Visit honeypot.io to find a job you love. To learn more about Honeypot: https://bit.ly/3OGoDjG Follow the cast: Adam Wolff: https://twitter.com/dmwlff Andrew Clark: https://twitter.com/acdlite Christopher Chedeau: https://twitter.com/Vjeux Dan Abramov: https://twitter.com/dan_abramov David Nolen: https://twitter.com/swannodette Lee Byron: https://twitter.com/leeb Michael Chan: https://twitter.com/chantastic Pete Hunt: https://twitter.com/floydophone Sebastian Markbåge: https://twitter.com/sebmarkbage Shane O'Sullivan: https://twitter.com/Chofter and https://chofter.com/ Sophie Alpert: https://twitter.com/sophiebits and https://sophiebits.com/ Tom Occhino: https://twitter.com/tomocchino Tony Casparro: https://twitter.com/IamTonyC Many people contributed to React throughout the years and this documentary is just a little slice of that history. You can find full acknowledgements here: https://reactjs.org/acknowledgements.html Thanks to these amazing people for translating subtitles: Charlie: https://twitter.com/charliesbot Jose: https://twitter.com/jbetosalinas Gustavo Gonçalves Follow us: Twitter: https://twitter.com/honeypotio Facebook: https://www.facebook.com/Honeypotio/ LinkedIn: https://www.linkedin.com/company/honeypotio/ Instagram: https://www.instagram.com/honeypot.cult/
이와 같은 유튜브 영상은 패키지 제작의 이유와 역사 파악에 좋은 예시중 하나이다. React의 초기에 “그들이 해결하고자 했던 문제들” 그리고 역사에 대해 다루는 영상인데, 당시 Facebook은 기존의 jQuery나 Backbone과 같은 명령형 프로그래밍 패키지들이 복잡한 UI 개발에 적합하지 않다는 문제를 인식했고, 이를 해결하기 위해 Jordan Walke와 소수의 개발자들이 React를 개발하게 되었다.
이 영상은 React의 주요 아이디어인 컴포넌트 기반 아키텍처와 선언적 UI의 필요성을 다루며, 왜 이런 접근 방식이 당시의 다른 프레임워크들과 차별화되었는지 설명한다. 이를 통해 React의 발전 과정과 의도, 그리고 초기부터 지금까지의 철학을 이해할 수 있다.
이와 같은 사전 지식으로 개발자들의 철학, 해결하고자 했던 문제점을 알고나면 Web FrontEnd 개발자로서 귀에 딱지가 앉도록 들었던 “선언형 프로그래밍”에 대한 명확한 이해가 가능해지므로 개발하며 이슈또는 첼린징한 과제를 만났을 때 더 “React(SPA)적인 해결법”을 도출해내게 더 쉬워진다.
React 적인 해결법이 항상 정답은 아니지만 그들이 의도한 바가 무엇인지 이해하고 그에 부합하지 않는 케이스일 경우 escape hatch를 사용하는게 맞다고 생각한다. 대부분의 패키지는 제작자들이 의도한 바를 벗어난 방법으로 문제해결을 할경우 더 복잡한 구현체 및 error prune한 기능이 만들어지기 마련이기 때문이다.

패키지에 추가된, 사라진 기능들에 대한 이해

Tanstack Query를 React Query 시절부터 사용해 온 사용자라면, Tanstack Query V5에서 useQuery의 onSuccess와 onError가 사라졌던 시점을 기억할 것이다. 필자 또한 “잘 사용하던 기능인데, 왜 없앴지?“라며 아쉬움을 느끼며 V4에서 V5로 업그레이드했던 경험이 떠오른다.
위에 북마크한 메인테이너 중 한 명인 TkDodo의 개인 블로그에서도 확인할 수 있듯, 해당 API는 처음부터 잘못 설계되었기에 이를 해결하기 위해 제거되었다고 언급한다. 또한, 사라진 기능에 대한 새로운 대처 방법을 제시하며, 이를 통해 Best Practice를 배울 수 있다. 이러한 글을 통해 개발자의 의도와 사용자가 자각하지도 못했던 문제를 인지할 수 있으며, 사라진 기능에 대한 새로운 대응법과 접근 방식을 배우게 된다. 이 과정은 개발자로서의 시야를 넓히는 데도 큰 도움을 준다.
필자는 패키지 개발과 프로덕트 개발은 요구사항 구현과 문제 해결의 관점에서 본질적으로 큰 차이가 없다고 생각한다. 다만, 패키지는 보다 일반적인 문제 해결에 초점을 맞추는 반면, 프로덕트는 최종 사용자가 실제로 활용할 기능 구현에 중점을 둔다는 차이점이 있다.
특히, 프로덕트 내 공통 유틸 함수나 컴포넌트를 개발할 때, 패키지 개발 방식을 적용하면 긍정적인 결과를 얻는 사례가 많다. 패키지에서 사용하는 방식 중 필요한 부분을 채택하되, 과도한 범용성과 불필요한 예외 처리를 줄이면, 특정 프로젝트에 적합하면서도 확장성이 높은 공통 요소를 효과적으로 개발할 수 있다.

완전히 바뀐 기능들에 대한 이해

JavaScript(TypeScript) 기반 프로젝트 들에서 코드에 규칙을 부여하기 위해 자주사용 되는 ESLint는 9버전 부터 설정파일의 구조와 사용방식 자체가 새롭게 바뀐 breaking change가 존재한다. 이와 같이 완전히 바뀐 기능들의 이유를 파악 하면 패키지의 전체적인 이해도를 향상 시키는데 큰 도움이된다.
이 글은 ESLint의 창시자인 Nicholas C. Zakas가 ESLint가 9 버전으로 업그레이드 하며 기존 .eslintrc가 가지고 있던 문제점과 새로운 eslint.config.js가 어떻게 해결하는지에 대해 설명하는 글이다. 이와 같이 “완전히 바뀐 기능들에 대한 설명”을 읽으면 1차적으로 지금껏 타성에 젖어 자각하지 못했던 패키지의 기존 방식의 한계와 단점들을 객관적인 입장에서 파악할 수 있다. 이로 인해 새로운 버전 upgrade의 필요성 또한 파악할 수 있다.
그다음으로, 새로운 설계 방식의 구체적인 의도를 이해함으로써 이전에 존재했던 문제가 무엇이었는지, 그리고 이를 어떻게 해결했는지를 더 명확히 파악할 수 있다. 이는 설계 철학이나 개선 방향에 대한 깊은 통찰을 제공하며, 변경 사항의 기술적 이유를 명확히 이해하는 데 도움을 준다. 직접적인 장점으로는 새로운 버전으로 패키지를 업그레이드할 때 주요 변화 포인트를 명확히 인지하고 대응할 수 있어, 마이그레이션 과정을 더 효율적이고 안정적으로 수행할 수 있다는 점이 있다. 이를 통해 예상치 못한 문제를 최소화하고, 업그레이드 비용과 시간을 절감할 수 있다.
간접적인 장점들은 아래와 같다.
1.
첫째, 메인테이너가 강조한 설계 철학과 변경 의도를 통해 패키지의 장기적인 방향성을 파악할 수 있다. 이를 통해 향후 업데이트에 대비하거나 해당 패키지를 사용하는 프로젝트의 전략을 보다 정교하게 수립할 수 있다.
2.
메인테이너가 제시한 개선 방식을 유사한 코드베이스에 적용함으로써 전반적인 코드 품질을 향상시킬 수 있다. 이를 통해 단순히 패키지를 활용하는 데 그치지 않고, 본인이 개발하는 프로젝트에서 비슷한 상황에 더 나은 설계와 유지보수성을 갖춘 코드베이스를 구축하는 데 영감을 얻을 수 있다.
“어차피 새 버전만 쓸껀데 굳이 이전 버전에 있던 문제점들을 알아야해?” 와 같이 생각 하는 독자들이 있을 수 있다고 생각한다. 필자는 이에 절대 동의하지 않는다.
기존 프로젝트에서 사용하던 패키지의 새로운 버전이 나왔다고 해서 항상 이를 즉시 사용할 수는 없다. 새로 시작하는 프로젝트 역시 마찬가지다. 예를 들어, ESLint 9은 Next.js 15 버전부터 지원되지만, Storybook의 Next.js 플러그인의 최신 버전이 Next.js 15을 지원한다고 해도 기존 프로젝트에서 이전 버전을 기반으로 Storybook이 설정되어 있다면 단순히 버전만 업그레이드한다고 해결되지 않는다. 이 과정에는 추가적인 작업 시간이 필요하다.
하다못해 사이드 프로젝트에서도 시간이 중요한데, 회사 프로젝트라면 시간의 중요성은 더욱 커진다. 누구나 알다시피, 패키지 버전 업그레이드는 버전 간 호환성 문제 등으로 인해 적지 않은 시간이 소요된다. 운이 좋으면 빠르게 끝날 수도 있지만, 대부분 많은 시간이 걸린다. 조직마다 다르겠지만, 많은 개발자가 버전 업그레이드를 미루고 미루다, “이제 더 이상 미루면 큰 문제가 생긴다”는 상황에 이르러서야 추가 리소스를 배정받아 업데이트를 진행하는 경우를 자주 볼 수 있다.
특히, ESLint처럼 프로젝트의 핵심 기능 구현에 직접적인 기능구현에 영향을 미치지 않는 패키지라면, 의사결정자를 설득하는 일이 더욱 어렵다. 이러한 이유로 “항상 최신 버전만 사용하기”라는 원칙은 실제 업무 환경에서 적용하기 어려운 경우가 많다.

5. 즐기는자 이길 수 없다.

모든 패키지를 연구하고 공식 문서를 읽어 사용법을 완벽히 숙지하는 것은 개발자가 이상적으로 지향해야 할 목표일지언정, 현실적으로 달성하기는 매우 어렵다. 업무 시간 내에 이를 온전히 소화하기에는 제한이 많으며, 이를 위해 업무 외 시간을 투자하지 않고는 사실상 불가능에 가깝다. 그러나 개인 시간을 희생하며 이상적인 목표를 쫓는 것은 추천하지 않는다. 적절한 타협이 필요하다.
우리는 개발자이기 전에 인간이며, 충분한 휴식이 뒷받침될 때 비로소 개인이 낼 수 있는 최고의 퍼포먼스를 낼 수 있다.
다만, “궁금해서”, “알고 싶어서”라는 이유로 취미처럼 적당한 여가 시간을 활용하는 것은 다른 이야기다. 이는 개발자에게 중요한 태도 중 하나로, 특히 “알고 싶어서 견딜 수 없다”는 열정이 필수적이다. 많은 사람들이 “즐기는 자를 이길 수 없다”는 말을 들어왔을 것이다. 즐기는 것이 높은 허들을 넘는 일처럼 보일 수 있지만, 실제로는 그렇지 않다. 내부 동작 방식을 알고 싶거나, 이해하지 못한 채 사용하는 것을 견딜 수 없으며, 왜 이 기술을 써야 하는지 알고 싶어 하는 모든 태도가 “즐긴다”의 범주에 포함된다고 볼 수 있다.
개발을 즐기며 배우는 사람들과 그렇지 않은 사람들 간의 이해력 차이는 개인차가 있을 수 있지만, 즐기며 배우는 사람들은 기본적으로 투자하는 시간이 더 많아 그렇지 못한 사람들보다 더 많은 것을 알고 있을 가능성이 높다.

6. Ghost Package

Ghost Package는 “구성원 중 누군가가 의견 교환 없이 추가하거나, 과거부터 사용되었지만 누가 추가했는지, 어디에서, 왜 사용하는지 모르는 패키지”를 의미한다. 이는 결과적으로 “존재하지만 사용 방법이나 사용 목적을 알 수 없는 패키지”로, 조직 내에서 실제로 사용되지 않고 마치 “유령”처럼 취급되는 패키지다.
Ghost Package는 주로 “이 패키지가 무엇을 해결하기 위한 것인지”, “왜 선택했는지”와 같은 이유를 구성원들과 공유하지 않고, 개개인의 판단과 의사소통의 부재로 인해 점점 쌓여간다.
Ghost Package는 조직의 시스템과 프로젝트에 여러 가지 위험을 초래한다. 그 위험들은 아래와 같다. 첫째, 패키지의 목적과 사용 방법이 명확하지 않아 유지보수 과정에서 혼란을 일으킬 수 있다. 누가, 왜 추가했는지에 대한 정보가 부족하면, 패키지를 삭제하거나 업데이트하는 과정에서 시스템 오류나 예상치 못한 문제가 발생할 가능성이 크다. 둘째, 사용되지 않는 패키지가 계속해서 시스템에 남아 있을 경우, 불필요한 리소스를 소모하고 프로젝트의 복잡성을 증가시킨다. 이는 개발 속도를 저하시킬 뿐만 아니라, 보안 취약점을 유발할 수도 있다. 특히 업데이트되지 않은 패키지는 보안 위협에 노출될 가능성이 높아 전체 시스템의 안정성을 저해할 수 있다. 마지막으로, Ghost Package는 조직 내 의사소통의 부재와 기술적 비효율성을 상징하며, 협업 문화와 업무 프로세스의 문제를 드러내는 신호로 작용할 수 있다. 이러한 이유로 Ghost Package의 발생을 방지하고 관리하는 체계가 필수적이다.

더 나은 대안 선택 기회의 상실

Ghost Package는 구성원 간 의견 교환 없이 추가되는 경우가 많아, 더 나은 패키지나 패키지 없이 간단히 해결할 수 있는 직접 구현 방식을 고려할 기회를 사라지게 한다. 이는 문제를 효율적으로 해결할 수 있는 대안에 대해 논의조차 하지 못하게 만들며, 결과적으로 프로젝트의 코드 퀄리티를 저하시킨다.

특정 인물에게 의존

Ghost Package는 종종 특정 개인이나 과거의 특정 구성원만 사용하는 패키지로 전락한다. 이는 팀 내 다른 구성원들이 해당 패키지를 이해하거나 활용하지 못하게 만들어, 팀 전체의 기술적 일관성을 해치고 특정 개인에게 지나치게 의존하게 되는 결과를 초래한다. 이러한 상황은 특히 해당 개인이 팀을 떠날 경우 심각한 문제가 될 수 있다.

유지보수 리소스의 증가

Ghost Package는 추후 코드 수정 시, 패키지의 사용 목적과 선택 이유를 이해하기 위해 추가적인 리소스를 요구한다. 패키지에 대한 정보를 찾고 그 의도를 파악하는 과정은 시간과 노력이 소모될 뿐 아니라, 새로운 문제를 야기할 가능성도 높다.

전염성과 조직 문화의 문제

Ghost Package는 “너도 했으니 나도 한다”는 보상 심리에 의해 높은 전염성을 보인다. 이는 단순히 개별적인 패키지 선택의 문제가 아니라, 조직의 의사소통과 협업 문화에 근본적인 문제가 있음을 나타낸다.

새로운 구성원에게 미치는 영향

개발팀의 특성상 구성원의 조합이 자주 바뀌게 되는데 이때, 새로운 구성원이 합류했을 때 Ghost Package는 큰 혼란을 초래할 수 있다. 새로운 구성원은 “왜 이 패키지를 사용했는가?” 또는 “이 패키지가 꼭 필요한가?“와 같은 질문을 던지게 되며, 과거에 이미 검토되었던 내용들을 다시 파악하고 고민해야 한다. 이로 인해 불필요한 리소스가 낭비되고, 최악의 경우 기존 테스트에서 걸러지지 않는 새로운 문제가 발생할 가능성도 존재한다.

불완전한 의도 파악으로 인한 리스크

Ghost Package의 목적과 의도가 불완전하게 전달될 경우, “이 패키지가 없어도 되는 것이 아니냐?“는 잘못된 판단으로 인해 해당 패키지를 제거하려는 시도가 이루어질 수 있다. 이러한 결정은 기존 시스템에서 예상치 못한 문제를 발생시킬 수 있으며, 특히 테스트로 걸러지지 않는 문제들이 나타날 위험이 크다. 이는 프로젝트 안정성에 큰 위협이 될 수 있다.

7. Package 품평회

Package 품평회는 패키지 사용을 제안한 개인이 아래의 주요 질문에 답변하고 이를 구성원들에게 발표하고 구성원들은 그에대해 질문하고 다른 해결법을 제안하는 자리이다.
Package 품평회는 Ghost Package가 프로젝트에 남아 리소스를 낭비할 가능성을 효과적으로 제거할 수 있으며, 팀원 간 지식과 정보를 공유하고 함께 학습할 기회를 제공한다. 이를 통해 조직 내 기술적 이해도 차이를 줄일 수 있고, 패키지 사용 여부를 객관적으로 검토할 수 있는 기회가 되어, 더 나은 선택지가 있을 경우 이를 발견하고 적용할 수 있는 기회를 제공 할 수 있게한다.
3. 패키지 사용의 기준 체크리스트에서도 언급했듯이 패키지 사용 기준 체크리스트는 기본적으로 “나 자신”을 대상으로 한다. 이는 조직 구성원들에게 제안하기 전에, 스스로에게 되묻는 과정을 위한 도구이기 때문이다. 체크리스트를 통해 “내 기준으로 판단했을 때 이 패키지가 정말 필요한가?“라는 고민을 하고, 이에 대한 답을 찾을 수 있도록 돕는다.
패키지 품평회에서 조직원 모두가 함께 고민해야 하는 단계에서도 “패키지 사용이 필요한지?”에 대한 고민을 해야한다. 그러나 결과적으로 패키지 사용이 필요하다고 판단된다면, 이 패키지의 한계와 장단점을 검토하여 과연 최선의 선택인지 고민하는 과정이 함께 이루어져야 한다. 이를 위해 더 많은 체크리스트가 필요하다.
물론 조직 구성원들도 대상이 될 수 있지만 조직 구성원들에게 설득하고 의견을 구하는 기준은 Package 품평회가 더 올바른 선택이다.
Package 품평회에 해당하는 체크리스트는 다음과 같다.

해결하고자 하는 문제가 무엇인가? - 문제의 파악

패키지를 도입하기 전에, 해결해야 할 문제를 구체적으로 정의하는 것이 중요하다. 이 과정에서는 문제가 무엇인지, 프로젝트에 어떤 영향을 미치는지, 그리고 이를 해결하지 않을 경우 발생할 수 있는 리스크를 명확히 해야 한다.
예를 들어, 특정 기능 구현이 필요한지, 성능 개선이 요구되는지, 또는 개발 효율성을 높이기 위한 도구가 필요한지를 확인해야 한다. 문제의 우선순위와 중요성을 파악하면, 패키지 사용이 최적의 선택인지 판단하는 데 도움이 된다.

왜 직접 구현할 수 없었는가? 또는 직접 구현하지 않았는가?

구성원 간 서로 다른 Capacity에 대한 해결책을 마련하기 위함이다. 여기서 말하는 Capacity는 절대적인 역량 차이가 아니라, 각기 다른 분야에서의 기술적 이해도의 차이를 의미한다. 이러한 차이를 극복하기 위한 질문 중 하나로 제기되었다.
또한, ROI(투자 대비 효율성)도 함께 고려해야 한다. 결과적으로, 직접 구현보다 패키지를 사용하는 것이 얼마나 더 효율적인지, 혹은 패키지 사용이 효율적인 이유를 검토하는 과정이 필요하다.
이 질문은 다른 구성원들이 패키지를 사용하지 않고도 문제를 해결할 수 있는 방법을 제안할 여지를 제공할 수 있다.

이 패키지의 장점과 단점은 무엇인가?

패키지를 도입하기 전, 해당 패키지의 장점과 단점을 명확히 파악하는 것은 필수적이다. 장점은 문제 해결에 있어 패키지가 제공하는 핵심 기능과, 이를 통해 기대할 수 있는 생산성 향상, 개발 시간 단축, 그리고 기술적 우위 등을 포함한다. 예를 들어, 특정 패키지가 제공하는 성능 최적화, 확장성, 커뮤니티 지원은 도입을 결정하는 중요한 요소가 될 수 있다.
물론, 단점 역시 함께 고려해야 한다. 패키지가 가진 한계나 잠재적인 문제점(예: 유지보수성 저하, 보안 취약점, 불필요한 의존성 증가 등)을 명확히 인지하지 못하면, 장기적으로 프로젝트에 악영향을 미칠 수 있다. 특히, 해당 패키지가 프로젝트의 특수한 요구사항과 얼마나 잘 맞는지, 과도하거나 불필요한 기능을 포함해 번들 크기를 증가시키지는 않는지, 패키지 유지보수를 위한 리소스가 과도하게 소모되지 않는지를 점검해야 한다.
또한, 단점을 파악하는 과정에서 대안적인 솔루션에 대해 논의할 수 있는 기회가 생긴다. 이는 패키지가 제공하는 가치와 이를 통해 해결하고자 하는 문제를 다시 한번 객관적으로 검토하는 과정으로 이어질 수 있다. 예를 들어, 직접 구현이 가능하거나, 더 적합한 다른 패키지가 존재한다면, 현재 패키지가 최선의 선택이 아닐 수도 있다.
마지막으로, 장점과 단점을 검토하는 과정은 단순히 의사결정을 돕는 데 그치지 않는다. 이 과정에서 구성원들은 패키지의 구조와 사용 방식, 그리고 한계를 명확히 이해하게 되어, 패키지 사용 이후 발생할 수 있는 문제를 사전에 예방할 수 있다.

왜 이 패키지여야 하는가?

이 질문에 제안자는 단순히 특정 패키지가 문제를 해결할 수 있다는 이유만으로는 충분하지 않으며, 해당 패키지가 다른 대안보다 우수한 이유를 명확히 설명할 수 있어야 한다. 이러한 논의는 패키지의 장점과 단점을 바탕으로 이루어진다.
결국 “왜 이 패키지여야 하는가?”에 대한 답변은 장점과 단점, 대안 분석을 종합적으로 고려하여 도출된다. 이를 통해 패키지의 선택이 단순히 편리함이나 관습적인 결정이 아니라, 프로젝트의 요구사항에 가장 부합하고, 장기적으로도 유지보수성과 품질을 보장할 수 있는 선택임을 증명해야 한다. 이러한 과정은 팀의 합의를 도출하고, 패키지 도입 이후 발생할 수 있는 문제를 예방하는 데도 크게 기여한다.

8. 마무리

패키지를 선택하고 사용하는 과정은 현대 개발자에게 있어 필수적인 역량으로 간주되어야 한다. 이는 단순히 필요한 기능을 구현하기 위해 패키지를 가져다 쓰는 수준에 머무르는 것이 아니라, 해당 패키지의 구조와 작동 원리를 깊이 이해하는 것까지 포함한다.
이러한 이해는 단순한 패키지를 사용한 구현 또는 문제해결을 넘어, 기능구현/문제 해결 과정에서 올바른 도구를 선택하고 적절히 활용할 수 있는 능력을 의미한다. 결국, 패키지 사용 여부와 선택의 적절성은 개발자가 직면한 문제를 얼마나 효과적으로 해결할 수 있는지 평가하는 중요한 기준이자, 개발자의 역량을 증명하는 척도가 된다.