Commit Graph

2 Commits

Author SHA1 Message Date
CIAgent 9ff86f9cd0 verify(P04): gaps_found — P0 docstring fixes; anchor->grader shipment is a P1 gap
Trivial P0 fixes (this commit): two docstrings claimed things the wiring
does not do. variants/__init__.py said the package 'never imports agents/'
— false since Wave 2: generator.py holds the module-direct
agents.structured import (the sanctioned D-020 shared defense, same
exception as grading/engine.py); docstring now states the real boundary.
templates.py (header + RubricAnchors) claimed rubric anchors are 'used by
grading context' / 'shipped to the grader' — false in the current wiring:
GradingEngine is variant-blind (variant_seed=None; no variant lookup; no
anchor consumption; render_trace_digest takes only the digest). Docstrings
now tell the truth and name the follow-up.

Verification (four layers, evidence in the phase report):
- Structural: AST boundary audit clean — variants/ has zero api/fastapi
  imports; only sanctioned agents.structured + llm/prompts/config/store.
- Behavioral: variants slice 41/41 green; full suite 324/324 green;
  pnpm typecheck 7/7 green (forced, no cache). Live app probes confirmed
  distinct learners -> distinct statements/seeds/task_ids at the API
  level, cache hit = zero LLM calls, deterministic fallback (calls==2),
  a-5 fairness envelope test green, sha256(template|learner|milestone)
  seed derivation verified byte-exact against the spec formula.
- Security: secrets scan over the P04 diff (b52bef9..4acffac, 17 files
  +2100/-1) clean — no key/token/password assignments, no URLs, no key
  shapes. Prompt-injection surface bounded: the variant prompt carries
  only template skeleton/title/id + seeded slot values — no learner id
  or user-controlled content reaches the LLM. Empty learner_id -> 422.
- Quality: ruff clean; AI_MODEL env override verified live; tests are
  mock-only (MockProvider family, zero network imports).

Must-Haves: 5 of 6 SATISFIED. NOT satisfied: MH#4 half — anchors are
present per template and a-5-testable, but NOT shipped to the grader
prompt context (non-trivial cross-module wiring: engine + prompt
signature + lifespan ordering — grading engine is built before the
variant store exists; reported as P1, not fixed here).

---ci---
phase: 4
milestone: v0.3
status: verify
requirements:
  covered: [REQ-3-005]
  partial: [REQ-3-005]
lessons:
  - Docstrings that describe a must-have's target state ('shipped to the
    grader prompt') read as done in review — verify wiring, not words:
    grep the consumer side (grading/) before believing the producer side.
  - main.py builds GradingEngine before variant_store exists; any P4/P6
    anchor-shipment fix must reorder lifespan construction or inject the
    variant store into the engine after the fact.
  - Params distinctness is parametric (280-64908 combos per template) —
    two learners CAN draw identical params (~15% at 10 learners on the
    tightest template); distinctness is proven via seeds/task_ids/statement
    embeddings, which is what the must-have actually requires.
---/ci---
2026-09-12 03:46:30 +00:00
CIAgent 430b4a727d feat(P04): task template library + VariantStore (Wave 1)
Task 4-1-01: variants/templates.py — 3 task templates (llm-judge, guardrail-schema,
rag-chunker) bound to D-021 corpus competency IDs; typed ParameterSlots
(enum/int_range/string-set) with seeded pure-code sampler (random.Random(seed));
RubricAnchors difficulty-normalization envelope; starter-file scaffolds + test command.
Task 4-1-02: VariantStore protocol + SQLiteVariantStore (insert-only first-wins;
unique (learner,template) + unique task_id; WAL; tz-normalized) — the audit trail
for proctoring cross-checks.

22 variant tests green; ruff clean.

---ci---
phase: 4
milestone: v0.3
status: execute
requirements: {covered: [REQ-3-005], partial: []}
---/ci---
2026-09-12 02:57:09 +00:00