Skip to content

Extend swarm lens set to 11 lenses in 4 clusters#35

Merged
gering merged 9 commits into
mainfrom
task/extend-swarm-lens-set
Jul 17, 2026
Merged

Extend swarm lens set to 11 lenses in 4 clusters#35
gering merged 9 commits into
mainfrom
task/extend-swarm-lens-set

Conversation

@gering

@gering gering commented Jul 15, 2026

Copy link
Copy Markdown
Owner

Summary

  • Grow /swarm:review's Claude lens set from 5 topical lenses to 11 by importing the two missing decomposition axes: methodological (removed-behavior, cross-file-trace) and design quality (reuse, simplification, efficiency, altitude) — all default-on, so every run reviews maintainability, not just defects.
  • Organize the 11 lenses into 4 clusters (LENS_CLUSTERS — single source of truth for the follow-up per-cluster externals task): breakage / threat / design / consistency. The Claude fan-out runs one finder per cluster by default (≤4 agents); --max splits to one finder per lens (≤11). The gate still prunes per-lens; an empty cluster spawns no agent.
  • Design findings carry a derived kind: "design" (no finding-schema change), pass the same 3-state verifier with a kind-aware applicability prompt (reuse target real? simpler form behavior-identical?), and render in their own Design report table so suggestions never dilute the defect ranking.

Changes

  • plugins/swarm/workflows/swarm-review.js — 6 new lens briefs; LENS_CLUSTERS + lensKind; per-cluster/per-lens fan-out ladder; gate prompt treats design lenses first-class; lens-prefix regex accepts hyphenated names ([\w-]); member-derived cluster kind (mixed ⇒ defect); kind-aware verify prompt; kind-first ranking; balance.design
  • plugins/swarm/skills/review/SKILL.md — external prompt names all 11 angles (one broad prompt per backend, as before); report renders a second same-format Design table with shared numbering; balance line gains · <design> Design; --pr post tags design rows with their lens; --max + Notes docs
  • Docs/knowledge sweep: plugin README (cluster table), pipeline-blueprint authority note, swarm-review-pipeline.md (lens table + verify-path decision), root README, CLAUDE.md, CHANGELOG
  • Version: swarm 0.4.2 → 0.5.0 (minor — new review surface)

Readiness

  • ✅ clean tree, rebased onto main
  • ✅ README (root + plugin) updated
  • ✅ version bumped + in sync (plugin.json / marketplace.json)
  • ✅ CHANGELOG entry (0.5.0)
  • ✅ knowledge entry + index updated
  • check-structure.py: 0 errors (3 pre-existing description-length warnings)
  • ➖ lint/build: N/A (declarative plugin repo)

Test plan

  • /swarm:review on a mixed diff: 4 cluster finders spawn (watch /workflows), findings keep per-lens [lens] prefixes
  • /swarm:review --max: one finder per gated lens (≤11), design lenses at xhigh
  • Report: defect table first, Design table after with shared numbering; balance shows · <n> Design
  • Doc-only diff: gate prunes efficiency-style lenses with a one-clause why
  • Design solo with a bogus reuse target gets REFUTED by the applicability verifier

🤖 Generated with Claude Code

https://claude.ai/code/session_0126cGxsBYxqgEFH4AcpriNk

@gering
gering force-pushed the task/extend-swarm-lens-set branch from f2db00e to 99633c9 Compare July 17, 2026 18:13
gering added a commit that referenced this pull request Jul 17, 2026
A full-ensemble --loop review of the rebased branch (composer swept, #37
merged) found real gaps, several in the prior harden rounds' own fixes:

- redactProposalPaths only caught whole-token paths (starts-with / ~ .. drive),
  missing embedded forms (`path=/…`, `file:///`, `$HOME/…`). Rewritten as
  redactOutOfRepoPaths: redact any token CONTAINING an absolute/home/traversal/
  drive/UNC/env/scheme:// indicator anywhere. 3-family consensus + CONFIRMED.
- Applied the redaction to EVERY attacker-controlled fence field (mechanism,
  summary, failure_scenario), not just the proposal (defense-in-depth parity).
- claudeCheckedLens grounded a methodological consensus on ANY Claude
  methodological tag; now requires a Claude member tagging the SAME lens that
  won plurality (c.lens), closing the distinct-methodological-lens hole.
- reclassifyToDefect + a REFUTED verdict silently dropped the promoted bug
  (schema permits the combo, kept-filter drops REFUTED); reclassify now forces
  PLAUSIBLE so the mis-filed defect survives (this also subsumes the
  mixed-cluster "dropped defect" finding).
- reclassify hardcoded lens='correctness', wiping the real defect class; now
  carries the non-design member's lens (or 'correctness' only as fallback).
- Stale comment claiming pr-post buckets by lens (it keys on kind alone now).
- CHANGELOG 0.5.0 dated 07-16 above 0.4.3 07-17 → 07-17; drop dead PR_POST
  binding in test_lens_sync.py.

Left: updatedFrom PR #35 (the correct provenance for this work; #37 is a
concurrent branch, not a regression).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0126cGxsBYxqgEFH4AcpriNk
gering added a commit that referenced this pull request Jul 17, 2026
Round-1 re-review escalated a round-0 dismissal to critical and caught two
bugs in round-0's own redaction fix:

- CRITICAL (consensus): a MIXED cluster (design member + real defect member)
  resolves to kind:defect but round-0 routed it onto the design applicability
  rubric via hasDesignMember — so a REFUTED "reuse target absent" dropped the
  whole cluster INCLUDING the defect, and a CONFIRMED shipped the defect
  unchecked. Route rubric selection on the RESOLVED kind (design = c.kind ===
  'design'); a mixed cluster now gets the adversarial defect rubric (still
  verified via needsVerify's hasDesignMember). reclassifyToDefect could not
  save these — the verifier judged applicability, not the bug.
- CRITICAL (security): redactOutOfRepoPaths under-redacted a path glued after
  ,;{}>| (delimiter class omitted them) AND over-redacted legit in-repo
  `...spread` / `main..HEAD` / `$IN_REPO_ROOT/...` (whole-token ..-/$VAR
  heuristic). Rewritten as substring matching: scheme://, drive/UNC, ../
  traversal match-anywhere; a ~/absolute path redacts only at a boundary
  (start or after any non-path char). Matrix-tested (evasions + false-positives).
- SKILL Notes "Only defect consensus is auto-accepted" corrected to match
  needsVerify (all-untagged + Claude-unchecked methodological still verify).

Left as residual: unprefixed-finder→design (PLAUSIBLE, reclassify exception
mitigates); prose lens-table drift not in test_lens_sync (runtime mirrors are
guarded); updatedFrom PR #35 (this branch's actual PR — a lower number than the
concurrently-merged #37 is not a regression).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0126cGxsBYxqgEFH4AcpriNk
gering and others added 9 commits July 18, 2026 00:08
- Add methodological lenses (removed-behavior, cross-file-trace) and
  design-quality lenses (reuse, simplification, efficiency, altitude),
  all default-on and gate-pruned per-lens like any lens
- Add LENS_CLUSTERS (breakage/threat/design/consistency) as single
  source of truth; Claude fan-out runs one finder per cluster by
  default (<=4 agents), one per lens under --max (<=11)
- Derive kind (defect|design) from the lens name — no finding-schema
  change; mixed merge clusters stay defects
- Verify design solos with a kind-aware applicability prompt through
  the same 3-state verifier (decision: verify, not bypass)
- Render design findings in their own report table with shared
  numbering; balance.design counts the subset
- Extend the external backend prompt with the six new angles so
  cross-family consensus can form on design findings too
- Fix the lens-prefix regex to accept hyphenated lens names
- Sweep docs/knowledge; bump swarm 0.4.2 -> 0.5.0

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0126cGxsBYxqgEFH4AcpriNk
First dogfooding run: /swarm:review --fix over its own diff (4 cluster
finders + codex + grok-4.5 + composer; 13 findings, 5 cross-family
consensus). Fixes the agreed findings:

- Keep validly tagged off-cluster lens prefixes: validate against the
  global lens set, not the finder's subset — coercion could flip kind
  and route a real defect through the applicability verifier (#1, consensus critical)
- Verify design clusters even with cross-family consensus: agreement
  attests agreement, not repo-grounded applicability (externals cannot
  open repo files); defect consensus stays auto-accepted (#2)
- Untagged external findings ('unspecified' lens) no longer vote in the
  cluster-kind derivation (#3)
- Derive CANDIDATE_LENSES from LENS_CLUSTERS — one list, no unchecked
  mirror; DRIFT WARNING on the SKILL.md external-prompt copy (#4, #9)
- Finder prompt: "issue (defect or substantive improvement)" + all lens
  prefixes; external prompt lead covers design improvements too (#5, #6)
- pr-post.py owns design-row ordering + [lens] prefixing via optional
  kind/lens row fields, unit-tested; SKILL.md step 5 passes rows through
  verbatim (#13)
- Doc sync: balance-spec finder count, README canonical cluster names +
  preset teaser wording, knowledge-index line trimmed (#8, #10, #11, #12)

Declined: #7 (per-cluster dilutes per-lens depth) — deliberate,
documented cost/coverage trade-off; --max is the depth profile.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0126cGxsBYxqgEFH4AcpriNk
Second dogfooding round at the deepest profile (/swarm:review --max --fix:
per-lens split live — gate pruned style, 10 xhigh finders + codex
gpt-5.6-sol@xhigh + grok-4.5 + composer; 24 findings, 10 consensus).
Fixes the agreed findings:

- Never auto-accept an all-untagged consensus cluster: no tagged lens
  backs it, so it is verified like a solo. Verify/auto-accept now derive
  from ONE needsVerify predicate (structural exactly-once partition);
  kind vote in clearer every-form (#1, consensus critical; #21, #22)
- Design verifier sees the finding's recommendation — the proposal the
  applicability rubric actually tests — and carries an escape hatch:
  a genuine defect mis-filed under a design lens is not refuted away
  (#12, #3); "solo" dropped from verifier prompts (#4)
- Untagged findings from multi-lens cluster finders fall back to
  'unspecified' (safe defect bucket), not lenses[0] (#7); merge-agent
  free-text lens validated, majority-member fallback (#9)
- Improvement invitation scoped to design finder units — defect-lens
  finders stay defect-only (#8); merge prompt clusters by issue, not
  only defect (#13); schema descriptions generalized for design
  findings (#14)
- LENS_BRIEF startup assertion (#6); gate prompt interpolates
  LENS_CLUSTERS.design (#19); new test_lens_sync.py guards all lens
  mirrors: SKILL HDR prompt, LENS_BRIEF, pr-post DESIGN_LENSES (#5)
- Workflow assigns stable finding num (defects first, shared sequence);
  presenter/pr-post render it verbatim (#20)
- pr-post.py: design lens is the backup kind signal when the handoff
  drops kind (explicit defect still wins); single-pass partition (#17, #24)
- Balance: REFUTED is its own segment (refuted ⊄ solo since design
  consensus can be refuted) (#2); LOCKED design-table column precedence
  in --loop rounds clarified (#11); "verifies solos" doc sweep across
  manifests/README/knowledge (#4); cluster failure-isolation trade-off
  documented (#10); knowledge index line trimmed (#15)

Declined: #16 (JS test harness for sandbox code; lens-sync test covers
the drift class), #18 (gate-fail under --max runs all lenses — the
documented never-silently-narrower degrade), #23 (micro-opt vs readability).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0126cGxsBYxqgEFH4AcpriNk
External-only --max dogfooding (codex + grok-4.5 + composer, no Claude
lenses) surfaced three real gaps, all hand-verified against the code:

- Merge-lens validation: accept the merge agent's cluster `lens` only when
  a member actually tagged it (was: any globally-valid lens), so a lens no
  member carried can't corrupt the [lens] prefix / survivingPerLens keys;
  `unspecified` no longer wins the majority fallback tally.
- Design escape-hatch: the mis-filed-bug exception now sets
  `reclassifyToDefect` so a genuine bug wearing a design lens is promoted to
  kind:"defect" and leaves the Design table (was: PLAUSIBLE but still design).
- Methodological consensus: a removed-behavior/cross-file-trace cross-family
  consensus with no repo-reading Claude voice is verified, not auto-accepted
  (diff-only externals can't confirm a repo fact — correlated hallucination).
- test_lens_sync.py pins METHODOLOGICAL_LENSES as a subset of LENS_CLUSTERS.

Two grok "critical" all-untagged-auto-accept findings were false alarms
(they describe the already-closed pre-fix hole); left untouched.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0126cGxsBYxqgEFH4AcpriNk
A full --max pass (with Claude lenses) re-reviewed the prior external-only
fixes; the adversarial verifier read the real repo and CONFIRMED two
regressions in commit 9e58661, plus real pre-existing gaps:

- Methodological-consensus guard checked family presence, not lens tag: a
  Claude [correctness] member on a cluster whose plurality lens resolved to
  cross-file-trace waved the (unchecked) repo claim through. Now checks the
  member (backend, lens) pair — a Claude voice must have tagged that lens.
- reclassifyToDefect left the design lens on the promoted bug; when the
  step-5 handoff drops the optional `kind`, pr-post re-bucketed it back into
  the Design section. Reclassify now strips the lens to a generic defect lens
  and drops the finding to solo (an applicability pass alone must not mint a
  consensus defect).
- needsVerify now fires on any design-tagged member, so a mixed design+defect
  cluster still applicability-checks its proposal; the design fence carries
  the proposal for all-untagged clusters too.
- README pipeline diagram + consensus blurb corrected to the 0.5.0 verify
  gate (the earlier doc sweep missed README:50 and :81).

The verifier also correctly REFUTED two false alarms (cross-round num
stability — presenter-owned; knowledge schema-mirror claim — correctly scoped).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0126cGxsBYxqgEFH4AcpriNk
A full --max pass REFUTED every re-flag of the prior round's fixes (they
hold), but caught fresh issues — two of them introduced by that round:

- pr-post bucketed rows by lens when the step-5 handoff dropped `kind`, so a
  reclassified/mixed-cluster defect carrying a design lens was re-promoted into
  the Design table (consensus claude+grok). Now bucket by `kind` ALONE — a
  dropped kind falls to defect (the safe bucket); the lens is no longer a
  design fallback. DESIGN_LENSES retired; tests inverted.
- The design applicability verifier is asked whether a reuse target exists, and
  the proposal is attacker-controllable; only c.file was repoSafePath-guarded.
  A hostile --pr proposal naming ~/.aws/... could lure the verifier into an
  out-of-repo read. Redact out-of-repo path tokens from the proposal before
  fencing (repo-relative targets preserved) + a repo-scope prompt reminder.
- Drop the dead `c.kind === 'design'` verify-rubric disjunct (subsumed by
  hasDesignMember).
- test_lens_sync upgraded from subset to completeness (METHODOLOGICAL_LENSES
  == breakage − topical); SKILL num-verbatim scoped to round 0 (cross-round #
  is presenter-owned); two stale doc comments corrected; CHANGELOG hardening
  bullets reordered ascending.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0126cGxsBYxqgEFH4AcpriNk
A full-ensemble --loop review of the rebased branch (composer swept, #37
merged) found real gaps, several in the prior harden rounds' own fixes:

- redactProposalPaths only caught whole-token paths (starts-with / ~ .. drive),
  missing embedded forms (`path=/…`, `file:///`, `$HOME/…`). Rewritten as
  redactOutOfRepoPaths: redact any token CONTAINING an absolute/home/traversal/
  drive/UNC/env/scheme:// indicator anywhere. 3-family consensus + CONFIRMED.
- Applied the redaction to EVERY attacker-controlled fence field (mechanism,
  summary, failure_scenario), not just the proposal (defense-in-depth parity).
- claudeCheckedLens grounded a methodological consensus on ANY Claude
  methodological tag; now requires a Claude member tagging the SAME lens that
  won plurality (c.lens), closing the distinct-methodological-lens hole.
- reclassifyToDefect + a REFUTED verdict silently dropped the promoted bug
  (schema permits the combo, kept-filter drops REFUTED); reclassify now forces
  PLAUSIBLE so the mis-filed defect survives (this also subsumes the
  mixed-cluster "dropped defect" finding).
- reclassify hardcoded lens='correctness', wiping the real defect class; now
  carries the non-design member's lens (or 'correctness' only as fallback).
- Stale comment claiming pr-post buckets by lens (it keys on kind alone now).
- CHANGELOG 0.5.0 dated 07-16 above 0.4.3 07-17 → 07-17; drop dead PR_POST
  binding in test_lens_sync.py.

Left: updatedFrom PR #35 (the correct provenance for this work; #37 is a
concurrent branch, not a regression).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0126cGxsBYxqgEFH4AcpriNk
Round-1 re-review escalated a round-0 dismissal to critical and caught two
bugs in round-0's own redaction fix:

- CRITICAL (consensus): a MIXED cluster (design member + real defect member)
  resolves to kind:defect but round-0 routed it onto the design applicability
  rubric via hasDesignMember — so a REFUTED "reuse target absent" dropped the
  whole cluster INCLUDING the defect, and a CONFIRMED shipped the defect
  unchecked. Route rubric selection on the RESOLVED kind (design = c.kind ===
  'design'); a mixed cluster now gets the adversarial defect rubric (still
  verified via needsVerify's hasDesignMember). reclassifyToDefect could not
  save these — the verifier judged applicability, not the bug.
- CRITICAL (security): redactOutOfRepoPaths under-redacted a path glued after
  ,;{}>| (delimiter class omitted them) AND over-redacted legit in-repo
  `...spread` / `main..HEAD` / `$IN_REPO_ROOT/...` (whole-token ..-/$VAR
  heuristic). Rewritten as substring matching: scheme://, drive/UNC, ../
  traversal match-anywhere; a ~/absolute path redacts only at a boundary
  (start or after any non-path char). Matrix-tested (evasions + false-positives).
- SKILL Notes "Only defect consensus is auto-accepted" corrected to match
  needsVerify (all-untagged + Claude-unchecked methodological still verify).

Left as residual: unprefixed-finder→design (PLAUSIBLE, reclassify exception
mitigates); prose lens-table drift not in test_lens_sync (runtime mirrors are
guarded); updatedFrom PR #35 (this branch's actual PR — a lower number than the
concurrently-merged #37 is not a regression).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0126cGxsBYxqgEFH4AcpriNk
Independent code review confirmed two regressions from the prior --loop fixes:

- redactOutOfRepoPaths corrupted legit finding text: it redacted regex literals
  (`/\s+/g`) and slash-prefixed tokens, so a design proposal became
  "[out-of-repo path redacted]" and the applicability verifier REFUTED it,
  dropping a valid suggestion; a defect's claim text was garbled. This was the
  4th distinct redaction defect across rounds — free-text can't reliably be
  scanned for out-of-repo paths (a `/etc/passwd` is indistinguishable from a
  regex literal or a repo path). Remove the redactor entirely and instead
  instruct the verifier to never open ANY path/URL named in the finding text —
  only c.file (repoSafePath-gated) is a real coordinate. Honest + non-corrupting,
  and in line with the plugin's minimal-security posture.
- needsVerify gated on hasDesignMember, so a cross-family DEFECT consensus that
  merged with a design suggestion was pushed through the single verifier where a
  false-REFUTE silently dropped a bug two families agreed on. Gate on the
  resolved kind (c.kind === 'design') instead: a mixed cluster is kind:defect and
  a cross-family one auto-accepts (the defect is the finding; the suggestion rides
  along). hasDesignMember is now unused — removed.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0126cGxsBYxqgEFH4AcpriNk
@gering
gering force-pushed the task/extend-swarm-lens-set branch from 9fbd7f6 to 38722f2 Compare July 17, 2026 22:08
@gering
gering merged commit 9eabb76 into main Jul 17, 2026
1 check passed
@gering
gering deleted the task/extend-swarm-lens-set branch July 17, 2026 22:10
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant