feat(core): generate brains-write capability artifact [BRNS-CORE-008] - #17
Conversation
RaekwonIII
left a comment
There was a problem hiding this comment.
Reviewed with the companion hub PR ssvlabs/brains#1069 — the full technical review and my answers to the three product questions live there. Comment, not approval.
This side checks out:
- The committed
capability-catalog.jsonis byte-identical to the brains-sidemanifest.json, and the contract test now recomputessha256(skills/brains-write/SKILL.md)and asserts it equalsb040…— so the artifact is bound to its source by content, and installation stays fully local (no runtime/install-time fetch). Good. - The internal-capability leak guard (
!/automation_secret|adminPool|handler_source|telegram_push|grant_token/) plus keeping the independent semantic assertions (digest proves provenance, not that the canonical source kept its load-bearing safety rules) is the right belt-and-braces. - The two new result kinds (
clarification,noop) are added consistently with the other faces.
One cosmetic note on provenance: #1069 merges by squash into stage, so the source commit b039b7d… cited in this PR's "Provenance and ordering" section won't exist on stage afterward (squash mints a new commit; the PR branch is deleted). That's harmless — the manifest binds by catalog_sha256 / artifact_sha256, i.e. content, not commit sha, and there's no source_commit field in the committed manifest. Just don't rely on that commit reference resolving after the squash; the digests are the real binding.
Ordering otherwise as you documented: land after (or immediately before) #1069 as the compatible public face.
stefan-ssv-labs
left a comment
There was a problem hiding this comment.
✅ review-pr (self-review, cannot approve own PR): no blockers on this side. One cross-repo note.
Reviewed against BRNS-CORE-008 at head b54a31b, alongside the hub PR ssvlabs/brains#1069. This side is clean and the provenance design is right.
Verified ✅
- The digest binding is enforced, not declared.
tests/plugin-contract/run.tsrecomputescreateHash("sha256").update(writeSkill)and asserts it equals the committedartifact_sha256. I confirmed independently:shasum -a 256 plugins/brains/skills/brains-write/SKILL.md=b0401fca…, matching both this repo'scapability-catalog.jsonand the brains-sidemanifest.json— which are byte-identical to each other. Running the hub generator with--check --plugin-root <this checkout>reports7 generated outputs are fresh, so the two repos agree at these exact heads. - Semantic assertions were kept alongside the digest. The comment gets the reasoning exactly right — "digest equality proves provenance, not that the canonical source itself kept the load-bearing safety rules." A hash check alone would have happily ratified a regenerated artifact that dropped the no-blind-retry rule. Keeping both is the correct belt-and-braces, and adding the
clarificationandnoopkind assertions closes the gap where only some kinds were covered. - Version pinning is complete.
schema_version,catalog_schema_version, andrenderer_versionare all asserted, so a future incompatible catalog or renderer revision fails loudly here rather than silently shipping a mismatched public face. - The leak guard is real.
!/automation_secret|adminPool|handler_source|telegram_push|grant_token/mirrors the monorepo-side check. I also readSKILL.mdin full: no internal or admin tools, no credentials or env values, no handler source, no user data. It reads as a genuine public face. - Installation stays local. No runtime or install-time fetch of a mutable artifact; the manifest travels with the skill.
Note — provenance binds by content, and the manifest is correctly commit-free
Worth recording since the PR body's "Provenance and ordering" section cites source commit b039b7d: that reference will not resolve on stage after #1069 squash-merges, and #1069's own head is now 33ff83b regardless. This is harmless, and I want to be clear it is not a finding — the committed manifest has no source_commit field at all, binding only by catalog_sha256 / artifact_sha256. I verified the digests are unaffected: git diff b039b7d1 33ff83bf -- packages/capability-catalog gbrain/src/core/generated docs/mcp-tool-reference.md is empty.
That is the better design, and it is why the stale pointer costs nothing. The only thing to avoid is treating that commit sha as a resolvable reference in future prose; the digests are the binding.
Merge ordering
Nothing in this PR depends on #1069 landing first — the artifact and its manifest are self-contained here, and the contract test verifies them without reaching into the other repo. So this can land in either order.
One caveat on sequencing: #1069 currently has a blocker (a bare @brains/capability-catalog import in the Deno automation sandbox that fails module resolution at runtime — details on that PR). Fixing it does not touch the catalog, the renderers, or any generated artifact, so it should not change artifact_sha256 and this PR should stay aligned. Worth re-running --check --plugin-root after that fix to confirm the digests still match before merging the pair.
|
Review follow-up: the PR body no longer treats the pre-squash source commit as durable provenance. It now names the content digests as the binding authority (matching the intentionally commit-free manifest), records @RaekwonIII’s resolved product decisions, and retains the explicit #1066 → production → #16 plus final #1069 → regenerate/rebase gates. No generated plugin bytes changed in this follow-up. |
stefan-ssv-labs
left a comment
There was a problem hiding this comment.
✅ review-pr (self-review, cannot approve own PR): re-review at f28d324f. No blockers, no critical issues.
Re-review at the new head. The only change since the previous pass is fix(core): regenerate action safety contract [BRNS-CORE-008], which regenerates the two committed artifacts to carry the upstream catalog fix from ssvlabs/brains#1069.
What I verified
This PR's contract is that its content is generated, never hand-edited, and provably tied to the upstream catalog. Both halves hold at this head:
plugins/brains/skills/brains-write/SKILL.mdis byte-identical to the artifact generated from ssvlabs/brains#1069 at014309fb.- Its actual SHA-256 (
52f9f4f6…) equals theartifact_sha256recorded inplugins/brains/generated/capability-catalog.json, and that manifest is identical to the brains-side manifest — samecatalog_sha256(3dbd82bd…), samerenderer_version: 2. - Running the upstream generator with this checkout passed as
--plugin-rootreports all 7 outputs fresh, so neither repository has drifted from the other.
The upstream change this regeneration carries — the restored auto_failed retry precondition and the verify-mode noop semantics — is reviewed on ssvlabs/brains#1069, where the catalog source lives. Reviewing that prose here would be reviewing a build output.
Validation
CI at f28d324f is 3/3 green (cross-client plugin contract, inbox-v2 contract, tool-error contract) and I reused it per the CI-first rule. Local checks added the byte-identity, digest, and cross-repo freshness proofs above, which CI cannot provide on its own because they span two repositories. No stage or production data was read or mutated.
No findings of this PR's own: its correctness is entirely a function of the upstream catalog, and the provenance binding that makes that checkable is intact.
QA review — artifact verified; hold for the release orderVerified at head
I also verified all four declared gates independently, and the description's self-assessment is accurate on every one:
So the hold is right, and it's the reason not to merge — not a defect in this diff. 🟠 MEDIUM —
|
|
Review follow-up at
The two Medium architecture items remain the documented release/deploy follow-up: a dedicated GitHub App should open reviewed cross-repo sync PRs, and the machine-readable catalog stays committed in brains until that workflow exists. They do not weaken the current content-digest or local semantic gates. Mandatory order is unchanged and explicit in the PR body: #1066 must reach production, then plugin #16 merges, then brains #1069 merges, then this branch merges latest plugin main, regenerates again, passes checks, receives current approval, and only then may #17 merge. |
nir-ssvlabs
left a comment
There was a problem hiding this comment.
Reviewed the generated brains-write face at head 1a67c3b2. Verified the binding end-to-end rather than trusting the receipt:
- The digest binding holds and is enforced, not just declared. I recomputed
sha256(SKILL.md)on the committed artifact =f14839e4…, which equals theartifact_sha256in the committedcapability-catalog.jsonand the provenance receipt;catalog_sha256=c46b9cf2…matches too. The contract test recomputes this exact digest (createHash("sha256").update(writeSkill).digest("hex")) and asserts equality, so a hand-edit to the committed SKILL that skipped regeneration fails CI. The manifest fields the test pins (schema 1 / catalog_schema 1 / renderer 2 /capability_id: integration-actions/artifact_path) all match. - No internal capability leaked into the public face — 0 matches for
automation_secret/adminPool/handler_source/telegram_push/grant_token, and that exclusion is a test assertion. - The independent semantic safety assertions all resolve against the whitespace-normalized artifact (the tuple-only call shape, "no source-enum fallback", both
requires_confirmationbranches,rate_limited/dry_run/clarification/noopresult kinds, the self-confirm_actionprohibition, thediscard_actionpath, and the unknown-outcome guidance). That layer matters precisely because digest equality proves provenance but not that the source kept the safety rules — and here it did. The assertion set was broadened in this diff (addedclarification/noop/dry_run/partial-tuples/rate-limit-context), not narrowed, so no rule was silently dropped alongside the regeneration; stale fields (audit_id, the legacy source-enum pointer) stay absent and the trailing newline is present.
Design is sound: installation is fully local (artifact committed, bound by content digest, no runtime/install-time fetch), and the commit-free manifest correctly binds by digest rather than commit id given squash merges. The cross-repo sequencing and the "no extra prod release of #1069 needed" call are flagged to @RaekwonIII and are a release-governance decision, not a defect in this diff.
Not duplicating @RaekwonIII's byte-identity check of the catalog vs the hub manifest — I confirmed the other half (SKILL → digest binding + the semantic safety coverage). LGTM.
RaekwonIII
left a comment
There was a problem hiding this comment.
Re-reviewed at head 1a67c3b. This has flipped from my earlier hold to approve — every blocker that was open then is now cleared, and I verified each independently rather than trusting the receipts.
Gates — all four now met (verified)
- Gate 1 — #1066 on production.
9c64d3cdis onorigin/mainvia the#1090stage→main promotion. ✅ - Gate 2 — #16 on plugins
main. Merged; andorigin/mainis an ancestor of this branch, so #17 carries it. ✅ - Gate 3 — #1069 on brains
stage. Merged. ✅ - Gate 4 — regenerated from the final catalog. The brains-
stagemanifest is byte-identical to this PR'scapability-catalog.json(catalog_sha256 c46b9cf2…,artifact_sha256 f14839e4…,renderer_version 2), and I recomputedsha256of the committedSKILL.md→f14839e4…, matching both the manifest and the brains-side generated body. So the artifact is byte-identical to what the merged #1069 generator produces. ✅
Upstream Critical resolved
The architectural concern on #1069 (the seven faces were hand-authored literals, not projected from the structured catalog) was fixed structurally — renderIntegrationActionContract is now the single common projector all adapters call — and #1069 merged. renderer_version: 2 here reflects that; this artifact is the unified-projector output.
Ravid's QA items
- Trailing newline (LOW) — fixed;
SKILL.mdnow ends in\nand a newline contract was added. - Dropped safety clauses (LOW) — the safety-critical substance is present and if anything stronger: the inline-fire enumeration (
rsvp_event/create_draft/add_labels) with "do not infer safety from read vs write", theauto_failedunknown-outcome / don't-blind-retry rule, "neverconfirm_actionyourself — only the out-of-band surface holds the secret", and the restored rate-cap /dry_run/verify_mode:clauses. The two dropped phrasings were the safe-direction enumeration and a bolded restatement whose mechanic survives in thedraftrow. Reads as intentional compaction, not a regression — flagging for an explicit nod, not blocking. - MEDIUM 1 (catalog_sha256 not auto-verified cross-repo) — I confirmed it matches brains
stagemanually today, so the claim holds now; the systemic fix (automated cross-repo verification) is the documented GitHub-App follow-up. Accepting as ticketed. - MEDIUM 2 (semantic assertions string-match generated English across the repo boundary) — real maintainability cost: the first reword in brains will break plugins CI with an opaque failure and a two-repo fix. Conscious tradeoff with a documented follow-up (move the semantic gate monorepo-side / assert against structured
result_semantics). Worth keeping the ticket warm — it will bite once — but not a merge blocker.
The digest recompute (tamper-evident hand-edits), the internal-capability leak guard, and vendoring-with-no-install-time-fetch remain the right calls.
Verdict
Approve. Merge order is satisfied (all upstream gates green), the artifact is provably bound to the merged catalog, and the safety contract is intact. The two Mediums are legitimate follow-ups, not blockers — MEDIUM 2 especially is worth doing before the first catalog reword.
|
|
||
| ## Live Gmail search | ||
|
|
||
| `gmail-inbox` ships `search_emails` with `requires_confirmation:false`. |
There was a problem hiding this comment.
🟡 Names the gmail-inbox live-search action search_emails, but plugins/brains/skills/brains-read/SKILL.md:58 calls the same action query_emails and points the reader here for the details. One of the two makes the agent dispatch a non-existent action_name. Settle which is real and align both — this file is generated, so the fix belongs in the upstream catalog.
| ); | ||
| assert( | ||
| capabilityManifest.artifact_sha256 === | ||
| createHash("sha256").update(writeSkill, "utf8").digest("hex"), |
There was a problem hiding this comment.
🟡 The digest pin hashes writeSkill raw, while every other content pin in this file goes through normalizeRegion (line 123), which explicitly collapses \r\n. A checkout with core.autocrlf=true therefore fails generated brains-write artifact digest mismatch with no fixable cause — and .gitattributes is listed in .gitignore, so line endings can't be pinned per-repo either. Hash writeSkill.replace(/\r\n?/g, "\n") (or reuse normalizeRegion's EOL step) to match the generator's byte assumption.
What and why
Publishes the public
brains-writeface generated by BRNS-CORE-008's typedcapability catalog. The renderer-v2 manifest binds the artifact to the exact
catalog and artifact SHA-256 digests. Installation remains fully local: there
is no runtime or install-time fetch from the monorepo.
The generated contract fails closed for undeclared side effects and preserves
the canonical retry, verification, confirmation, and rate-limit rules without
maintaining a sixth hand-written copy.
Mandatory precedence — satisfied
The required cross-repository order is now complete:
ssvlabs/brains#1066was released tomain/production.ssvlabs/brains-plugins#16then merged as50424b21.ssvlabs/brains#1069merged into brainsstageassigned squash commit
58cabc5f.main(including fix(brains): Codex owns the MCP credential via its own OAuth login #16), regenerated from#1069's landed catalog, and revalidated the generated outputs.
No additional production release of #1069 is required before this PR merges.
The remaining merge gates are the normal current-head teammate approval and
green CI checks.
Final provenance receipt
58cabc5f306601c8871c0b35cb6fa9dddbfb6d6cd80a29e7047841b3e1da679110a9f8a7aa72d2ea1a67c3b2e5a9ba7f695d1fc1bcc17b76175d148c2c46b9cf2f88ed3cefe0f5766665c12f06dafaa0e56dba1f5586ab9cd56c39ac2f14839e4ed852771fc8dd91b0196f9caeeb63ce56dead747a53d83fd83dd9475commit-free because squash merge changes commit identity.
Verification
--check --plugin-root— 7/7 outputs freshbun run tests/plugin-contract/run.tsbun run tests/inbox-v2/run.tsbun run tests/tool-error/run.tsProduct decisions and one pending input — @RaekwonIII
Calling out @RaekwonIII explicitly:
only its source revision remains pending for historical comparison.
repository-limited, short-lived write/PR tokens. It opens a PR and never
auto-merges.
consumer exists; then revisit a versioned, language-neutral GitHub Release
that installations still vendor locally.
None of these product inputs blocks this bounded first slice.