From 13b304991394aeec07de71c61cdc634badf3fde8 Mon Sep 17 00:00:00 2001 From: fullsend-code Date: Thu, 21 May 2026 14:53:09 +0000 Subject: [PATCH] docs(#1299): document forge.Client abstraction convention Add a "Forge abstraction" section to AGENTS.md documenting that all git forge operations must go through the forge.Client interface in internal/forge/forge.go. This gives both the code agent (to write correct code) and the review agent (to catch violations) the architectural context they were missing. The new section covers: - The rule: all forge ops use forge.Client - What is prohibited outside internal/forge/github/ - Where forge-specific code belongs - Guidance for extending the interface - Review severity for violations (medium or higher) Also adds a brief mention in CLAUDE.md's Go code section for broader visibility, cross-linking to the full AGENTS.md section. Note: make lint could not run due to a sandbox infrastructure issue (Go toolchain download permission denied). The changes are documentation-only (Markdown files) so no Go tests apply. Closes #1299 Signed-off-by: fullsend-code --- AGENTS.md | 16 ++++++++++++++++ CLAUDE.md | 2 ++ 2 files changed, 18 insertions(+) diff --git a/AGENTS.md b/AGENTS.md index 8f1650503..2dd14dd15 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -9,3 +9,19 @@ Use [Conventional Commits](https://www.conventionalcommits.org/) format for ever This is not optional — GoReleaser parses commit prefixes to build release notes. A missing or wrong prefix produces incorrect changelogs. When reviewing PRs, check that commit messages and PR titles follow this format. Flag violations as a required change — they are not cosmetic. + +## Forge abstraction + +All git forge operations (GitHub API calls, PR comments, issue creation, workflow dispatch, etc.) **must** go through the `forge.Client` interface defined in `internal/forge/forge.go`. This is a fundamental architectural rule — the codebase supports multiple forges (GitHub, GitLab, Forgejo) and direct coupling to any single forge breaks the abstraction. + +**Prohibited outside `internal/forge/github/`:** + +- `exec.Command("gh", ...)` — shelling out to the GitHub CLI +- Direct GitHub REST or GraphQL API calls (e.g., raw `net/http` to `api.github.com`) +- Any other forge-specific operation that bypasses `forge.Client` + +**Where forge-specific code belongs:** Only the `internal/forge/github/` package (the GitHub implementation of `forge.Client`) should contain GitHub-specific logic. All other packages must use the `forge.Client` interface, which is injected as a dependency. + +**When writing code:** If you need a forge operation that `forge.Client` does not yet support, add a new method to the interface and implement it in the GitHub client — do not work around the interface. + +**When reviewing PRs:** Flag any direct `exec.Command("gh", ...)`, raw GitHub API calls, or other forge-specific operations outside `internal/forge/github/` as a medium-severity or higher finding. This is an architectural violation, not a style preference. diff --git a/CLAUDE.md b/CLAUDE.md index 9ba8f10be..3e091851c 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -22,6 +22,8 @@ Fullsend is a platform for fully autonomous agentic development for GitHub-hoste When changing `internal/mint/main.go`, always copy it to `internal/dispatch/gcf/mintsrc/main.go.embed`. If `go.mod` or `go.sum` changed, sync those to `go.mod.embed` and `go.sum.embed` too. +**Forge abstraction:** All git forge operations must go through the `forge.Client` interface in `internal/forge/forge.go`. Do not use `exec.Command("gh", ...)` or direct GitHub API calls outside `internal/forge/github/`. See [AGENTS.md](AGENTS.md#forge-abstraction) for details. + When making changes to Go code under `cmd/` or `internal/`: 1. **Unit tests:** Run `make go-test` (or `go test ./...`) and fix any failures before committing.