모든 것을 바꾼 라이브러리 추출
우리의 채팅 UI와 파일 시스템을 재사용 가능한 패키지로 통합하면서 단일 제품이 어떻게 플랫폼으로 발전했는지에 대한 이야기입니다.
제품이 플랫폼이 되는 순간
모든 제품의 생애에는 단일 애플리케이션에서 플랫폼으로 전환되는 특정 순간이 있습니다. 우리에게 그 순간은 2025년 11월 26일 — 첫 커밋 후 5일이었습니다.
바로 그때 우리는 채팅 인터페이스, 가상 파일 시스템, 그리고 핵심 유틸리티를 세 개의 별도 재사용 가능한 패키지로 분리했습니다: @fulldiveVR/chat-ui, @fulldiveVR/vfs-ui, @fulldiveVR/core-ui-utils.
이건 엔지니어링 결정처럼 들리지만, 사실 비즈니스 결정이었습니다.
왜 다섯째 날에 했는가, 오십째 날이 아닌
전통적인 지혜는 이렇게 말합니다: 라이브러리를 너무 일찍 추출하지 마라. 두 번째 사용 사례가 생길 때까지 기다려라. API가 안정될 때까지 기다려라. “무엇을 만들고 있는지 알 때까지” 기다려라.
우리는 그런 모든 것을 무시했습니다.
그 이유는 이렇습니다: 우리는 여러 제품이 동일한 채팅 인터페이스를 사용할 것이라는 걸 알고 있었습니다. 파일 관리 UI가 다양한 맥락에서 필요할 것이라는 걸 알고 있었습니다. 그리고 우리가 기다릴수록 이 구성 요소들이 대시보드의 특정 요구에 더 밀접하게 결합될 것이라는 걸 알고 있었습니다.
다섯째 날, chat-ui 패키지는 약 2,000줄의 코드로 구성되어 있었습니다. 깔끔하고, 범위가 명확하며, 추출하기 쉬웠습니다.
오십째 날까지 기다렸다면, 10,000줄이 되었고 대시보드 특정 상태, 라우팅 및 구성에 대한 수십 개의 암묵적 의존성이 생겼을 것입니다. 그때 추출하는 것은 2일이 아닌 여러 주의 프로젝트가 되었을 것입니다.
우리가 추출한 것들
chat-ui — 전체 채팅 렌더링 시스템. 메시지 버블, 스트리밍 응답, 파일 첨부, 에이전트 전환, 도구 호출 표시. 사용자가 AI 에이전트와 대화할 때 보는 모든 것.
vfs-ui — 가상 파일 시스템 인터페이스. 파일 트리, 폴더 생성, 파일 미리보기, 드래그 앤 드롭, 업로드 대화상자. 사용자가 파일을 관리할 때 보는 모든 것.
core-ui-utils — 공유 유틸리티. 테마 토큰, 공통 훅, 레이아웃 프리미티브. chat-ui와 vfs-ui 모두가 필요하지만 어느 쪽도 소유해서는 안 되는 것들.
각각 버전 관리된 npm 패키지가 되어 GitHub Packages에 게시되었고, 대시보드는 다른 의존성과 마찬가지로 이를 사용했습니다.
복리 효과
2026년 2월까지 우리의 chat-ui 패키지는 버전 2.0.12에 도달했습니다. 수십 개의 릴리스가 있었고, 각 릴리스는 이를 사용하는 모든 제품의 채팅 경험을 개선했습니다.
채팅 UI에 백그라운드 작업 메시지를 추가했을 때, 모든 제품이 백그라운드 작업 메시지를 받았습니다. 사용자 메시지를 접을 수 있게 했을 때, 모든 제품이 접을 수 있는 사용자 메시지를 받았습니다. 렌더링 버그를 수정했을 때, 모든 제품이 그 수정 사항을 받았습니다.
이것이 초기 추출의 복리 효과입니다: 개선이 곱해집니다.
하지만 코드 재사용을 넘어섭니다. 이러한 라이브러리를 추출하는 것은 우리의 인터페이스에 대해 생각하게 했습니다. 채팅 구성 요소는 무엇을 알아야 할까요? 파일 관리자는 호스트 애플리케이션에서 무엇을 필요로 할까요? 이러한 질문들은 초기 단계에서 제기되어, 몇 달 후 모든 것이 얽힌 상태에서보다 더 깔끔한 답변을 만들어냈습니다.
예상치 못한 이점: 속도
가장 놀라웠던 점은 이거였습니다. 초기 추출 비용(약 2일의 리팩토링) 이후, 우리의 개발 속도가 증가했습니다.
왜 그럴까요? 경계가 명확했기 때문입니다. 채팅 경험을 작업하는 것은 chat-ui에서 작업하는 것을 의미했습니다. 파일 관리를 작업하는 것은 vfs-ui에서 작업하는 것을 의미했습니다. “채팅을 변경했더니 파일 관리자가 망가졌다"는 일이 없었습니다. 왜냐하면 이들은 명확한 인터페이스를 가진 별도의 패키지였기 때문입니다.
새로운 팀원들은 전체 대시보드 코드베이스를 이해하지 않고도 chat-ui에서 작업할 수 있었습니다. 버그 보고서는 즉시 올바른 패키지로 분류될 수 있었습니다. 각 패키지는 자체 테스트 스위트를 가졌기 때문에 테스트도 더 빨라졌습니다.
다른 빌더들을 위한 교훈
구성 요소 주위에 상자를 그릴 수 있다면 — 명확한 입력, 명확한 출력, 명확한 목적이 있다면 — 조기에 추출하세요. 신화 같은 “적절한 시기"를 기다리지 마세요. 적절한 시기는 추출이 작고 저렴할 때입니다. 그 기회는 생각보다 빠르게 닫힙니다.
우리는 첫 주에 세 개의 라이브러리를 추출했습니다. 80일 후, 이들은 백 번 이상 업데이트되었습니다. 각 업데이트는 모든 제품을 개선했습니다. 이것이 작은 팀을 생산적인 팀으로 바꾸는 레버리지입니다.
우리가 어떻게 일주일 만에 세 개의 라이브러리를 추출했는지
- 1
경계를 식별하세요.
채팅 렌더링, 파일 관리, 그리고 핵심 유틸리티는 명확한 인터페이스를 가지고 있었어. 그 인터페이스 뒤에 있는 모든 것은 패키지로 이동할 수 있었지.
- 2
추출하고 게시하세요
우리는 chat-ui, vfs-ui, 그리고 core-ui-utils를 GitHub Packages의 별도 패키지로 이동했습니다. 같은 코드지만, 적절히 범위가 설정되었습니다.
- 3
우리의 패키지를 사용하세요.
대시보드가 로컬 코드에서 게시된 패키지로 전환되었어요. 만약 이게 우리에게 문제가 생긴다면, 다른 누구에게도 문제가 생길 거예요.
- 4
패키지 속도로 반복하세요.
이제 chat-ui의 개선 사항이 이를 사용하는 모든 제품에 혜택을 줍니다. 한 번의 수정으로 모든 곳에서!
라이브러리 추출에 대한 질문
1주차에 라이브러리를 추출하기에는 너무 이른 거 아닌가요?
그건 상황에 따라 달라. 만약 경계가 명확하다면 — 채팅 UI와 파일 관리에서는 그랬어 — 초기 추출이 얽힘을 방지해. 여섯 달 동안 함께 성장한 코드에서 라이브러리를 추출하는 건 훨씬 더 어려워.
패키지 간 버전 관리는 어떻게 하나요?
시맨틱 버전 관리. 주요 변경 사항은 메이저 버전이 올라갑니다. 우리는 대시보드를 자주 업데이트하는데, 때로는 하루에 여러 번 업데이트하기도 해서 회귀를 빠르게 잡아냅니다.
이게 개발 속도를 늦췄나요?
약 이틀 정도 그랬어요. 그 이후로는 개발이 크게 가속화됐죠. UI 라이브러리에 대한 변경 사항이 이를 사용하는 모든 제품을 자동으로 개선했어요.