adept code style
Conventions for Go in github.com/itaywol/adeptability. CI enforces formatting and lint;
the rest is reviewed.
Formatting & lint (enforced)
gofmt+goimports— tabs for indentation, grouped imports (stdlib / third-party / local). CI fails on any unformatted file.golangci-lint run(.golangci.yml):errcheck(incl. type assertions),staticcheck,govet,gocritic,revive(every exported symbol needs a doc comment),errorlint,nilerr,bodyclose,prealloc,unconvert,misspell,unused,ineffassign.
Errors
- Always wrap with context and
%w:fmt.Errorf("clone %s: %w", url, err). - Compare with
errors.Isagainst the sentinels inpkg/adept/errors.go(ErrSkillNotFound,ErrMergeConflict,ErrBudgetOverflow, …). Never match on error strings. Need a new category? Add a sentinel there. errcheckis strict — handle or explicitly_ =an ignored error, and say why if it isn't obvious. Don't drop an error that loses data.
Structure
- Composition root, no globals. Concrete implementations are wired behind interfaces into
*Depsininternal/cli/deps.go. No package-level mutable state, noinit()side effects. Take dependencies as parameters so code is testable with fakes/mocks. pkg/adeptis types-only. Keep it dependency-light and stable; behavior lives ininternal/. (Example:SkillIDPatternis a string inpkg/adept, compiled ininternal/canonical— don't add aregexpimport topkg/adept.)- Doc comments are full sentences starting with the symbol name (
// NewRoot builds …).
Readability
- Small, single-purpose functions; prefer early returns over deep nesting.
- Name things for what they are; avoid one-letter names outside tight loops/receivers.
- No magic numbers/strings — name on-disk paths and limits as constants (see
pkg/adept/constants.go). - Comments explain why, not what. Keep them in sync with the code — a stale comment is a bug.
Invariants you must not break
- Identity is
(id, content-hash)— no version numbers as a sync signal. - Secrets never written to disk — API keys come from the environment at call time.
- Harness models differ (per-skill / single-file / aggregator) — renderers and importers must respect each; aggregators parse their own section markers and honor byte budgets.
- Canonical layout
<root>/skills/<id>/SKILL.md; the directory name is the authoritative id.