마이크로서비스 전반에 걸친 중앙화된 문서 구축: Docusaurus, GitLab CI, TypeDoc 활용
Source: Dev.to
마이크로서비스 전역 문서화 구축하기: Docusaurus, GitLab CI, TypeDoc 활용
소개
여러 개의 마이크로서비스를 운영하면서 각 서비스마다 별도의 README와 API 문서가 흩어져 있는 경우가 많습니다.
이러한 문서를 한 곳에 모아 검색 가능하고 일관된 형태로 제공하면 개발 생산성이 크게 향상됩니다.
이번 글에서는 Docusaurus(정적 사이트 생성기)와 TypeDoc(TypeScript API 문서 생성기)를 결합하고, GitLab CI를 이용해 자동으로 빌드·배포하는 파이프라인을 구현하는 방법을 단계별로 살펴보겠습니다.
전체 아키텍처
+-------------------+ +-------------------+ +-------------------+
| Service A Repo | ---> | TypeDoc (API) | | |
+-------------------+ +-------------------+ | |
+---+ Docusaurus Site |
+-------------------+ +-------------------+ | (Docs) |
| Service B Repo | ---> | TypeDoc (API) | | |
+-------------------+ +-------------------+ +-------------------+
| |
v v
+-------------------+ +-------------------+
| GitLab CI/CD | | GitLab Pages |
+-------------------+ +-------------------+
- 각 마이크로서비스 레포지토리에서
typedoc을 실행해 API 문서를 JSON 형태로 출력합니다. - Docusaurus 레포지토리에서는
docs/디렉터리와static/api/디렉터리를 통해 일반 문서와 API 문서를 통합합니다. - GitLab CI 파이프라인이 트리거되면 모든 서비스의 API 문서를 가져와 Docusaurus 사이트를 빌드하고, 결과물을 GitLab Pages에 배포합니다.
1. Docusaurus 프로젝트 초기화
npx create-docusaurus@latest docs-site classic
cd docs-site
npm install
classic템플릿을 사용하면 기본적인 블로그, 문서, 검색 기능이 포함됩니다.docs/디렉터리에 마이크로서비스별 가이드와 튜토리얼을 Markdown 파일로 추가합니다.
2. TypeDoc 설정 및 API 문서 생성
각 마이크로서비스 레포지토리 루트에 typedoc.json을 추가합니다.
{
"entryPoints": ["src/index.ts"],
"out": "typedoc",
"json": "typedoc/api.json",
"excludePrivate": true,
"excludeProtected": true,
"excludeExternals": true
}
json옵션을 사용해 JSON 형태로 API 메타데이터를 출력합니다.- 이후 CI 단계에서 이 JSON 파일을 Docusaurus 레포지토리의
static/api/폴더로 복사합니다.
3. GitLab CI 파이프라인 구성
3.1. 중앙 문서 레포지토리 (docs-site/.gitlab-ci.yml)
stages:
- fetch-api
- build
- deploy
variables:
NODE_ENV: "production"
fetch_api:
stage: fetch-api
image: node:18
script:
- mkdir -p static/api
# 각 서비스 레포지토리에서 API JSON을 가져옴
- curl -L "$SERVICE_A_API_URL" -o static/api/service-a.json
- curl -L "$SERVICE_B_API_URL" -o static/api/service-b.json
artifacts:
paths:
- static/api
build_site:
stage: build
image: node:18
script:
- npm ci
- npm run build
artifacts:
paths:
- build
pages:
stage: deploy
image: alpine:latest
script:
- mv build public
artifacts:
paths:
- public
only:
- main
fetch_api단계에서는 각 서비스 레포지토리에서 API JSON을 다운로드합니다.SERVICE_A_API_URL,SERVICE_B_API_URL등은 해당 레포지토리의 GitLab CI 변수로 정의합니다.build_site단계에서 Docusaurus 사이트를 정적 파일(build/)로 생성하고,pages단계에서 GitLab Pages에 배포합니다.
3.2. 마이크로서비스 레포지토리 (.gitlab-ci.yml)
stages:
- doc
generate_api_docs:
stage: doc
image: node:18
script:
- npm ci
- npx typedoc
artifacts:
paths:
- typedoc/api.json
only:
- main
- 서비스 레포지토리에서는
typedoc실행 결과인api.json을 아티팩트로 저장합니다. - GitLab Pages에 배포되는 중앙 문서 레포지토리는 이 아티팩트를
curl혹은 GitLab API를 통해 받아옵니다.
4. Docusaurus에서 API JSON 활용하기
src/pages/api.tsx (또는 .js) 파일을 추가해 API 데이터를 읽고, 원하는 형태로 렌더링합니다.
import React, { useEffect, useState } from 'react';
import Layout from '@theme/Layout';
import { API } from '@typedoc/api-json-schema';
export default function ApiPage() {
const [data, setData] = useState<API | null>(null);
useEffect(() => {
fetch('/api/service-a.json')
.then((res) => res.json())
.then(setData);
}, []);
if (!data) {
return <div>Loading...</div>;
}
return (
<Layout title="Service A API">
<main>
<h1>Service A API Reference</h1>
{/* 여기서 data를 순회하며 문서화 */}
</main>
</Layout>
);
}
fetch('/api/service-a.json')경로는 Docusaurusstatic/api/폴더에 복사된 파일을 가리킵니다.- 실제 구현에서는 검색, 필터링, 코드 하이라이트 등을 추가해 사용자 경험을 개선할 수 있습니다.
5. 배포 확인
main브랜치에 커밋을 푸시하면 GitLab CI가 자동으로 실행됩니다.- 파이프라인이 성공하면 GitLab Pages URL(예:
https://group.gitlab.io/docs-site/)에서 통합 문서를 확인할 수 있습니다. - 새로운 마이크로서비스를 추가하거나 기존 API가 변경될 경우 해당 서비스 레포지토리에서
typedoc만 다시 실행하면 중앙 문서가 자동으로 최신화됩니다.
결론
- Docusaurus + TypeDoc + GitLab CI 조합은 마이크로서비스 환경에서 중앙 집중식 문서를 손쉽게 구축할 수 있는 강력한 솔루션입니다.
- 각 서비스는 독립적으로 API 문서를 생성하고, 중앙 레포지토리는 이를 모아 정적 사이트 형태로 제공하므로 버전 관리, 배포, 검색이 모두 자동화됩니다.
다음 단계로는
- 검색 엔진 최적화(SEO) 설정,
- 버전별 문서 관리,
- 자동화된 테스트(예:
linkcheck) 등을 추가해 더욱 견고한 문서 플랫폼을 만들 수 있습니다.
여러분의 프로젝트에도 적용해 보시고, 궁금한 점이나 개선 아이디어가 있으면 언제든지 댓글로 알려 주세요!
현대 마이크로서비스 아키텍처에서는 문서가 수십 개의 저장소에 흩어지는 경우가 많습니다. 각 서비스가 자체 문서를 유지하고, 개발자는 정보를 찾기 위해 고군분투하며, 새로운 팀원을 온보딩하는 과정은 보물찾기와 같습니다. 저는 최근 중앙 집중식 문서 시스템을 구축하여 TypeDoc으로 생성된 API 문서와 사용자 가이드를 하나의 검색 가능한 Docusaurus 사이트에 자동으로 집계했습니다.
흩어진 문서의 문제점
우리 마이크로서비스 생태계는 시간이 지남에 따라 자연스럽게 성장했습니다. 각 저장소마다 자체 기술 문서를 가지고 있었지만, 이를 접근하려면 다음과 같은 절차가 필요했습니다:
- 어느 저장소를 찾아야 할지 파악하기
- 로컬에 클론하기
README파일을 탐색하기
신입 개발자에게는 이 과정이 압도적이었습니다. AI 학습용으로는 우리 아키텍처 전체를 포괄적으로 제공하는 것이 거의 불가능했습니다.
우리가 필요로 한 해결책은 다음과 같았습니다:
- TypeScript 코드베이스에서 API 문서를 자동으로 생성하고 중앙에 집중
- 코드 수준 문서와 함께 사용자 정의 문서 포함
- 최소한의 유지 보수 비용
- 코드 변경 시 자동 업데이트
- 모든 문서에 대한 단일 접근 지점 제공
아키텍처
솔루션은 서로 협력하는 세 가지 핵심 기술을 활용합니다:
| Technology | Role |
|---|---|
| TypeDoc | TypeScript 소스 코드(인터페이스, 클래스, 메서드, 인라인 주석)로부터 포괄적인 API 문서를 생성합니다. 각 마이크로서비스 저장소는 자체 문서 스냅샷을 생성합니다. |
| GitLab CI | 스케줄된 파이프라인을 통해 전체 프로세스를 처리합니다. 생성된 문서를 각 서비스 저장소에 커밋하는 대신(저장소가 부풀어 오르고 잡음이 발생할 수 있음), CI 파이프라인은 문서를 중앙 위치로 푸시합니다. |
| Docusaurus | 프레젠테이션 레이어 역할을 하며, 모든 서비스의 콘텐츠를 통합하여 빠르고 정적인 문서 사이트를 구축합니다. 이 정적 사이트는 GitLab Pages를 통해 배포됩니다. |
작동 방식: 파이프라인 흐름
단계 1 – 서비스‑레벨 문서 자동 생성
각 마이크로서비스 저장소에는 문서를 생성하는 간단한 Yarn 스크립트가 포함되어 있습니다:
{
"scripts": {
"docs": "typedoc --out docs src/"
}
}
Note: 생성된 문서는 서비스 저장소에 커밋되지 않습니다. 파이프라인 실행 중에만 일시적으로 존재합니다.
단계 2 – 예약된 문서 동기화
각 서비스 저장소에는 (보통 야간 또는 필요 시) 예약된 GitLab CI 파이프라인이 있으며, 다음 단계들을 수행합니다:
- Generate –
yarn docs를 실행하여 최신 TypeDoc 문서를 생성합니다. - Delete & Replace – 서비스의 기존 문서 디렉터리를 완전히 삭제하고 새로 생성된 문서로 교체합니다. 소스 저장소가 진실의 원천이므로 기존 문서를 단순히 덮어씁니다.
- Handle Race Conditions – 푸시하기 전에
git pull을 수행하고, 필요 시 짧은 재시도 간격을 두어 여러 파이프라인이 동시에 실행될 때 충돌을 방지합니다. - Push – 문서를 메인 문서 저장소의 서비스 이름 폴더에 커밋하고 푸시합니다.
- Trigger – 푸시가 자동으로 메인 문서 저장소의 재빌드 파이프라인을 트리거합니다.
이렇게 하면 서비스 저장소는 깔끔하게 유지되면서, 문서는 수동 개입 없이 최신 상태를 유지합니다.
단계 3 – 중앙 문서 빌드
메인 문서 저장소에는 Docusaurus 설정과 사용자 정의 문서가 포함되어 있습니다. 이 저장소의 파이프라인은 모든 커밋에 대해 트리거되며:
- 모든 서비스‑별 TypeDoc 문서를 포함해 전체 사이트를 재빌드합니다.
- 정적 사이트를 GitLab Pages에 배포합니다.
- 개발자에게 모든 문서를 한 번에 확인할 수 있는 단일 URL을 제공합니다.
왜 Docusaurus인가?
TypeDoc이 /docs 디렉터리에 직접 문서를 생성하고, Docusaurus도 콘텐츠를 /docs 디렉터리에서 기대합니다. 별도의 설정 없이도 완벽히 맞아떨어집니다.
맞춤형 문서 지원
자동 생성된 API 문서 외에도, 우리는 시스템을 확장하여 손으로 작성한 사용자 가이드, 아키텍처 개요, 온보딩 자료를 지원합니다. 이러한 문서는 모두 주제별로 정리된 표준 Markdown 파일 형태로 메인 문서 저장소에 직접 포함됩니다(서비스별이 아니라 주제별로 조직됨).
생성된 문서를 더욱 유용하게 만들기 위해 맞춤형 TypeDoc 플러그인을 만들었습니다. 이 플러그인은 원래 프로젝트 구조를 그대로 유지합니다. TypeDoc이 기본적으로 파일을 타입(클래스, 인터페이스 등)별로 재구성하는 대신, 플러그인은 소스 저장소에 존재하는 디렉터리 계층을 정확히 그대로 유지합니다.
예시:
소스 파일이 src/auth/services/UserService.ts인 경우, 문서도 동일한 경로 아래에 표시됩니다. 이는 특정 문서를 찾는 것이 직관적이라는 장점을 제공합니다—개발자는 이미 코드베이스에서 파일이 어디에 있는지 알고 있기 때문에, 문서 역시 그 위치에서 찾을 수 있습니다.
이러한 하이브리드 접근 방식은 TypeDoc의 자동화된 기술 정확성과 필요에 따라 인간이 직접 다듬은 설명을 결합하여, 양쪽의 장점을 모두 제공합니다.
혜택
AI 교육을 위해
모든 문서를 일관된 형식의 단일 저장소에 통합함으로써 전체 코드베이스의 컨텍스트를 언어 모델에 제공할 수 있었습니다. 이로 인해 AI가 생성하는 코드 제안 및 설명의 품질이 크게 향상되었습니다.
개발자 온보딩을 위해
새 팀원들은 이제 하나의 즐겨찾기만 있으면 됩니다. “인증 문서는 어느 레포에 있지?”라고 물어볼 필요 없이 문서 사이트에서 바로 검색하면 됩니다. 개발자들이 시스템 아키텍처와 API 계약을 수십 개의 레포를 복제하지 않고도 탐색할 수 있게 되면서 온보딩 시간이 눈에 띄게 단축되었습니다.
팀 간 협업을 위해
- 통합된 지식 베이스는 중복 작업을 줄여줍니다.
- 팀은 사이트에서 서로의 API를 직접 참조할 수 있어 재사용을 장려합니다.
- 업데이트가 자동으로 전파되어 모두가 최신 정보를 기반으로 작업할 수 있습니다.
TL;DR
- TypeDoc → 서비스별 API 문서를 생성 (레포 커밋 없이).
- GitLab CI → 야간 파이프라인이 문서를 중앙 레포에 푸시.
- Docusaurus → 모든 문서와 커스텀 마크다운을 모아 검색 가능한 정적 사이트로 집계.
그 결과: 모든 마이크로서비스 문서의 단일 진실의 원천이 마련되고, 유지 보수 부담이 감소하며, 온보딩 속도가 빨라지고, AI 지원 개발을 위한 풍부한 데이터셋을 확보할 수 있습니다.
통합이 쉬워졌습니다
팀이 서비스를 통합하거나 종속성을 이해해야 할 때, 이제 즉시 소스 코드를 파고들 필요가 없습니다. 중앙 집중식 문서는 인터페이스 계약, 사용 예시, 그리고 아키텍처 컨텍스트를 한눈에 제공합니다.
유지보수를 위해
문서 업데이트는 자동으로 이루어집니다. 개발자가 코드에 JSDoc 주석을 추가하면, 해당 주석은 다음 예약된 파이프라인 실행 후 중앙 문서에 표시됩니다. 수동으로 문서를 업데이트할 필요가 없습니다.
배운 교훈
충돌은 생각보다 간단합니다
여러 서비스가 동시에 문서를 푸시할 때 병합 충돌이 발생할까 걱정할 수 있습니다. 해결책은 간단합니다 – 이전 문서 디렉터리를 전체 삭제하고 새 디렉터리로 교체하면 됩니다. 소스 저장소가 진실의 원천이므로 오래된 문서를 보존하거나 병합할 필요가 없습니다. 소스에서 나온 최신 문서가 항상 우선합니다.
레이스 컨디션은 간단히 처리합니다
스케줄된 파이프라인이 동시에 실행될 경우, 메인 저장소에 푸시할 때 충돌이 발생할 수 있습니다. 우리는 푸시 전에 git pull을 수행하고, 푸시가 실패하면 몇 초간 대기하는 재시도 메커니즘을 추가함으로써 해결했습니다. 우아하지는 않지만 안정적으로 동작합니다.
# Example of the push logic
git pull --rebase
git push origin main || {
echo "Push failed – retrying in 5 seconds..."
sleep 5
git push origin main
}
서로 맞는 도구를 선택하세요
Docusaurus는 TypeDoc이 /docs에 출력하고 Docusaurus가 /docs를 읽기 때문에 명백한 선택이었습니다. 때로는 가장 좋은 기술적 결정이 가장 적은 설정을 요구하는 경우가 있습니다.
사용성을 위한 구조가 중요합니다
레포지토리의 디렉터리 구조를 그대로 유지하는 커스텀 TypeDoc 플러그인은 큰 차이를 만들었습니다. 개발자는 새로운 조직 방식을 배울 필요 없이, 기대하던 위치에 문서가 존재한다는 것을 알 수 있습니다.
GitLab Pages와 정적 사이트는 손쉽습니다
GitLab Pages에 배포하면 서버 관리가 필요 없고, 호스팅 비용도 없으며, HTTPS가 자동으로 적용됩니다. 정적 사이트는 2분 이내에 빌드되고 즉시 서비스됩니다.
결론
중앙 집중식 문서를 구축하는 데 복잡한 도구나 비용이 많이 드는 플랫폼이 필요하지 않습니다. GitLab CI pipelines, TypeDoc, Docusaurus, 그리고 GitLab Pages를 사용하여 전체 마이크로서비스 아키텍처 전반에 걸쳐 포괄적이고 검색 가능한 문서를 자동으로 유지하는 시스템을 만들었습니다.
투자는 즉시 효과를 발휘했습니다. 온보딩 속도가 빨라지고 AI 지원이 향상되었으며 개발자들의 불만이 감소했습니다. 디렉터리 구조를 보존하는 맞춤형 TypeDoc 플러그인은 문서를 직관적으로 탐색할 수 있게 했습니다. 충돌에 대한 간단한 접근 방식—삭제 후 교체—은 복잡성을 없애면서 부작용도 없었습니다. 가장 중요한 점은 시스템이 스스로 유지된다는 것입니다. 문서는 최신 상태를 유지하면서 개발 팀에게 부담이 되지 않습니다.
마이크로서비스 전반에 걸쳐 문서가 파편화되어 고민하고 있다면, 이 접근 방식은 아키텍처와 함께 확장 가능한 실용적이고 유지 관리가 쉬운 솔루션을 제공합니다.