You are working in harness-python-react, a template repo whose harness IS the product. Code quality here is enforced mechanically — every gate fails CI, not just tests. Keep that bar as you work.
A production-quality LLM-driven coding harness over a minimal FastAPI + React scaffold. The point isn't the features (one /health, one /echo, one hello page); the point is that every layer of the pipeline — lint, types, architecture, security, eval, agent hooks — catches a different failure class without anyone remembering to run it.
docs/HARNESS.md— umbrella; the controls and where they live.docs/INVARIANTS.md— the load-bearing rules. Every PR is checked against them.docs/BOUNDARIES.md— layered import-linter contract; reverse imports fail CI.docs/DEVELOPMENT.md— branching, commit format, justfile, CI overview.
- One issue per change. Branch name:
feat|fix|chore|docs|test|refactor/<issue-number>-<kebab-title>. - One PR per branch, base
develop. PR title = the conventional-commit subject. develop → mainhappens via arelease:PR.- The pre-push gate is
just check(lint + typecheck + architecture + tests). Run it before pushing. - For frontend changes, also run
just frontend-check.
- Python: 3.14,
uv run --frozeneverywhere, mypy--strict, ruff with the wide select set (E W F I N UP B SIM TCH S RUF). - Type hints: every public function.
from __future__ import annotationsat module top. - Models: anything crossing a module / process seam inherits from
StrictModel(src/models/_base.py).extra="forbid". Addstrict=Trueto the class when you want strict type coercion (rejecting"3.14"→ float). - API: every route under
/api/v1/. Typed Pydantic responses, not raw dicts. - Layer flow: one-way. Reverse imports are a CI failure. See
docs/BOUNDARIES.md. - Observability: OTel
agent_span(...)for any operation in the request path; semconv-defined attribute keys only (constants at the top ofsrc/observability/spans.py). - Frontend: React 19 + TS strict; functional components + hooks; never
dangerouslySetInnerHTMLon backend output; SSE consumers use the typed primitive atfrontend/src/lib/api/client.ts.
- Don't bypass gates.
--no-verify/--no-hooks/--no-gpg-signare blocked bypretooluse_bash.pyfor a reason. If a hook is wrong, fix the hook. - Don't introduce a new commit-type prefix without updating both
pyproject.toml's commitizen schema ANDpr-title.yml(theCommit-type syncmeta-gate will fail otherwise). - Don't add a CI job without listing it in
.github/branch-protection/{develop,main}.json(theBranch-protection contexts syncmeta-gate will fail). - Don't skip the architecture contract by accident —
lint-importsruns in CI and locally viajust architecture. - Don't write code without tests. Coverage gate is 75% on
src/. - Don't hand-roll secrets into config. Use env /
.env(gitignored) →Settingsfromsrc/models/config.py. - Don't create files unless they're necessary. The scaffold has no dead modules.
The agent-side skills in .claude/skills/ auto-activate based on context:
architect— when designing module boundaries, API contracts, layer-flow decisions.code-reviewer— after writing/editing code; runs the 10-point review checklist.devops— when touching Docker, CI, pyproject.toml, observability config.frontend— when working infrontend/(React 19 + TS + Vite).qa-engineer— when writing tests or extending the eval harness.technical-writer— when updating docs / READMEs.
Trust their guidance — they encode this project's conventions.
- If the change touches a gate, update the meta-gate inputs (
branch-protection/*.json,pr-title.yml,check_required_contexts.py's exemption list). - If the change touches an invariant, decide whether the invariant is wrong (update
docs/INVARIANTS.mdin the same PR) or the change is wrong (rework). - If a CI job is failing for a reason that doesn't match the change, dig — don't reroll. Recent fix patterns: tag-vs-commit SHA in pinned action references,
if: hashFiles(...)startup failures (see project-memory), pytest exit-5 on empty test suites.
The harness exists to make sloppy work hard. Lean into it — when a gate trips, it's protecting the next person reading this codebase.