GitHub Actions로 게시 자동화하기

GitHub Actions로 게시 자동화하기 (How to Automate Publishing with GitHub Actions)

레지스트리에 서버를 게시하는 과정을 GitHub Actions 워크플로로 자동화할 수 있어요. 이 글은 버전 태그를 푸시할 때마다 MCP 서버를 레지스트리에 자동 게시하는 워크플로를 만드는 방법을 단계별로 안내합니다.

출처: MCP 공식 문서 - How to Automate Publishing with GitHub Actions

💡 MCP 레지스트리는 현재 프리뷰 단계예요. 일반 공개 전에 파괴적 변경이나 데이터 리셋이 있을 수 있습니다. 이슈가 있으면 GitHub에 보고해 주세요.

1단계: 워크플로 파일 만들기

서버 프로젝트 디렉토리에 .github/workflows/publish-mcp.yml 파일을 만드세요. 다음은 npm 기반 로컬 서버의 예시이지만, MCP 레지스트리 게시 단계는 모든 패키지 유형에서 동일해요.

OIDC 인증(권장):

name: Publish to MCP Registry

on:
  push:
    tags: ["v*"] # Triggers on version tags like v1.0.0

jobs:
  publish:
    runs-on: ubuntu-latest
    permissions:
      id-token: write # Required for OIDC authentication
      contents: read

    steps:
      - name: Checkout code
        uses: actions/checkout@v5

      ### Publish underlying npm package:

      - name: Set up Node.js
        uses: actions/setup-node@v5
        with:
          node-version: "lts/*"

      - name: Install dependencies
        run: npm ci

      - name: Run tests
        run: npm run test --if-present

      - name: Build package
        run: npm run build --if-present

      - name: Publish package to npm
        run: npm publish
        env:
          NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}

      ### Publish MCP server:

      - name: Install mcp-publisher
        run: |
          curl -L "https://github.com/modelcontextprotocol/registry/releases/latest/download/mcp-publisher_$(uname -s | tr '[:upper:]' '[:lower:]')_$(uname -m | sed 's/x86_64/amd64/;s/aarch64/arm64/').tar.gz" | tar xz mcp-publisher

      - name: Authenticate to MCP Registry
        run: ./mcp-publisher login github-oidc

      # Optional:
      # - name: Set version in server.json
      #   run: |
      #     VERSION=${GITHUB_REF#refs/tags/v}
      #     jq --arg v "$VERSION" '.version = $v' server.json > server.tmp && mv server.tmp server.json

      - name: Publish server to MCP Registry
        run: ./mcp-publisher publish

PAT 인증:

name: Publish to MCP Registry

on:
  push:
    tags: ["v*"] # Triggers on version tags like v1.0.0

jobs:
  publish:
    runs-on: ubuntu-latest
    permissions:
      contents: read

    steps:
      - name: Checkout code
        uses: actions/checkout@v5

      ### Publish underlying npm package:

      - name: Set up Node.js
        uses: actions/setup-node@v5
        with:
          node-version: "lts/*"

      - name: Install dependencies
        run: npm ci

      - name: Run tests
        run: npm run test --if-present

      - name: Build package
        run: npm run build --if-present

      - name: Publish package to npm
        run: npm publish
        env:
          NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}

      ### Publish MCP server:

      - name: Install mcp-publisher
        run: |
          curl -L "https://github.com/modelcontextprotocol/registry/releases/latest/download/mcp-publisher_$(uname -s | tr '[:upper:]' '[:lower:]')_$(uname -m | sed 's/x86_64/amd64/;s/aarch64/arm64/').tar.gz" | tar xz mcp-publisher

      - name: Authenticate to MCP Registry
        run: ./mcp-publisher login github --token ${{ secrets.MCP_GITHUB_TOKEN }}

      # Optional:
      # - name: Set version in server.json
      #   run: |
      #     VERSION=${GITHUB_REF#refs/tags/v}
      #     jq --arg v "$VERSION" '.version = $v' server.json > server.tmp && mv server.tmp server.json

      - name: Publish server to MCP Registry
        run: ./mcp-publisher publish

DNS 인증:

name: Publish to MCP Registry

on:
  push:
    tags: ["v*"] # Triggers on version tags like v1.0.0

jobs:
  publish:
    runs-on: ubuntu-latest
    permissions:
      contents: read

    steps:
      - name: Checkout code
        uses: actions/checkout@v5

      ### Publish underlying npm package:

      - name: Set up Node.js
        uses: actions/setup-node@v5
        with:
          node-version: "lts/*"

      - name: Install dependencies
        run: npm ci

      - name: Run tests
        run: npm run test --if-present

      - name: Build package
        run: npm run build --if-present

      - name: Publish package to npm
        run: npm publish
        env:
          NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}

      ### Publish MCP server:

      - name: Install mcp-publisher
        run: |
          curl -L "https://github.com/modelcontextprotocol/registry/releases/latest/download/mcp-publisher_$(uname -s | tr '[:upper:]' '[:lower:]')_$(uname -m | sed 's/x86_64/amd64/;s/aarch64/arm64/').tar.gz" | tar xz mcp-publisher

      # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
      # TODO: Replace `example.com` with your domain name
      # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
      - name: Authenticate to MCP Registry
        run: ./mcp-publisher login dns --domain example.com --private-key ${{ secrets.MCP_PRIVATE_KEY }}

      # Optional:
      # - name: Set version in server.json
      #   run: |
      #     VERSION=${GITHUB_REF#refs/tags/v}
      #     jq --arg v "$VERSION" '.version = $v' server.json > server.tmp && mv server.tmp server.json

      - name: Publish server to MCP Registry
        run: ./mcp-publisher publish

2단계: 시크릿 추가

선택한 인증 방법에 따라 저장소에 시크릿을 추가해야 할 수 있어요.

  • GitHub OIDC 인증: 전용 시크릿 불필요.
  • GitHub PAT 인증: read:orgread:user 스코프를 가진 GitHub Personal Access Token(PAT)으로 MCP_GITHUB_TOKEN 시크릿 추가.
  • DNS 인증: Ed25519 비공개 키로 MCP_PRIVATE_KEY 시크릿 추가.

패키지 레지스트리용 시크릿도 추가해야 할 수 있어요. 예를 들어 위 워크플로는 npm 토큰이 담긴 NPM_TOKEN 시크릿이 필요해요.

저장소에 시크릿을 추가하는 방법은 GitHub Actions에서 시크릿 사용하기를 보세요.

3단계: 태그 만들고 릴리스

워크플로를 트리거하려면 버전 태그를 만들고 푸시하세요.

git tag v1.0.0
git push origin v1.0.0

워크플로가 테스트를 실행하고, 패키지를 빌드하고, 패키지를 npm에 게시하고, 서버를 MCP 레지스트리에 게시할 거예요.

문제 해결

오류 메시지 조치
"Authentication failed" OIDC용으로 id-token: write 권한이 설정됐는지 확인하거나, 시크릿을 확인하세요.
"Package validation failed" 패키지가 패키지 레지스트리(예: npm, PyPI)에 성공적으로 게시됐는지, 패키지에 필요한 검증 정보가 있는지 확인하세요.

더 알아보기 (Learn more)