Files
claude-code-action/prds/done/5-dedicated-forgejo-user.md
T
Vlad MocanuandClaude Opus 4.6 2f7d0a7fb2 docs(prd-5): mark complete and archive to prds/done/ [skip ci]
- All milestones delivered, E2E validated on PR #8
- Deferred: commit authorship E2E, cross-repo test

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-25 21:11:20 +02:00

6.1 KiB

PRD #5: Dedicated Forgejo User for Claude Bot

Issue: #5 Priority: High Created: 2026-02-25 Status: Complete (2026-02-25)


Problem

Claude currently runs under the human operator's personal Forgejo token (FORGEJO_TOKEN / github_token). This causes:

  1. Attribution confusion: Commits and comments appear as the human user, not as a bot
  2. Over-privileged access: The bot inherits all permissions of the human account
  3. Audit trail: No clear separation between human actions and bot actions in repo history
  4. Security: If the action is compromised, the human's full token is exposed

On GitHub, this is solved by the GitHub App OIDC token exchange (bot gets its own claude[bot] identity). On Forgejo, there's no such mechanism — we need a manual equivalent.

Solution

Create a dedicated claude-bot user on the Forgejo instance (git.wxs.ro), generate a scoped API token for it, and configure the action workflow to use that token. This gives Claude its own identity for commits, comments, and API operations.

Milestones

Phase 1: Forgejo Admin Setup

  • M1: Create dedicated claude-bot user on git.wxs.ro

    • Create user via Forgejo admin panel or API (POST /admin/users)
    • Set appropriate display name (e.g., "Claude Bot")
    • Set avatar to distinguish from human users
    • User should NOT have admin privileges
    • Validation: User exists and can log in
    • Evidence: User ID 48, is_admin: false, avatar set to Claude logo
  • M2: Configure bot user permissions and token

    • Add claude-bot to the actions org (and any other orgs where the action runs)
    • Grant write permission on repos where Claude needs to operate
    • Generate a scoped API token for the bot user with minimal required permissions:
      • repo (read/write issues, PRs, comments, branches, commits)
      • packages (if needed for container operations)
      • NO admin scope, NO user scope beyond what's needed
    • Validation: Token can create comments and push branches on a test repo
    • Evidence: Claude team with write permission created in all 12 orgs, token validated (comment create/delete on issue #5, push: true on k8s/flux, crossplane/harbor-resources)

Phase 2: Action Configuration

  • M3: Update workflow to use bot token

    • Store the bot token as a Forgejo Actions secret (e.g., CLAUDE_BOT_TOKEN)
    • Update claude.yml workflow to pass github_token: ${{ secrets.CLAUDE_BOT_TOKEN }} instead of the human token
    • Update bot_id and bot_name inputs to match the new Forgejo user's ID and username
    • Document the token rotation procedure
    • Validation: Action runs with bot token, comments appear as claude-bot
    • Evidence: CLAUDE_BOT_TOKEN org secret in all 12 orgs, claude.yml updated with bot_id: "48", bot_name: "claude-bot", bot_email: "claude@wxs.ro". New bot_email input added to action.yml.
    • E2E validated: @claude mention on PR #8 — claude-bot responded with full review, tracking comment updated correctly
  • M4: Verify git commit attribution

    • Ensure git config user.name and user.email use the bot user's identity
    • Verify that src/github/operations/git-config.ts correctly picks up the bot user info from the token
    • Test that pushed commits show the bot user as author in Forgejo UI
    • Validation: A tag-mode response that creates a branch shows claude-bot as commit author
    • Evidence: git-config.ts uses user.email when provided (falls back to noreply), context.ts reads BOT_EMAIL env var, all call sites pass botEmail. 797 tests pass.
    • Deferred: Branch creation + commit authorship E2E (will be validated naturally on next code-changing @claude request)

Phase 3: Documentation & Hardening

  • M5: Update documentation and test across repos
    • Update docs/forgejo.md with bot user setup instructions (full 6-step guide added)
    • Document token rotation procedure (tokens expire, need renewal plan)
    • [~] Test the bot user setup on at least one additional repo beyond claude-code-action (deferred — bot token is org-level, will work on first use)
    • Update CLAUDE.md if any workflow changes affect development
    • Validation: Another developer can follow the docs to set up the bot user on a new Forgejo instance

Dependencies

  • Forgejo admin access to git.wxs.ro (to create the user)
  • Understanding of Forgejo's permission model (org membership, repo access)

Risks

Risk Mitigation
Token expiration Document rotation procedure, set long-lived token or calendar reminder
Bot user locked out Keep admin access to reset password/token
Permission too narrow Start with write on repos, expand only if needed
Bot user confused with human in reviews Set clear display name and avatar

Success Criteria

  • All Claude comments and commits on Forgejo repos appear as claude-bot, not the human user
  • The bot token has minimal scoped permissions (no admin access)
  • Documentation allows reproducing the setup on a fresh Forgejo instance

Implementation Notes

New bot_email Action Input

Added bot_email input to action.yml — when set, overrides the default noreply email format ({id}+{name}@users.noreply.{host}). On Forgejo, setting this to the bot user's registered email links commits to the bot's profile in the UI.

Org-Level Secrets

CLAUDE_BOT_TOKEN is stored as an org-level secret (not repo-level) in all 12 orgs with visibility: "all". This means any new repo in any org will automatically have access.

Team Structure

Each org has a Claude team with write permission on all repositories (includes_all_repositories: true). New repos are automatically covered.