je개발 회고

[ 디자인 시스템 ] (3) 라이브러리 버전 관리

Je-chan 2026. 1. 12. 13:52

모노레포 버전 관리: Changeset 자동화

모노레포에서 수십 개의 패키지 버전을 수동으로 관리하는 건 불가능에 가깝습니다. 이번 글에서는 Changeset을 활용한 자동 버전 관리 시스템을 구축하는 방법을 설명합니다. Conventional Commits와 연동하여 커밋 한 번으로 버전 결정부터 배포까지 이어지는 흐름을 만들어보겠습니다.

수동 관리의 한계

우리가 겪었던 문제들

자동화 이전에는 릴리즈 담당자가 엑셀이나 메모장에 변경 사항을 적어가며 버전을 올렸습니다. 이 과정에서 휴먼 에러는 필연적이었습니다.

문제점 상세 내용
의존성 누락 utils 패키지를 업데이트했는데 이를 사용하는 hooks 패키지의 버전을 올리는 걸 깜빡함
버전 규칙 위반 새로운 기능을 추가했는데(Minor) 실수로 버그 수정(Patch) 버전만 올림
CHANGELOG 부담 배포 때마다 어떤 내용이 바뀌었는지 커밋 로그를 뒤져가며 수동으로 작성

자동화 워크플로우

버전 관리 자동화 파이프라인
1. Conventional Commits 작성
2. 커밋 메시지 분석 (스크립트)
3. Changeset 파일(.md) 자동 생성
4. 버전 업데이트 실행 (changeset version)
변경된 패키지 버전업
의존 패키지 연쇄 버전업
5. CHANGELOG.md 자동 생성

Semantic Versioning과 커밋 규칙

Conventional Commits 매핑 전략

커밋 메시지의 접두어를 통해 버전 단위를 자동으로 결정합니다. 개발자는 코드를 작성할 때 커밋 메시지만 규칙에 맞게 쓰면 됩니다.

커밋 타입 버전 단위 의미
feat!: / BREAKING CHANGE: MAJOR 하위 호환성을 깨뜨리는 변경
feat: MINOR 새로운 기능 추가
fix: / refactor: PATCH 버그 수정 또는 내부 개선

Changeset 설정 및 활용

설정 파일 (.changeset/config.json)

// .changeset/config.json
{
  "$schema": "https://unpkg.com/@changesets/config@3.0.0/schema.json",
  "changelog": "@changesets/cli/changelog",
  "commit": false,
  "baseBranch": "main",
  "updateInternalDependencies": "patch",
  "access": "restricted"
}
💡 핵심 설정: updateInternalDependencies

이 옵션을 patch로 설정하면 의존성 캐스케이딩이 활성화됩니다. 하위 패키지가 업데이트되었을 때 이를 의존하는 상위 패키지도 자동으로 patch 버전을 올려주어 의존성 누락을 방지합니다.

버전 전파(Cascading) 예시

시나리오: utils 패키지에 새로운 기능을 추가(Minor)했습니다.

의존성 연쇄 업데이트
직접 변경
utils: 0.2.0 → 0.3.0 (minor - feat 커밋)
1차 전파
hooks: 0.1.5 → 0.1.6 (patch - utils 최신 버전 반영)
2차 전파
components: 0.2.1 → 0.2.2 (patch - hooks 최신 버전 반영)

자동화 스크립트

개발자가 매번 Changeset 파일을 수동으로 만들 필요가 없도록, 커밋 로그를 분석해 자동으로 생성해 주는 스크립트(generate-changeset.mjs)를 사용합니다.

스크립트 동작 원리

  1. 마지막 태그 이후의 커밋 목록을 조회합니다.
  2. 각 커밋 메시지를 파싱하여 변경된 패키지와 변경 유형(Major/Minor/Patch)을 추출합니다.
  3. 분석된 내용을 바탕으로 .changeset 폴더에 마크다운 파일을 생성합니다.
<!-- 생성된 파일 예시: .changeset/brave-cats-jump.md -->
---
"@design-system/utils": minor
"@design-system/hooks": patch
---

- feat: add isEmpty function
- fix: correct phone number validation

실제 버전 업데이트 프로세스

배포 시점에 changeset version 명령어를 실행하면 다음과 같은 작업이 일괄 처리됩니다.

  1. Changeset 파일 읽기: .changeset 폴더의 모든 파일을 읽습니다.
  2. 버전 계산: 직접 변경된 패키지와 의존성 전파를 고려해 최종 버전을 계산합니다.
  3. 파일 수정: 각 패키지의 package.json 버전을 업데이트합니다.
  4. 문서화: 각 패키지의 CHANGELOG.md에 변경 내역을 기록합니다.
  5. 정리: 처리가 완료된 Changeset 파일을 삭제합니다.

결과물

packages/utils/
├── package.json      # version: "0.3.0"으로 변경됨
└── CHANGELOG.md      # 새로운 Minor 버전 내역 추가됨
⚠️ 주의사항

자동 생성된 Changeset 파일이나 업데이트된 package.json을 수동으로 수정하지 않는 것이 좋습니다. 의존성 그래프 계산이 꼬일 수 있으므로 항상 도구를 통해 제어하는 것이 안전합니다.