Files
Cita 8ebfc39745 [codex] add harness engineering guardrails (#284)
* refactor: add harness engineering guardrails

* fix: address harness review feedback

---------

Co-authored-by: apple <apple@appledeMacBook-Pro.local>
2026-03-26 21:22:36 +08:00

3.5 KiB

Metapi Engineering Rules

These rules apply to the whole repository unless a deeper AGENTS.md overrides them. They are intentionally opinionated and mechanical so humans and agents can make small, consistent changes without re-learning the codebase each time.

Golden Principles

  • Prefer one source of truth. If a helper, contract, or workflow already owns an invariant, extend it instead of creating a parallel implementation.
  • Fix the family, not just the symptom. When a bug comes from a repeated pattern, sweep adjacent paths in the same subsystem before calling the work done.
  • Keep changes narrow and reviewable. Land one coherent slice at a time and avoid bundling unrelated cleanup into the same patch.

Server Layers

  • src/server/routes/** are adapters, not owners. Route files may register Fastify endpoints, parse request context, and delegate. They must not own protocol conversion, retry policy, stream lifecycle, billing, or persistence.
  • If a helper is imported by anything outside one route file, it does not belong under src/server/routes/proxy/.
  • src/server/proxy-core/** owns proxy orchestration. Endpoint fallback should flow through executeEndpointFlow(). Channel/session bookkeeping should flow through sharedSurface.ts.
  • src/server/transformers/** are protocol-pure. Do not import from src/server/routes/**, Fastify, OAuth services, token router, or runtime dispatch modules. If a transformer needs a shared contract, move it to a neutral module first.
  • Whole-body upstream reads in proxy orchestration should use readRuntimeResponseText() instead of direct .text() reads.

Platform And Routing Rules

  • Platform behavior must be explicit. Detection, endpoint preference, discovery transport, and management capability should come from one declared capability story, not scattered if platform === ... branches.
  • Thin adapters must stay honest. Do not let a platform look feature-complete through inherited defaults if the underlying upstream does not support the feature.
  • Retry classification and routing health classification should share the same failure vocabulary whenever possible.

Database Rules

  • One schema change requires three synchronized outputs: update the Drizzle schema, update SQLite migration history, and regenerate checked-in schema artifacts together.
  • Cross-dialect bootstrap and upgrade SQL must be generated from the schema contract. Do not hand-write new MySQL/Postgres schema patches in feature code.
  • Legacy schema compatibility is temporary and spec-owned. Additive startup shims should stay narrow and trace back to a feature compatibility spec.

Web Rules

  • Pages are orchestration surfaces, not shared utility libraries. Do not import one top-level page from another top-level page.
  • Mobile behavior should reuse existing shared primitives first: ResponsiveFilterPanel, ResponsiveBatchActionBar, MobileCard, useIsMobile, and mobileLayout.ts.
  • When a page grows a second complex modal, drawer, or panel family, extract it into a domain subfolder before adding more inline state and rendering logic.

Guardrails

  • Run npm run repo:drift-check before finishing changes that touch shared architecture boundaries.
  • If you add a new boundary-heavy module, add or extend an architecture test in the same area so the rule becomes executable.
  • Keep local planning files under docs/plans/. They are intentionally ignored by git and should not be treated as published documentation.