AgentSkillsCN

subagent

作为 Clubhouse 项目问题的子代理开展工作。认领待处理的问题,创建 Git 工作树,按照项目规范实现功能,运行针对性测试,创建拉取请求,并及时回应评审反馈。

SKILL.md
--- frontmatter
name: subagent
description: Work as a subagent on Clubhouse project issues. Claim available issues, create git worktrees, implement features following project patterns, run targeted tests, create pull requests, and address review feedback.

Subagent Instructions

You are a subagent for the Clubhouse project. Your job is to claim an issue, implement it in a dedicated worktree, open a PR, and then address any review feedback until the PR is merged.

Step 1: Claim an Issue and Create a Worktree

From the main repository root, run the start script:

bash
.codex/skills/subagent/scripts/start-agent.sh

The script will:

  1. Find the next available issue (dependencies satisfied, bugs prioritized)
  2. Atomically claim it in the work queue
  3. Create a dedicated git worktree

It outputs two lines:

code
ISSUE_NUMBER=<number>
WORKTREE_PATH=<path>

Parse these values. You will use them throughout the rest of the workflow.

Step 2: Change to the Worktree

bash
cd <WORKTREE_PATH>

Mandatory: Do all work from the designated worktree. Never edit or run commands from the main repo root once the worktree is created.

CRITICAL: Worktree Isolation Rules:

  • NEVER create, edit, or delete files outside your worktree
  • NEVER run git add, git commit, or git push from the main repository root
  • ALWAYS verify your current working directory before any file operation: pwd
  • ALWAYS use absolute paths within your worktree (e.g., <WORKTREE_PATH>/backend/...)
  • If you accidentally create or modify files outside your worktree, you MUST immediately fix this (see "Worktree Contamination Check" below)

Frontend Setup (if applicable): If the issue involves frontend work, run npm install in the frontend directory first to ensure dependencies are ready:

bash
cd frontend && npm install && cd ..

Autonomy: After entering the worktree, start the task immediately. Do not wait for any further input until the PR is opened.

Step 3: Fetch Issue Context

bash
# Use GitHub MCP server's github_get_issue tool

Read the issue description and acceptance criteria. This is your specification.

Step 4: Get Code Context (Efficiently)

Use the reference tables below to go directly to the files you need. Do not explore broadly.

Key File Locations

All paths relative to backend/internal/:

DomainHandlerServiceHandler Tests
Authhandlers/auth.goservices/session.go-
Postshandlers/post.goservices/post.gohandlers/post_test.go
Commentshandlers/comment.goservices/comment.gohandlers/comment_test.go
Reactionshandlers/reaction.goservices/reaction.gohandlers/reaction_test.go
Usershandlers/user.goservices/user.gohandlers/user_test.go
Sectionshandlers/section.goservices/section.gohandlers/section_test.go
Adminhandlers/admin.go-handlers/admin_test.go
Searchhandlers/search.goservices/search.gohandlers/search_test.go
Notificationshandlers/notification.goservices/notification.go-
WebSockethandlers/websocket.go--
Pub/Subhandlers/pubsub.go-handlers/pubsub_test.go

Other key files:

  • models/ - Request/response types, ErrorResponse struct
  • middleware/ - Auth, logging, etc.
  • db/ - Database initialization

Schema Quick Reference

Foreign keys to users always use user_id (NOT author_id):

  • posts.user_id, comments.user_id, reactions.user_id
  • mentions.mentioned_user_id, notifications.user_id
  • audit_logs.admin_user_id

Soft deletes: deleted_at timestamp + deleted_by_user_id

All IDs are UUIDs

Check backend/migrations/ only for the specific table you need.

Only read full files if you need more detail:

  • AGENTS.md - Code standards (skim relevant sections)
  • DESIGN.md - Only if you need API spec details

What NOT to Explore

  • Backend-only issues: Don't read frontend code
  • Frontend-only issues: Don't read backend code
  • Schema lookups: Don't read all migrations — just the table you need
  • Don't read DESIGN.md fully — use the schema reference above
  • Don't read all of AGENTS.md — skim for your specific domain

Step 5: Implement the Feature

Follow the issue description and acceptance criteria.

Pattern Examples

New endpoint handler:

go
// Copy pattern from handlers/post.go
func (h *Handler) YourEndpoint(w http.ResponseWriter, r *http.Request) {
    ctx := r.Context()
    userID := ctx.Value(middleware.UserIDKey).(string)
    // ... parse request, call service, return JSON
}

Error responses:

go
models.ErrorResponse{Error: "message", Code: "ERROR_CODE"}

Standard error codes: INVALID_REQUEST, UNAUTHORIZED, FORBIDDEN, NOT_FOUND, CONFLICT, INTERNAL_ERROR

Add Audit Logging (When Required)

All state-changing operations must emit an audit event. This applies to:

  • Admin actions (approve/reject user, hard delete, restore, toggle settings)
  • User actions that mutate persistent state (delete post/comment, restore own content)

Audit event format:

  • action: snake_case action name (e.g., delete_post, approve_user, toggle_link_metadata)
  • target_user_id: user affected by the action (nullable; use the closest related user)
  • metadata: JSON map with relevant IDs and context

Common action names (use these for consistency): approve_user, reject_user, delete_post, hard_delete_post, restore_post, delete_comment, hard_delete_comment, restore_comment, generate_password_reset_token, toggle_link_metadata, update_section, delete_section

Example:

go
auditQuery := `
    INSERT INTO audit_logs (admin_user_id, action, related_comment_id, related_user_id, created_at)
    VALUES ($1, 'delete_comment', $2, $3, now())`
_, err := tx.ExecContext(ctx, auditQuery, adminUserID, commentID, commentUserID)

See AGENTS.md "Audit Logging" section for full details.

Add Observability (When Required)

New endpoints and operations must include OpenTelemetry signals per DESIGN.md Section 9:

Traces:

  • Every new HTTP endpoint should be traced
  • Include span attributes: user_id, section_id, post_id, error details
  • Database queries should be traced

Metrics:

  • Business operations (posts created, comments added, deletes, etc.) should emit metrics
  • HTTP request counts and durations (usually handled by middleware)

Logs:

  • Use internal/observability functions: LogDebug, LogInfo, LogWarn, LogError
  • Never use fmt.Println or standard log package
  • Include structured key-value pairs

If your implementation adds new endpoints or business operations, follow existing patterns in handlers/services for observability.

Add Tests (When It Makes Sense)

If you change or add backend logic, add or update unit tests (services/) and handler tests (handlers/) where applicable. If you change frontend logic, add frontend unit tests (stores/services) and component tests (Svelte) where reasonable. If the change affects critical user flows, add or extend E2E tests (Playwright) to cover the new behavior. If tests are not reasonable for the change, state why in the PR description.

If you added audit logging, add/extend tests to verify audit logs are written when expected.

Tests should pass before finalizing an issue. If you're explicitly instructed that tests may fail, create follow-up issues per failing domain and link them in the PR description.

Step 6: Test Your Changes

Run only tests for your domain instead of the full suite:

bash
# Backend - build first, then test your domain only
cd backend && go build ./...
go test ./internal/handlers/your_handler_test.go -v
go test ./internal/services/your_service_test.go -v

# Frontend (if applicable)
cd frontend && npm run check
npm run test -- --grep "YourComponent"

Only run full test suite (go test ./...) before creating PR.

Step 7: Commit and Push

bash
git add .
git commit -m "feat(issue-<ISSUE_NUMBER>): description"
git push -u origin <BRANCH_NAME>

Update Markdown Docs (When Relevant)

If your changes affect behavior, setup, or architecture, update relevant markdown docs (README, DESIGN, AGENTS, docs/, or these instructions) to reflect the new reality.

Step 8: Create Pull Request

bash
# Use GitHub MCP server's github_create_pull_request tool
# Title: "Issue Title"
# Body:
## Summary
- ...

Closes #<ISSUE_NUMBER>

Step 9: Wait for Review and Address Feedback

After opening the PR, wait for instructions. The reviewer or orchestrator will either:

  • Merge it — you are done.
  • Post feedback — you must address it (see below).
  • Ask you to rebase — see the rebase section below.

Handling Review Feedback

When you receive review feedback on your PR:

  1. Read all comments on the PR:

    bash
    # Use GitHub MCP server's github_list_pull_request_comments tool
    
  2. Implement the requested fixes in the worktree. Address every comment — do not skip or defer items unless explicitly told to.

  3. Test your fixes the same way as Step 6 (targeted tests for the affected domain).

  4. Commit and push the fixes:

    bash
    git add .
    git commit -m "fix(issue-<ISSUE_NUMBER>): address review feedback"
    git push
    
  5. Wait again for the next round of review. Repeat this cycle until the PR is merged or you are told to stop.

Rebasing on Main

If instructed to rebase (e.g., due to merge conflicts):

bash
git fetch origin main
git rebase origin/main
# Resolve any conflicts, then:
git push --force-with-lease

After rebasing, wait for the next review cycle.

Important Notes

  1. Always use the start script (.codex/skills/subagent/scripts/start-agent.sh) — it handles claiming atomically
  2. CRITICAL: Work in the designated worktree ONLY — NEVER use the main repo for edits/commands once a worktree exists. This is the most important rule. Violations break the orchestrator.
  3. Use the file location table above — don't explore; go directly to the right files
  4. Copy existing patterns — check one similar handler/service, not multiple
  5. Add tests when it makes sense — include frontend tests; explain in PR if you didn't add tests
  6. Add audit logging for state-changing operations — see "Add Audit Logging" section above
  7. Add observability signals for new endpoints — see "Add Observability" section above
  8. Failing tests policy — tests must pass unless explicitly told otherwise; if allowed to fail, file follow-up issues and link them in the PR
  9. Don't skip dependencies — the script handles this automatically
  10. Rebase if asked — rebase on main when the reviewer requests it; never merge main into your branch
  11. Minimize exploration — see "What NOT to Explore" section
  12. Start immediately — once in the worktree, begin work without waiting for more user input; keep going until the PR is opened
  13. No confirmation prompts — never ask whether to run extra tests or whether to commit/create a PR; decide and proceed without asking
  14. Worktree contamination checks — run the contamination check (see below) after EVERY file operation, commit, and before pushing. If contamination is detected, fix it immediately.
  15. Stay alive after PR — do not exit after creating the PR. Wait for review feedback and address it until the PR is merged.
  16. Do not spawn sub-agents — you are already the subagent; proceed with this workflow directly.

Taskfile Maintenance

If you discover a useful command or workflow that could benefit other developers:

  1. Check if a similar task already exists: task --list
  2. Add the task to Taskfile.yml following existing patterns
  3. Use appropriate namespace (dev:, backend:, frontend:, db:, docker:, ci:, queue:, agent:)
  4. Include a desc: field for discoverability
  5. Mention the new task in your PR description

Worktree Contamination Check

Run this check after EVERY commit and before EVERY push. Also run it if you're unsure whether you accidentally modified files outside your worktree.

Step 1: Detect Contamination

From your worktree, check for changes in the main repository root:

bash
# Get the main repo root (parent of .worktrees)
MAIN_REPO=$(dirname $(dirname <WORKTREE_PATH>))

# Check for any uncommitted changes in main repo (excluding orchestrator-managed files)
git -C "$MAIN_REPO" status --porcelain | grep -v '.work-queue.json' | grep -v '.work-queue.lock'

Expected output: Empty. (.work-queue.json and .work-queue.lock are managed by the orchestrator and can be ignored.)

If you see other files listed, you have contaminated the main repo. Proceed to Step 2.

Step 2: Identify Your Changes

Determine which contaminated files belong to your issue:

bash
# List the contaminated files (excluding orchestrator-managed files)
git -C "$MAIN_REPO" status --porcelain | grep -v '.work-queue.json' | grep -v '.work-queue.lock'

Step 3: Move Changes to Your Worktree

For each contaminated file that belongs to your issue:

bash
# Example: if you accidentally created backend/internal/handlers/foo.go in main repo
# Move it to your worktree
mv "$MAIN_REPO/backend/internal/handlers/foo.go" "<WORKTREE_PATH>/backend/internal/handlers/foo.go"

Step 4: Discard Remaining Contamination

After moving your files, discard any remaining contamination (files that don't belong to your issue):

bash
# Discard all uncommitted changes in main repo (except orchestrator-managed files)
cd "$MAIN_REPO"
git checkout -- . 2>/dev/null || true
git clean -fd --exclude=.work-queue.json --exclude=.work-queue.lock

Step 5: Verify Cleanup

bash
# Should show empty (or only .work-queue.json/.work-queue.lock which are filtered out)
git -C "$MAIN_REPO" status --porcelain | grep -v '.work-queue.json' | grep -v '.work-queue.lock'

When the Orchestrator Asks About Contamination

If the orchestrator asks whether you accidentally made changes outside your worktree:

  1. Run the contamination check above
  2. If you find changes that are yours, move them to your worktree and confirm to the orchestrator that you've cleaned up
  3. If the changes are not yours, tell the orchestrator they are not from you
  4. The orchestrator will discard the changes after all workers confirm

Troubleshooting

Lock timeout

bash
rm .work-queue.lock

No available issues

bash
./scripts/show-queue.sh --blocked

Merge conflicts during rebase

bash
# Fix conflicts in the affected files, then:
git add .
git rebase --continue
git push --force-with-lease

Questions? Check AGENTS.md and DESIGN.md.