Files
waggle-os/docs/ux-refactor/p5-skill-governance-plan.md
Oleg Maslov 0c3e2ead3b
Some checks failed
Installer Smoke / installer-smoke (push) Has been cancelled
moving
2026-09-02 10:10:29 +02:00

6.5 KiB
Raw Permalink Blame History

P5 — D4 Skill-Write Governance · Build Plan

Phase sequence (open-questions.md:574): P1=D3 · P2=verify+J08 · P3=D2 · P4=D11/D12 · P5=D4 ← here · P7=D15 (card risk-taxonomy alignment, deferred). Decision text: docs/ux-refactor/deltas/open-questions.md §D4 (lines 537543).

What D4 ratified (four bindings)

  • (i) Policy. create_skill — normal = ask (in-chat approval card), trusted/yolo = auto-execute. delete_skill — always ask, every autonomy level. read_skill ungated. Always-audit all three with initiator:'agent'.
  • (ii) Surface. In-chat SSE approval card is canonical. Card↔ui/approval-modal.tsx risk-taxonomy alignment is D15/P7 — explicitly deferred, NOT P5.
  • (iii) One write path. Do NOT route the agent tool through HTTP. Extract a shared skill-write service module (create/update/delete + redaction + audit inside the service), consumed by both routes/skills.ts and skill-tools.ts. One module, one audit trail, two callers.
  • (iv) Endpoint consolidation (absorbs D14). POST /api/skills delegates to the audited service. PUT/DELETE /api/skills/:name enter the audit trail. Provenance: frontmatter initiator/source + GET /api/skills returns it + Skills Hub badge ("created by agent — review"), replacing the name-heuristic "Custom" classification.
  • Persona exception (already shipped): read-only personas keep losing create_skill/delete_skill, retain read_skill.
  • PM residual (no code): skill creation stays FREE at launch — tier gate unchanged.

Recon — current seams (verified 2026-06-12)

Seam File State
Agent tool packages/agent/src/skill-tools.ts create/delete write to disk + redact; no audit, no provenance, no gate
HTTP routes packages/server/src/local/routes/skills.ts POST /api/skills, PUT/DELETE /:name redact but don't audit; POST /api/skills/create (structured) DOES audit action:'installed'
Autonomy gate packages/agent/src/confirmation.ts declarative sets; chat.ts:900 calls needsConfirmationWithAutonomy
Frontmatter packages/agent/src/skill-frontmatter.ts parser+serializer; has name/description/scope/promoted_from/permissions — no initiator/source
Audit store packages/core/src/install-audit.ts record(); action enum lacks a delete value
Skills Hub UI apps/web/src/components/os/apps/skills/SkillRow.tsx, routes/SkillsRoute.tsx custom badge driven by name-heuristic

Decisions

DEC-1 — Audit action for delete (the one real fork)

AuditAction = 'proposed'|'approved'|'installed'|'rejected'|'failed'|'blocked' — no delete/uninstall value. The CHECK is duplicated in packages/core/src/install-audit.ts and packages/hive-mind-core/src/mind/schema.ts (OSS-synced, §7.5). SQLite CHECK can't be ALTERed → widening needs a table-rebuild migration on existing installs.

  • create / update → action:'installed' (established convention — routes/skills.ts structured-create already does this; a skill on disk = installed).
  • delete → needs a decision (see status note). Options:
    • A (recommended): add 'uninstalled' to AuditAction + both schema CHECKs + a rebuild migration. Fills a genuine pre-existing gap (no uninstall of ANY capability is auditable today); additive/backward-compatible; honest trail. Cost: migration in 2 files + OSS drift check.
    • B: reuse 'rejected' with detail:'deleted by agent'. Zero migration, but semantically muddy and pollutes rejection queries.

DEC-2 — Shared service location

packages/agent/src/skill-write-service.ts. The agent package is already a server dependency (@waggle/agent imported by routes/skills.ts), so one module serves both callers. Signature (pure, deps injected — no hidden globals):

createSkillWrite({ skillsDir, name, content, initiator, source, auditStore?,
                   skillHashStore?, onChange? }) → { path, redactions, action }
updateSkillWrite({ … }) ; deleteSkillWrite({ skillsDir, name, initiator, auditStore?, … })

Redaction (redactSkillContent) + provenance frontmatter stamp + audit record() all live inside the service. Callers stop doing these by hand.

DEC-3 — Provenance frontmatter

Add initiator?: 'agent'|'user' and source?: string to SkillFrontmatter + parser + serializeFrontmatter. The service stamps them on create (preserves on update). Legacy skills with no frontmatter → treated as initiator:'user' (no badge). Name-heuristic "Custom" classification retired in favor of initiator==='agent'.

Build order (TDD, commit per step)

  1. D4(i) gatingconfirmation.ts sets + tests. (73f2ed5)
  2. DEC-1 audit enum — founder picked Option A: 'uninstalled' + widen-CHECK migration in core install-audit.ts (belt-and-suspenders rebuild) AND hive-mind-core db.ts runMigrations sentinel + schema.ts DDL. (658884f)
  3. DEC-3 frontmatterinitiator/source in parser/serializer. (f3bda5b)
  4. DEC-2 serviceskill-write-service.ts (lossless provenance stamp). (2b56b78)
  5. Rewire agentskill-tools.ts create/delete via service. (2b56b78)
  6. Rewire HTTProutes/skills.ts POST/create/PUT/DELETE via service; GET /api/skills returns provenance. (29313a9)
  7. UI badgeSkillRow.tsx "agent · review" off provenance. (48292ef)
  8. Adversarial review workflow → record → final gates. (pending — needs opt-in)

Status — implementation COMPLETE (2026-06-12)

All four D4 bindings shipped in 7 commits (73f2ed548292ef), NOT pushed. Gates: tsc 0 across shared/hive-mind-core/core/agent/server/apps-web · 147 P5 tests green (agent 96, core 22, server 20, FE 9) · lint 0.

Remaining for P5 closeout:

  • OSS re-split (§7.5): hive-mind-core/src/mind/{schema.ts,db.ts} changed here first (the 'uninstalled' CHECK + migration sentinel). The marolinik/hive-mind mirror must be regenerated via subtree-split before the next OSS release.
  • Adversarial review (step 8) — every prior P-phase ran a multi-agent review workflow; deferred pending explicit opt-in.
  • Decision-log + open-questions phase-line update marking P5 done.
  • D4(ii) card↔modal risk-taxonomy alignment stays P7/D15 (out of P5 scope).

Out of scope (ledgered)

  • D4(ii) card↔modal risk-taxonomy alignment → P7/D15.
  • Marketplace install PRO-gate (unchanged).
  • promote_skill/auto_extract_skills/retire_skills audit (not named by D4; leave).