コンテンツにスキップ

CI/CDパイプライン

KanjiIQは継続的インテグレーションとデプロイメントにForgejo Actionsを使用しています。Forgejo ActionsはGitHub Actions YAML構文と互換性があり、セルフホストランナーで動作します。

ワークフロー構造

.forgejo/workflows/
├── deploy-frontend.yml    # Build & deploy Flutter Web
├── deploy-backend.yml     # Build & deploy Dart Frog API
└── deploy-docs.yml        # Build & deploy documentation site

各ワークフローは同じパターンに従います:

graph TD
    A[Push to main] --> B{Path filter<br/>matches?}
    B -->|Yes| C[Checkout code]
    B -->|No| X[Skip]
    C --> D[Login to Forgejo<br/>Container Registry]
    D --> E[Docker build<br/>--no-cache]
    E --> F[Push :latest +<br/>:COMMIT_SHA]
    F --> G[kubectl set image]
    G --> H[Wait for rollout<br/>timeout: 5m]
    H --> I[Cleanup: logout]

フロントエンドワークフロー

name: Deploy Frontend to k3s

on:
  push:
    branches: [main]
    paths:
      - 'frontend/**'
      - 'Dockerfile.frontend'
      - 'nginx.frontend.conf'

jobs:
  build-and-deploy:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4

      - name: Login to registry
        run: echo "$FORGEJO_TOKEN" | docker login $REGISTRY_URL -u $REGISTRY_USER --password-stdin

      - name: Build image
        run: |
          docker build --no-cache --pull \
            --build-arg CACHEBUST=$(date +%s) \
            -f Dockerfile.frontend \
            -t <registry>/jlpt-kanji-frontend:latest \
            -t <registry>/jlpt-kanji-frontend:$(git rev-parse --short HEAD) .

      - name: Push & deploy
        run: |
          docker push <registry>/jlpt-kanji-frontend:latest
          docker push <registry>/jlpt-kanji-frontend:$(git rev-parse --short HEAD)
          kubectl set image deployment/jlpt-kanji \
            frontend=<registry>/jlpt-kanji-frontend:$(git rev-parse --short HEAD) \
            -n jlpt-kanji
          kubectl rollout status deployment/jlpt-kanji -n jlpt-kanji --timeout=5m

シークレット

ワークフローは単一のシークレットを使用します:

シークレット 用途
FORGEJO_TOKEN コンテナレジストリへのプッシュとKubernetesアクセスの認証

トークンはForgejoのリポジトリ設定 > シークレットで設定されます。

イメージレジストリ

すべてのイメージはForgejo Container Registryに保存されます:

<registry>/jlpt-kanji-frontend:latest
<registry>/jlpt-kanji-frontend:<commit-sha>
<registry>/jlpt-kanji-backend:latest
<registry>/jlpt-kanji-backend:<commit-sha>
<registry>/jlpt-kanji-docs:latest
<registry>/jlpt-kanji-docs:<commit-sha>

ロールアウト検証

kubectl set imageの後、ワークフローはロールアウトの完了を待ちます:

kubectl rollout status deployment/jlpt-kanji -n jlpt-kanji --timeout=5m

これは以下のいずれかまでブロックされます:

  • すべての新しいPodがreadinessプローブを通過する、または
  • タイムアウトが期限切れになる(ワークフローが失敗し、開発者に通知)

ロールアウトが失敗した場合、Kubernetesは自動的にロールアウトを停止し、以前のバージョンがトラフィックの配信を継続します。

手動ロールバック

以前のバージョンに戻すには:

# Rollback to previous revision
kubectl rollout undo deployment/jlpt-kanji -n jlpt-kanji

# Or roll back to a specific image
kubectl set image deployment/jlpt-kanji \
  frontend=<registry>/jlpt-kanji-frontend:<previous-sha> \
  -n jlpt-kanji