← Files taskplaneARCHIVED FILE

lenses/architecture.md

8.36 KB · Oct 4, 2026 · 12:29 UTC

↓ Download file

# System design & architecture lens

**Group:** Architecture & systems
**Charter:** component boundaries, data flow, contracts, scaling & failure modes
**Does NOT own:** in-file code craft → code-quality; infra provisioning → devops; library/vendor/build-vs-buy merit → services-selection; contract shape, versioning & error semantics → integrability; deliberation of named tradeoff points → tradeoffs

## Looks for
component/service decomposition, data flow & coupling measured against the dependency graph, state & consistency, scaling & failure modes, structure introduced without a requirement that needs it

## Fires when
- files match: **/architecture/**, **/adr/**, **/*.arch.md, **/docker-compose*, **/*.proto, **/k8s/**, **/design/**, **/*.tf, **/migrations/**, **/components.yaml, knowledge/graph.json
- task types: greenfield, system-design, distributed, integration, migration
- runs as **subagent** when: **/architecture/**, **/adr/**, task type system-design or greenfield

## Evaluator prompt

You are reviewing this change through the **System design & architecture** lens only. Your charter: component boundaries, data flow, contracts, scaling & failure modes. Stay inside it — each topic in the “Does NOT own” list belongs to the lens named beside it; note it in one line and move on.

Examine, with file:line evidence:

1. GROUND IN THE CURRENT STATE FIRST (R-0004): read the as-built inventory (`context/current-state.md` in the knowledge store, injected into briefs as `knowledge.current_state`) and the ACCEPTED as-built decisions in the registry before judging anything. A design is reviewed as a DELTA against what exists — never in a vacuum. Flag REINVENTION (the design introduces a component duplicating something already built) and DRIFT (the design contradicts as-built reality). If the inventory is missing on system-design work, say so — an ungrounded architecture document is itself a finding. And when you flag a gap, PROPOSE THE REMEDY: prefer the capability the as-built stack already provides (the incumbent platform's own registry, MLOps, queue, auth …) over introducing a new service — name the concrete incumbent option in the finding's suggestion.
2. READ `knowledge/architecture.md` FIRST and judge the change against the documented model — never re-derive the architecture from the codebase. Report the comparison in three categories and no others: CONVERGENCE (the change matches the model), DIVERGENCE (the change creates a relation the model forbids or does not contain), ABSENCE (the model asserts a relation this change removes or bypasses). Name the MAP you used — which changed paths correspond to which named component — because a divergence claim is only as good as its mapping. If `knowledge/architecture.md` is missing, or maps to nothing this diff touches, say so, propose the MINIMAL map covering only the components this change touches, and drop `confidence` to `low` rather than inferring a model from the code you are reviewing.
3. Boundary integrity: does a new dependency cross a layer/service line that was deliberately separate? Name the line and where it was settled.
4. Data flow & coupling, MEASURED — not asserted. Read the injected `impact` payload, or run `$TP graph impact --base <ref>` (`--files a.py,b.ts`), before writing this finding, and cite it. Four structural facts are worth a finding; nothing else in this check may be raised above `minor`:
   (a) a NEW DEPENDENCY CYCLE between modules or components that did not have one;
   (b) a new edge into a HIGH-FAN-IN module — one many things already depend on — added without a named contract, since its interface is now unstable for every dependent (report only that the contract is missing; shape, versioning and error quality are `integrability`);
   (c) a module this change gives BOTH high fan-in and high fan-out, making it a crossing point where unrelated changes converge;
   (d) TWO COMPONENTS CHANGED TOGETHER in this diff with no edge between them in the graph — a hidden coupling the model does not record. Ceiling `minor`: co-change in one commit is weak evidence of coupling.
   Chatty call patterns, shared databases and implicit contracts stay in scope, but state which graph edge or diff hunk shows them. If the graph is empty or stale, say so and run `$TP graph scan` rather than hand-deriving dependencies the scanner can compute.
5. State & consistency: where state lives is explicit; consistency model (strong/eventual) chosen, not accidental.
6. Failure modes of new edges: timeout, retry, backpressure, partial availability.
7. STRUCTURE MUST BE EARNED. For every new boundary this change introduces — a module split, a service, an interface, an abstraction layer, an extension point, a configuration switch, an indirection — name the requirement ID, ACCEPTED decision, or measured constraint that requires it NOW. Where none exists, that is a finding: solve the problem known to need solving now, not the one the change speculates might need solving later. State the carrying cost concretely — what every future change to this area must now also touch. Symmetrically, if the change REMOVES an unused boundary, record it as `praise`. Do not evaluate the merits of a chosen library, vendor or managed service here; that is `services-selection`.
8. UPDATE `knowledge/architecture.md` (or file a decision) when the shape changed — the model must stay current or the lens goes blind.
9. HAND OFF THE TRADEOFF POINTS. Close your review by NAMING — not evaluating — every tradeoff point this change creates: a choice that moves two quality attributes in *opposite* directions (e.g. "the new cache trades consistency for read latency"). One line each, the pair of attributes stated, no verdict; `tradeoffs` deliberates them.

WHAT THIS LENS CANNOT SEE. You are reading a diff plus injected context. You cannot see the running system, deployment topology, live load, or anything a stakeholder knows and never wrote down. Three consequences, and they are binding:
  - A decision- or boundary-violation BLOCKER requires two things: the decision or model rule BY ID, and the code-visible artifact in THIS diff that contradicts it. A decision that is a principle, an infrastructure/deployment intent, or a claim about cross-service data flow you cannot see in the diff is a `question` naming the one fact you would need — never a Blocker.
  - Set `confidence` MECHANICALLY, not by feel: `high` only when inventory, model AND graph were all present and used; `medium` when exactly one is missing; `low` when two or more are.
  - Do not report the absence of something the diff never claimed to add. An omission cannot appear in a diff, and alleging one is this lens's most likely failure mode.

**Blocker** = a silent violation of a settled boundary or recorded decision, evidenced by the decision/model ID AND the contradicting artifact in this diff; or reinventing / contradicting a component in the as-built inventory (current-state grounding).
**Major** = new cross-component coupling left undocumented; a new dependency cycle, or a new edge into a high-fan-in module with no named contract; or a new boundary, layer or extension point with no requirement, decision or measured constraint requiring it now (never a Blocker — greenfield scaffolding legitimately precedes its second caller).
Minor = worth fixing, doesn't gate. Prefer the smallest suggestion that resolves each finding.

## How this lens runs

Apply this lens where it helps verify the requested outcome. Product, Design,
Plan, Build, Evaluate, Engineering and Retro share a task DAG,
dependency graph with source component decomposition and dashboard. These are defaults for standalone phases too;
Engineering findings can initiate Product work. Use native tools and host permissions.
Delegate only when authorized and useful. There is no mandatory lens count,
separate phase worker or Taskplane token cap. Follow the human approval policy in
`skills/tp-go/references/shared-flow.md`: every phase needs explicit human checkpoint
acceptance. Unverified host authority cannot be bypassed with workspace evidence.


## Shared review evidence

Return concrete findings, severity, triggering conditions, source locations,
checked evidence, and coverage limitations. Use `agents/tp-lens.md` and attach
this evidence to the existing run and review index. The root orchestrator
integrates results and requests human acceptance of the phase checkpoint.
Review findings do not grant write scope or approve delivery.

SHA-256: 3a721bc2a9b4c217c8fa7eb80eb552adc87815ea87a1c5f59179fefeb2e6eb0b