🤖

claude-code-actionをForgejo対応させてみた話

に公開

はじめに

Anthropicが公開しているGitHub Actionsで使えるAIアシスタント「claude-code-action」をForgejo対応させました。ForgejoはGitHub互換のGitホスティングサービスですが、すんなりとはいかず、予想以上に大変でした。本記事では、その修正内容と使い方について説明します。

リポジトリ: https://github.com/yellowback/forgejo-claude-code-action

claude-code-actionとは

claude-code-actionは、Anthropicが公式に提供している、Claude AIを使用してPRやIssueで自動的にコードレビューや実装支援を行うGitHub Actionです。主な機能は以下の通りです:

  • PRやIssueへのコメントに対する自動応答
  • コードレビューと改善提案
  • 実装の自動化
  • ドキュメントの自動更新
  • @claude メンション(タグモード)または自動実行(エージェントモード)での動作

Forgejoとは

ForgejoはGiteaからフォークされたオープンソースのGitホスティングサービスです。GitHub互換を目指していますが、実際にはいくつかの重要な違いがあります。

GitHub互換だが思った以上に大変だった点

ForgejoがGitHub互換とはいえ、claude-code-actionを移植する際にいくつかの大きな課題に直面しました。

1. GraphQL APIが存在しない

最大の違いは、ForgejoにGraphQL APIがないことです。GitHub版のclaude-code-actionはGraphQLを多用していたため、すべてのAPIコールをREST APIに書き換える必要がありました。

- const { data } = await graphql(query, variables);
+ const response = await fetch(`${forgejoUrl}/api/v1/repos/${owner}/${repo}/issues/${number}`, {
+   headers: { 'Authorization': `token ${token}` }
+ });

2. 認証方式の違い

GitHubでは以下の認証方式がサポートされています:

  • GitHub App
  • Personal Access Token
  • OIDCによる一時トークン

一方、Forgejoでは:

  • Personal Access Tokenのみ

GitHub Appのような高度な認証機能がないため、トークン管理がシンプルになる反面、権限管理の柔軟性が失われました。

3. ActionsランナーとワークフローパスPの違い

ワークフローファイルの配置場所

- .github/workflows/claude.yml
+ .forgejo/workflows/claude.yml

ランナーの指定方法

- runs-on: ubuntu-latest
+ runs-on: docker

Forgejoでは独自のランナー(Forgejo Runner)を使用し、Dockerコンテナ内で実行されます。

4. APIレスポンスの微妙な違い

GitHub互換とはいえ、APIレスポンスの構造に微妙な違いがありました:

  • 一部のフィールド名の違い
  • ページネーションの実装方法
  • エラーレスポンスの形式

これらの違いを吸収するため、アダプター層を実装する必要がありました。

実装時の具体的な課題と解決方法

課題1: GraphQL to REST APIの変換

GraphQLクエリを解析し、対応するREST APIエンドポイントに変換するロジックを実装しました。

// GraphQLクエリの例
const query = `
  query($owner: String!, $name: String!, $number: Int!) {
    repository(owner: $owner, name: $name) {
      pullRequest(number: $number) {
        title
        body
        comments(first: 100) {
          nodes {
            body
            author {
              login
            }
          }
        }
      }
    }
  }
`;

// REST APIへの変換
async function getPullRequestData(owner: string, repo: string, number: number) {
  const pr = await fetch(`${forgejoUrl}/api/v1/repos/${owner}/${repo}/pulls/${number}`);
  const comments = await fetch(`${forgejoUrl}/api/v1/repos/${owner}/${repo}/issues/${number}/comments`);
  
  return {
    repository: {
      pullRequest: {
        ...pr,
        comments: {
          nodes: comments
        }
      }
    }
  };
}

課題2: 依存関係の手動インストール

Forgejo Runnerのコンテナイメージには必要なツールが含まれていないため、ワークフロー内で手動インストールが必要でした。

- name: Install dependencies
  run: |
    apt-get update
    apt-get install -y curl git jq

課題3: APIレート制限への対応

REST APIはGraphQLよりも多くのリクエストが必要になるため、レート制限に配慮した実装が必要でした。

async function fetchWithRetry(url: string, options: RequestInit, maxRetries = 3) {
  for (let i = 0; i < maxRetries; i++) {
    try {
      const response = await fetch(url, options);
      if (response.status === 429) {
        const retryAfter = response.headers.get('X-RateLimit-Reset');
        await sleep(retryAfter);
        continue;
      }
      return response;
    } catch (error) {
      if (i === maxRetries - 1) throw error;
    }
  }
}

使い方とセットアップ手順

前提条件

  1. Forgejoインスタンス(Actionsが有効化されていること)
    • 動作確認済みバージョン:Forgejo 11.0.2
  2. Forgejo Runner(インストール済み)
  3. 認証トークン(いずれか必須)
    • Anthropic APIキー:APIを直接利用する場合
    • Claude Code OAuthトークン:Claude Code PRO/MAXユーザーの場合

セットアップ手順

1. シークレットの設定

リポジトリの設定画面で以下のシークレットを追加:

FORGEJO_TOKEN: Forgejoのアクセストークン

# 以下のいずれか1つが必須
ANTHROPIC_API_KEY: Anthropic APIキー(APIを直接利用する場合)
CLAUDE_CODE_OAUTH_TOKEN: Claude Code OAuthトークン(Claude Code PRO/MAXユーザーの場合)

2. ワークフローファイルの作成

.forgejo/workflows/claude.ymlを作成:

name: Claude Code Assistant

on:
  issue_comment:
    types: [created]
  pull_request_review_comment:
    types: [created]
  issues:
    types: [opened]
  pull_request:
    types: [opened]

jobs:
  claude:
    runs-on: docker
    container:
      image: ubuntu:latest
    
    steps:
    - name: Install dependencies
      run: |
        apt-get update
        apt-get install -y curl git jq nodejs
    
    - name: Checkout
      uses: actions/checkout@v4
    
    - name: Run Claude Code Action
      uses: https://github.com/yellowback/forgejo-claude-code-action@forgejo
      with:
        forgejo-token: ${{ secrets.FORGEJO_TOKEN }}
        claude-code-oauth-token: ${{ secrets.CLAUDE_CODE_OAUTH_TOKEN }}

3. 使用方法

IssueやPRで@claudeをメンションすると、Claudeが応答します:

@claude このPRのコードをレビューしてください

詳しい使い方については、Anthropic公式のclaude-code-actionドキュメントを参照してください。基本的な使い方はGitHub版と同じです。

設定オプション

パラメータ 説明 必須 デフォルト
forgejo-token Forgejoアクセストークン -
claude-code-oauth-token Claude Code OAuthトークン -
anthropic-api-key Anthropic APIキー -

※ シークレットにANTHROPIC_API_KEYまたはCLAUDE_CODE_OAUTH_TOKENのいずれかが必須
※ Claude Code PRO/MAXユーザーはCLAUDE_CODE_OAUTH_TOKENを使用することで、APIキーの管理が不要になります

まとめ

ForgejoへのClaude Code Actionの移植は、以下の点で予想以上に大変でした:

  1. GraphQL非対応 - すべてのAPIコールをREST APIに書き換え
  2. 認証方式の制限 - トークン認証のみ対応
  3. ランナー環境の違い - Dockerコンテナでの実行と依存関係の管理
  4. API仕様の微妙な違い - レスポンス構造の差異への対応

しかし、これらの課題を解決することで、Forgejoでも高度なAIアシスタント機能を利用できるようになりました。セルフホストのGitサービスでもAIによる開発支援を受けられるのは大きなメリットです。

ぜひForgejoユーザーの方は試してみてください!

関連プロジェクト

Forgejo対応のClaude Code Actionには、他にも以下のような実装があります:

  • Sunwood-ai-labs/claude-code-action-forgejo
    • Bunランタイムを使用した実装
    • 日本語に完全対応
    • リアルタイムの絵文字リアクションでワークフロー状態を表示
    • セキュリティ重視の最小権限設計

それぞれ異なるアプローチで実装されているので、用途に応じて選択できます。

参考リンク

Discussion