Commit Graph
2 Commits
Author SHA1 Message Date
Renn F 5bea82dbbc fix(gateway): resolve adversarial-review findings on the pr_reviewer flow
An adversarial review of the feature found two blocking defects (both would
surface the moment external_pr_enabled is turned on) plus hardening gaps:

- HIGH: the enforcement legacy role-gate overlay OVERWROTE spec-derived roles,
  so pr_reviewer was erased from the (in_progress->completed) edge it shares
  with the PM self-complete gate — the review task could never complete. Fix:
  UNION legacy + spec roles instead of overwriting (also preserves the legacy
  'add roles' intent on every shared edge).
- HIGH: claim_pr_review routed claim+start through the verb runner, which hit
  start()'s plan gate (planless review task -> None -> crash/respawn loop) and
  auto-created+pushed a stray branch (violating the read-only/branchless
  invariant). Fix: mirror QA's claim_review — a verb-body TaskService.pr_review_claim
  does pending->in_progress with no plan and no branch.
- MED: add the pr_reviewer Write(*)/Edit(*) deny at the permission layer (it
  ingests untrusted PR diffs — make read-only explicit, not implicit).
- MED: regenerate the verb-table artifacts (the schemas existed but the
  generator had not been re-run; the agent prompt showed 'unknown' signatures).

ruff + mypy clean (279 files); foundation + gateway suites green (5205 passed).
2026-06-16 11:48:24 +02:00
Renn F 5902c0fe38 feat(roles): add the read-only pr_reviewer role end-to-end
A global, read-only PR reviewer agent (pr-reviewer-1) that reviews inbound
external/fork PRs and posts one change-request. Wired end-to-end:

- identity: Role.PR_REVIEWER + agent + ROLE_LEVEL (QA-peer) + REVIEWER_ROLES
- lifecycle: CLAIM_RULES + ROLE_TEAM_RULES + a dedicated claim_pr_review /
  post_pr_review verb pair (distinct from QA's) + the pr_review_done action and
  its in_progress->completed transition; give_me_work / i_am_idle gain the role
- role_config: a read-only RoleConfig (allows_write=False)
- journaling: ALL_CELLS read tier so it can read internal intent like QA
- tracing: post_pr_review requires a learning entry; claim_pr_review is waived
- seeds presentation + factory prompt layer + builtin tools + the agentrole
  enum migration (037) + regenerated verb/lifecycle artifacts

Read-only at /app like QA/auditor; default-off — nothing dispatches review work
until external_pr_enabled. Foundation + role-config + enum suites green; ruff +
mypy clean; orchestrator boots.
2026-06-16 10:37:06 +02:00