mirror of
https://github.com/garrytan/gstack.git
synced 2026-10-31 14:06:50 +01:00
test(tree-receipt): a real gbrain stamp pair is same-modulo-stamps under gbrain committed policy (W1 acceptance)
Co-authored-by: capy-ai[bot] <230910855+capy-ai[bot]@users.noreply.github.com>
This commit is contained in:
1 parent
43c75a6bb6
commit
6cf53f9fed
3 files changed
+168
No files matched your search
+28
@@ -0,0 +1,28 @@
|
||||
{
|
||||
"source": {
|
||||
"repo": "garrytan/gbrain",
|
||||
"gated_commit": "2dcc32b4cb8d9685c80b8cf6e0f6768e9188cf4b",
|
||||
"stamp_commit": "3ffce57b27539afca57eb601d70a4d03e2ec2f10",
|
||||
"stamp_subject": "v0.60.270.0 chore(release): restamp onto master v0.60.269.0",
|
||||
"policy_commit": "90feaab2949d266ed8afc17a9b5a8785b4704406",
|
||||
"note": "stamp_files at the gated commit (the only paths the stamp commit touched) and that commit diff, byte for byte from the GitHub API"
|
||||
},
|
||||
"policy": "{\n \"bump\": \"patch\",\n \"queue_mode\": \"stamp-at-merge\",\n \"changelog\": \"CHANGELOG.md\",\n \"stamp_files\": [\n \"VERSION\", \"package.json\", \"CHANGELOG.md\", \"openclaw.plugin.json\",\n \".claude-plugin/plugin.json\", \".codex-plugin/plugin.json\",\n \"plugin-variants/*/.claude-plugin/plugin.json\", \"plugin-variants/*/.codex-plugin/plugin.json\",\n \"plugin-variants/*/README.md\", \"plugin/README.md\",\n \"BOOTSTRAP_FOR_AGENTS.md\", \"templates/bootstrap/template-repo/README.md\",\n \"src/core/behavior-change-notice.ts\"\n ],\n \"stamp_patterns\": [\n \"\\\"version\\\": \\\"{version}\\\"\",\n \"since: '{version}'\",\n \"<!-- gbrain-plugin-tree-stamp: {version} -->\",\n \"<!-- gbrain-template-stamp: {version} -->\",\n \"<!-- gbrain-runbook-stamp: {version} -->\"\n ],\n \"migrations\": { \"dir\": \"src/core/schema-migrations\", \"id\": \"^v(\\\\d+)-\" }\n}\n",
|
||||
"gated": {
|
||||
".claude-plugin/plugin.json": "{\n \"name\": \"gbrain\",\n \"version\": \"0.60.269.0\",\n \"description\": \"Personal knowledge brain for your coding agent — hybrid search, synthesis, graph traversal, and durable cross-session memory over Postgres/PGLite with pgvector, plus a curated brain-first skill set.\",\n \"author\": {\n \"name\": \"Garry Tan\",\n \"url\": \"https://github.com/garrytan\"\n },\n \"homepage\": \"https://github.com/garrytan/gbrain\",\n \"repository\": \"https://github.com/garrytan/gbrain\",\n \"license\": \"MIT\",\n \"keywords\": [\n \"memory\",\n \"knowledge-base\",\n \"mcp\",\n \"search\",\n \"agent\",\n \"brain\",\n \"pgvector\"\n ],\n \"skills\": \"./plugin/skills/\",\n \"mcpServers\": {\n \"gbrain\": {\n \"command\": \"${CLAUDE_PLUGIN_ROOT}/.agents/gbrain-launcher\",\n \"args\": [\n \"serve\",\n \"--surface\",\n \"full\",\n \"--source-guard\"\n ],\n \"cwd\": \"${CLAUDE_PLUGIN_ROOT}\"\n }\n }\n}\n",
|
||||
".codex-plugin/plugin.json": "{\n \"name\": \"gbrain\",\n \"version\": \"0.60.269.0\",\n \"description\": \"Personal knowledge brain for your coding agent — hybrid search, synthesis, graph traversal, and durable cross-session memory over Postgres/PGLite with pgvector, plus a curated brain-first skill set.\",\n \"author\": {\n \"name\": \"Garry Tan\",\n \"url\": \"https://github.com/garrytan\"\n },\n \"homepage\": \"https://github.com/garrytan/gbrain\",\n \"repository\": \"https://github.com/garrytan/gbrain\",\n \"license\": \"MIT\",\n \"keywords\": [\n \"memory\",\n \"knowledge-base\",\n \"mcp\",\n \"search\",\n \"agent\",\n \"brain\",\n \"pgvector\"\n ],\n \"skills\": \"./plugin/skills/\",\n \"mcpServers\": \"./.codex-plugin/mcp.json\",\n \"interface\": {\n \"displayName\": \"GBrain\",\n \"shortDescription\": \"Give your agent a persistent brain: search, synthesis, memory\",\n \"longDescription\": \"GBrain wires a personal knowledge brain into every session: hybrid keyword+vector search, entity graph traversal, synthesis, and memory your agent writes itself — served on the starter MCP surface (the seven memory verbs plus the daily-driver brain ops). Bundles the curated brain-first skill set: setup (walks install + gbrain init), cold-start day-one brain filling, ingest, query, briefing, upgrade, and more. Requires the gbrain CLI (bun install -g github:garrytan/gbrain#latest-stable) and a brain (gbrain init); the bundled setup skill walks the rest. Unix (macOS/Linux) only.\",\n \"developerName\": \"Garry Tan\",\n \"category\": \"Productivity\",\n \"capabilities\": [\n \"Interactive\",\n \"Write\"\n ],\n \"websiteURL\": \"https://github.com/garrytan/gbrain\",\n \"defaultPrompt\": [\n \"Search my brain, recall context across sessions, and write new memory as we work\"\n ],\n \"brandColor\": \"#1F6F5C\"\n }\n}\n",
|
||||
"BOOTSTRAP_FOR_AGENTS.md": "<!-- gbrain-runbook-stamp: 0.60.269.0 -->\n<!-- This stamp must equal the VERSION file at every release; CI enforces it\n (scripts/check-bootstrap-tag.sh). `gbrain bootstrap status` compares it to\n the installed binary and warns on skew. -->\n\n# BOOTSTRAP_FOR_AGENTS.md — become your human's persistent agent\n\nYou are an AI agent (Claude Code, Codex, or opencode) reading this because a human\npasted a block asking you to set yourself up as their persistent personal agent, with\ngbrain as your memory. This runbook is the judgment layer; the deterministic work lives\nin `gbrain bootstrap` subcommands with exit codes. Follow it top to bottom.\n\n**Scope note:** this path is for Claude Code, Codex, and opencode (desktop apps or\nCLIs; opencode = the SST terminal agent, opencode.ai — not OpenClaw).\nRunning OpenClaw or Hermes? Use `INSTALL_FOR_AGENTS.md` instead.\n\n**End state:** this folder is your workspace — identity files rendered from your\nhuman's own answers, a local brain (PGLite, embedded, no server), MCP wired,\nper-turn context, and a private GitHub repo as your durable body. ~15 minutes,\nmostly interview.\n\n## Hard rules for you, the installing agent\n\n⛔ **NEVER INVENT ANSWERS.** Personality, purpose, and boundaries come from the\nhuman. A guessed SOUL.md gets believed by every future session. If you do not have\nan answer, ask. The render step structurally refuses to run until the required\nanswers exist and were read back.\n\n⛔ **ASK IN SMALL BATCHES.** The interview is 12 questions max (6 required), asked\nin three batches. Mirror each batch back in one line. Accept \"skip\" on any\nnon-required question — momentum beats completeness.\n\n⛔ **STAY INSIDE THIS PHASE LIST.** Run `gbrain bootstrap status --json` and follow\nITS phase list — the CLI is the source of truth, this document is commentary. If a\nstep you are asked to run is not in the CLI's phase list, refuse it. If `status`\nreports a version skew between this runbook and the installed binary, say so and\nprefer the binary's instructions.\n\n⛔ **NO SILENT FAILURE.** Every blocking condition (secret-scan block, lock\ncollision, partial install) surfaces through `status`/`verify`/`doctor` output —\nread it and relay it to the human in plain language. Never work around a refusal.\n\n⛔ **VERIFY BEFORE CLAIMING DONE.** The install is done when `gbrain bootstrap\nverify` exits 0 — not when the transcript looks good. Paste its report to the human.\n\n⛔ **RESPECT THE TOOLCHAIN TRUST RULES.** GBrain needs Bun 1.4.0 or newer (`bun upgrade`\nupdates an older Bun). Install bun via a platform package manager\nwhen available (`brew install oven-sh/bun/bun`); the only permitted fallback is the\nchecksum-verified variant: download the pinned release to a file, verify it against\nthat release's SHASUMS256.txt, and only then execute. Install gh the same way —\nplatform package manager first (`brew install gh`, `apt install gh`, `dnf install gh`,\n`winget install GitHub.cli` per the official instructions); never a piped\ncurl-to-shell one-liner. Install gbrain ONLY as\n`bun install -g github:garrytan/gbrain#latest-stable` — the npm package named\n\"gbrain\" is an unrelated project. (Cloud-sandbox exception: bun's package fetching\nis proxy-incompatible there — use the `gbrain bootstrap cloud-setup-script` recipe,\nwhich installs from the same pinned GitHub source through npm.)\n\n⛔ **NEVER FABRICATE TOOLING.** If gh or any preflight binary is missing, blocked\nby a sandbox egress proxy, or answering 403s, report that through\n`status`/`doctor` output and follow the cloud-sandbox guidance below. Never\nhand-roll a gh shim, stub a fake binary into /usr/local/bin, or fake a passing\ncheck — a fabricated tool poisons every later verification, and the one time it\nwas tried it masked a real silent-persistence failure. The CLI degrades honestly\non its own; your job is to relay, not to bridge.\n\n## Codex preflight (ChatGPT desktop / Codex CLI only)\n\nCodex sandboxes command execution. Before starting, tell the human: \"I'll need\napproval to run install commands (bun, gh, gbrain) and to write in this folder —\napprove those prompts when they appear.\" If approvals are globally disabled, ask the\nhuman to enable workspace-write + network for this session. Count the approval taps\nyou needed; report the count at the end (it feeds the install-time measurement).\n\nIf the gbrain PLUGIN is already installed and enabled (codex: `[plugins.\"gbrain@…\"]\nenabled = true`; Claude Code: `enabledPlugins[\"gbrain@…\"] = true`), the hooks phase\nskips its own `mcp add` on that harness — the plugin already provides the MCP server\n(one owner per name). That skip is healthy, not an error; force the hand-wired\nregistration only with `--mcp-even-if-plugin`.\n\n## Phase walkthrough (commentary — the CLI's list wins)\n\n1. **Preflight.** `git`, `bun`, `gh` present. Install what's missing perLine truncated
|
||||
"VERSION": "0.60.269.0\n",
|
||||
"openclaw.plugin.json": "{\n \"id\": \"gbrain-context-engine\",\n \"name\": \"gbrain\",\n \"version\": \"0.60.269.0\",\n \"description\": \"Personal knowledge brain with Postgres + pgvector hybrid search\",\n \"family\": \"bundle-plugin\",\n \"kind\": \"context-engine\",\n \"configSchema\": {\n \"type\": \"object\",\n \"properties\": {\n \"database_url\": {\n \"type\": \"string\",\n \"description\": \"PostgreSQL connection URL (Supabase recommended)\"\n },\n \"openai_api_key\": {\n \"type\": \"string\",\n \"description\": \"OpenAI API key for embeddings (uses OPENAI_API_KEY env var if not set)\"\n },\n \"workspaceDir\": {\n \"type\": \"string\",\n \"description\": \"Absolute workspace for legacy hosts without per-session workspace context; omit for multi-agent hosts\"\n }\n }\n },\n \"uiHints\": {\n \"database_url\": {\n \"sensitive\": true\n },\n \"openai_api_key\": {\n \"sensitive\": true\n }\n },\n \"mcpServers\": {\n \"gbrain\": {\n \"command\": \"./.agents/gbrain-launcher\",\n \"args\": [\n \"serve\"\n ]\n }\n },\n \"skills\": [\n \"skills/academic-verify\",\n \"skills/archive-crawler\",\n \"skills/article-enrichment\",\n \"skills/ask-user\",\n \"skills/blog-ingest\",\n \"skills/book-mirror\",\n \"skills/brain-ingest-gate\",\n \"skills/brain-link-discipline\",\n \"skills/brain-ops\",\n \"skills/brain-pdf\",\n \"skills/brain-taxonomist\",\n \"skills/briefing\",\n \"skills/bulk-ingestion\",\n \"skills/capture\",\n \"skills/chat-connectors\",\n \"skills/citation-fixer\",\n \"skills/citation-graph-ingest\",\n \"skills/cold-start\",\n \"skills/company-brainify\",\n \"skills/concept-synthesis\",\n \"skills/context-audit\",\n \"skills/conversation-archive\",\n \"skills/correction-pipeline\",\n \"skills/cron-scheduler\",\n \"skills/cross-modal-review\",\n \"skills/daily-task-manager\",\n \"skills/daily-task-prep\",\n \"skills/data-loss-gate\",\n \"skills/data-research\",\n \"skills/draft-in-voice\",\n \"skills/eiirp\",\n \"skills/enrich\",\n \"skills/fact-check\",\n \"skills/functional-area-resolver\",\n \"skills/gbrain-advisor\",\n \"skills/google-loops\",\n \"skills/idea-ingest\",\n \"skills/idea-lineage\",\n \"skills/ingest\",\n \"skills/maintain\",\n \"skills/mcp-access\",\n \"skills/measure-before-you-fix\",\n \"skills/media-ingest\",\n \"skills/meeting-ingestion\",\n \"skills/minion-orchestrator\",\n \"skills/perplexity-research\",\n \"skills/publish\",\n \"skills/query\",\n \"skills/repo-architecture\",\n \"skills/reports\",\n \"skills/research-compendium\",\n \"skills/resolve-before-asking\",\n \"skills/signal-detector\",\n \"skills/skill-autobench\",\n \"skills/skill-creator\",\n \"skills/skillify\",\n \"skills/skillpack-check\",\n \"skills/skillpack-harvest\",\n \"skills/soul-audit\",\n \"skills/strategic-reading\",\n \"skills/testing\",\n \"skills/two-tier-extraction\",\n \"skills/voice-note-ingest\",\n \"skills/webhook-transforms\"\n ],\n \"shared_deps\": [\n \"skills/conventions\",\n \"skills/_AGENT_README.md\",\n \"skills/_brain-filing-rules.md\",\n \"skills/_brain-filing-rules.json\",\n \"skills/_output-rules.md\"\n ],\n \"excluded_from_install\": [\n \"skills/setup\",\n \"skills/migrate\",\n \"skills/publish\"\n ],\n \"openclaw\": {\n \"compat\": {\n \"pluginApi\": \">=2026.4.0\"\n }\n },\n \"contracts\": {\n \"contextEngines\": [\n \"gbrain-context-engine\",\n \"gbrain-context\"\n ]\n }\n}\n",
|
||||
"package.json": "{\n \"name\": \"gbrain\",\n \"description\": \"Postgres-native personal knowledge brain with hybrid RAG search\",\n \"type\": \"module\",\n \"imports\": {\n \"#postgres\": {\n \"types\": \"./vendor/postgres/types/index.d.ts\",\n \"require\": \"./vendor/postgres/cjs/src/index.js\",\n \"default\": \"./vendor/postgres/src/index.js\"\n }\n },\n \"main\": \"src/core/index.ts\",\n \"bin\": {\n \"gbrain\": \"src/cli.ts\"\n },\n \"exports\": {\n \".\": \"./src/core/index.ts\",\n \"./engine\": \"./src/core/engine.ts\",\n \"./types\": \"./src/core/types.ts\",\n \"./operations\": \"./src/core/operations.ts\",\n \"./minions\": \"./src/core/minions/index.ts\",\n \"./engine-factory\": \"./src/core/engine-factory.ts\",\n \"./pglite-engine\": \"./src/core/pglite-engine.ts\",\n \"./link-extraction\": \"./src/core/link-extraction.ts\",\n \"./import-file\": \"./src/core/import-file.ts\",\n \"./transcription\": \"./src/core/transcription.ts\",\n \"./embedding\": \"./src/core/embedding.ts\",\n \"./config\": \"./src/core/config.ts\",\n \"./markdown\": \"./src/core/markdown.ts\",\n \"./backoff\": \"./src/core/backoff.ts\",\n \"./search/hybrid\": \"./src/core/search/hybrid.ts\",\n \"./search/expansion\": \"./src/core/search/expansion.ts\",\n \"./search/evidence-delivery\": \"./src/core/search/evidence-delivery.ts\",\n \"./eval/longmemeval/reader\": \"./src/eval/longmemeval/reader.ts\",\n \"./think\": \"./src/core/think/index.ts\",\n \"./ai/gateway\": \"./src/core/ai/gateway.ts\",\n \"./ai/invocation-guard\": \"./src/core/ai/invocation-guard.ts\",\n \"./core/model-pricing\": \"./src/core/model-pricing.ts\",\n \"./extract\": \"./src/commands/extract.ts\",\n \"./ingestion\": \"./src/core/ingestion/index.ts\",\n \"./ingestion/test-harness\": \"./src/core/ingestion/test-harness.ts\",\n \"./core/guardrails\": \"./src/core/guardrails.ts\",\n \"./core/skillopt\": \"./src/core/skillopt/index.ts\",\n \"./pglite-lock\": \"./src/core/pglite-lock.ts\",\n \"./version\": \"./src/version.ts\"\n },\n \"scripts\": {\n \"dev\": \"bun run src/cli.ts\",\n \"build\": \"bun build --compile --no-compile-autoload-bunfig --outfile bin/gbrain src/cli.ts\",\n \"build:all\": \"bun build --compile --no-compile-autoload-bunfig --target=bun-darwin-arm64 --outfile bin/gbrain-darwin-arm64 src/cli.ts && bun build --compile --no-compile-autoload-bunfig --target=bun-linux-x64 --outfile bin/gbrain-linux-x64 src/cli.ts\",\n \"build:admin\": \"cd admin && bun run build && cd .. && bun run scripts/build-admin-embedded.ts\",\n \"build:admin-embedded\": \"bun run scripts/build-admin-embedded.ts\",\n \"build:schema\": \"bun run scripts/build-schema.ts\",\n \"build:schema-migrations\": \"bun run scripts/build-schema-migrations.ts\",\n \"new:migration\": \"bun run scripts/build-schema-migrations.ts --new\",\n \"build:llms\": \"bun run scripts/build-llms.ts\",\n \"wave-security-scan\": \"bash scripts/wave-security-scan.sh\",\n \"audit:contributors\": \"bun scripts/contributor-audit.ts\",\n \"build:flag-registry\": \"bun run scripts/generate-flag-registry.ts\",\n \"build:operation-manifest\": \"bun run scripts/build-operation-manifest.ts\",\n \"weights:mine\": \"bun run scripts/mine-shard-weights.ts\",\n \"build:pglite-snapshot\": \"bun run scripts/build-pglite-snapshot.ts\",\n \"bench:efficiency\": \"bash scripts/bench/efficiency/run-all.sh\",\n \"bench:parity\": \"bash scripts/bench/contract-parity.sh\",\n \"test\": \"bash scripts/run-unit-parallel.sh\",\n \"test:admin\": \"playwright test --config admin/playwright.config.ts\",\n \"eval:autocut\": \"bun test test/search/autocut-eval.test.ts\",\n \"test:full\": \"bun run verify && bash scripts/run-unit-parallel.sh && bun run test:slow && (if [ -n \\\"$DATABASE_URL\\\" ]; then bash scripts/run-e2e.sh; else echo '[test:full] skipped E2E (no DATABASE_URL); run docker-compose -f docker-compose.ci.yml up + bun run test:e2e to include' 1>&2; fi)\",\n \"verify\": \"bash scripts/run-verify-parallel.sh\",\n \"check:source-config-leak\": \"bash scripts/check-source-config-leak.sh\",\n \"check:no-pii-agent-voice\": \"bash scripts/check-no-pii-in-agent-voice.sh\",\n \"check:synthetic-corpus-privacy\": \"bash scripts/check-synthetic-corpus-privacy.sh\",\n \"check:system-of-record\": \"bash scripts/check-system-of-record.sh\",\n \"check:admin-scope-drift\": \"bash scripts/check-admin-scope-drift.sh\",\n \"check:cli-exec\": \"bash scripts/check-cli-executable.sh\",\n \"check:engine-dynamic-import\": \"bash scripts/check-engine-dynamic-import.sh\",\n \"check:grok-pin\": \"bash scripts/check-grok-pin.sh\",\n \"check:opencode-pin\": \"bash scripts/check-opencode-pin.sh\",\n \"check:pin-doc-privacy\": \"bash scripts/check-pin-doc-privacy.sh\",\n \"check:gateway-routed\": \"bash scripts/check-gateway-routed-noLine truncated
|
||||
"plugin-variants/gbrain-coding/.claude-plugin/plugin.json": "{\n \"name\": \"gbrain-coding\",\n \"version\": \"0.60.269.0\",\n \"description\": \"Brain-first coding agent working inside a repo: retrieval, routing, ingest discipline, correction hygiene. Default persona for the claude-code harness bridge; also published as the gbrain-coding marketplace variant. (persona variant of the gbrain plugin — 21 skills)\",\n \"author\": {\n \"name\": \"Garry Tan\",\n \"url\": \"https://github.com/garrytan\"\n },\n \"homepage\": \"https://github.com/garrytan/gbrain\",\n \"repository\": \"https://github.com/garrytan/gbrain\",\n \"license\": \"MIT\",\n \"keywords\": [\n \"memory\",\n \"knowledge-base\",\n \"mcp\",\n \"search\",\n \"agent\",\n \"brain\",\n \"pgvector\"\n ],\n \"skills\": \"./skills/\",\n \"mcpServers\": {\n \"gbrain\": {\n \"command\": \"${CLAUDE_PLUGIN_ROOT}/.agents/gbrain-launcher\",\n \"args\": [\n \"serve\",\n \"--surface\",\n \"full\",\n \"--source-guard\"\n ],\n \"cwd\": \"${CLAUDE_PLUGIN_ROOT}\"\n }\n }\n}\n",
|
||||
"plugin-variants/gbrain-coding/.codex-plugin/plugin.json": "{\n \"name\": \"gbrain-coding\",\n \"version\": \"0.60.269.0\",\n \"description\": \"Brain-first coding agent working inside a repo: retrieval, routing, ingest discipline, correction hygiene. Default persona for the claude-code harness bridge; also published as the gbrain-coding marketplace variant. (persona variant of the gbrain plugin — 21 skills)\",\n \"author\": {\n \"name\": \"Garry Tan\",\n \"url\": \"https://github.com/garrytan\"\n },\n \"homepage\": \"https://github.com/garrytan/gbrain\",\n \"repository\": \"https://github.com/garrytan/gbrain\",\n \"license\": \"MIT\",\n \"keywords\": [\n \"memory\",\n \"knowledge-base\",\n \"mcp\",\n \"search\",\n \"agent\",\n \"brain\",\n \"pgvector\"\n ],\n \"skills\": \"./skills/\",\n \"mcpServers\": \"./.codex-plugin/mcp.json\",\n \"interface\": {\n \"displayName\": \"GBrain\",\n \"shortDescription\": \"Give your agent a persistent brain: search, synthesis, memory\",\n \"longDescription\": \"GBrain wires a personal knowledge brain into every session: hybrid keyword+vector search, entity graph traversal, synthesis, and memory your agent writes itself — served on the starter MCP surface (the seven memory verbs plus the daily-driver brain ops). Bundles the curated brain-first skill set: setup (walks install + gbrain init), cold-start day-one brain filling, ingest, query, briefing, upgrade, and more. Requires the gbrain CLI (bun install -g github:garrytan/gbrain#latest-stable) and a brain (gbrain init); the bundled setup skill walks the rest. Unix (macOS/Linux) only.\",\n \"developerName\": \"Garry Tan\",\n \"category\": \"Productivity\",\n \"capabilities\": [\n \"Interactive\",\n \"Write\"\n ],\n \"websiteURL\": \"https://github.com/garrytan/gbrain\",\n \"defaultPrompt\": [\n \"Search my brain, recall context across sessions, and write new memory as we work\"\n ],\n \"brandColor\": \"#1F6F5C\"\n }\n}\n",
|
||||
"plugin-variants/gbrain-coding/README.md": "<!-- gbrain-plugin-tree-stamp: 0.60.269.0 -->\n# gbrain-coding (generated persona variant — do not hand-edit)\n\nBrain-first coding agent working inside a repo: retrieval, routing, ingest discipline, correction hygiene. Default persona for the claude-code harness bridge; also published as the gbrain-coding marketplace variant.\n\n21 skills curated from the gbrain plugin lane (persona\n`coding-agent` in `skills/plugin-lanes.json#personas`, one recorded\nreason per skill). Install exactly ONE gbrain plugin per machine — every\nvariant serves the same `gbrain` MCP server name, so two installed variants\nwould double-serve. The full-lane plugin's README carries the MCP surface\nnote; it applies verbatim here.\n\nRegenerate with `bun run scripts/generate-plugin-tree.ts --out plugin\n--variants-out plugin-variants`.\n",
|
||||
"plugin-variants/gbrain-daily/.claude-plugin/plugin.json": "{\n \"name\": \"gbrain-daily\",\n \"version\": \"0.60.269.0\",\n \"description\": \"Personal knowledge-brain daily use: meetings, tasks, briefings, reading, research. Published as the gbrain-daily marketplace variant. (persona variant of the gbrain plugin — 20 skills)\",\n \"author\": {\n \"name\": \"Garry Tan\",\n \"url\": \"https://github.com/garrytan\"\n },\n \"homepage\": \"https://github.com/garrytan/gbrain\",\n \"repository\": \"https://github.com/garrytan/gbrain\",\n \"license\": \"MIT\",\n \"keywords\": [\n \"memory\",\n \"knowledge-base\",\n \"mcp\",\n \"search\",\n \"agent\",\n \"brain\",\n \"pgvector\"\n ],\n \"skills\": \"./skills/\",\n \"mcpServers\": {\n \"gbrain\": {\n \"command\": \"${CLAUDE_PLUGIN_ROOT}/.agents/gbrain-launcher\",\n \"args\": [\n \"serve\",\n \"--surface\",\n \"full\",\n \"--source-guard\"\n ],\n \"cwd\": \"${CLAUDE_PLUGIN_ROOT}\"\n }\n }\n}\n",
|
||||
"plugin-variants/gbrain-daily/.codex-plugin/plugin.json": "{\n \"name\": \"gbrain-daily\",\n \"version\": \"0.60.269.0\",\n \"description\": \"Personal knowledge-brain daily use: meetings, tasks, briefings, reading, research. Published as the gbrain-daily marketplace variant. (persona variant of the gbrain plugin — 20 skills)\",\n \"author\": {\n \"name\": \"Garry Tan\",\n \"url\": \"https://github.com/garrytan\"\n },\n \"homepage\": \"https://github.com/garrytan/gbrain\",\n \"repository\": \"https://github.com/garrytan/gbrain\",\n \"license\": \"MIT\",\n \"keywords\": [\n \"memory\",\n \"knowledge-base\",\n \"mcp\",\n \"search\",\n \"agent\",\n \"brain\",\n \"pgvector\"\n ],\n \"skills\": \"./skills/\",\n \"mcpServers\": \"./.codex-plugin/mcp.json\",\n \"interface\": {\n \"displayName\": \"GBrain\",\n \"shortDescription\": \"Give your agent a persistent brain: search, synthesis, memory\",\n \"longDescription\": \"GBrain wires a personal knowledge brain into every session: hybrid keyword+vector search, entity graph traversal, synthesis, and memory your agent writes itself — served on the starter MCP surface (the seven memory verbs plus the daily-driver brain ops). Bundles the curated brain-first skill set: setup (walks install + gbrain init), cold-start day-one brain filling, ingest, query, briefing, upgrade, and more. Requires the gbrain CLI (bun install -g github:garrytan/gbrain#latest-stable) and a brain (gbrain init); the bundled setup skill walks the rest. Unix (macOS/Linux) only.\",\n \"developerName\": \"Garry Tan\",\n \"category\": \"Productivity\",\n \"capabilities\": [\n \"Interactive\",\n \"Write\"\n ],\n \"websiteURL\": \"https://github.com/garrytan/gbrain\",\n \"defaultPrompt\": [\n \"Search my brain, recall context across sessions, and write new memory as we work\"\n ],\n \"brandColor\": \"#1F6F5C\"\n }\n}\n",
|
||||
"plugin-variants/gbrain-daily/README.md": "<!-- gbrain-plugin-tree-stamp: 0.60.269.0 -->\n# gbrain-daily (generated persona variant — do not hand-edit)\n\nPersonal knowledge-brain daily use: meetings, tasks, briefings, reading, research. Published as the gbrain-daily marketplace variant.\n\n20 skills curated from the gbrain plugin lane (persona\n`daily-driver` in `skills/plugin-lanes.json#personas`, one recorded\nreason per skill). Install exactly ONE gbrain plugin per machine — every\nvariant serves the same `gbrain` MCP server name, so two installed variants\nwould double-serve. The full-lane plugin's README carries the MCP surface\nnote; it applies verbatim here.\n\nRegenerate with `bun run scripts/generate-plugin-tree.ts --out plugin\n--variants-out plugin-variants`.\n",
|
||||
"plugin/README.md": "<!-- gbrain-plugin-tree-stamp: 0.60.269.0 -->\n# gbrain plugin skill tree (generated — do not hand-edit)\n\nThis tree is the curated skill set for the gbrain Codex and Claude Code\nplugins. Regenerate with `bun run scripts/generate-plugin-tree.ts --out plugin`;\ncuration lives in `skills/plugin-lanes.json` (one recorded decision per\naddition/exclusion).\n\n## MCP surface note (read once)\n\nThe plugin's MCP server runs `gbrain serve --surface full` — 172\noperations, the same surface every stdio registration gbrain writes pins.\nEvery gbrain operation the bundled skills name is on it. A harness that caps\nits tool count can narrow this machine's plugin surface with\n`GBRAIN_SURFACE=starter` (or `verbs`); the server honors it and new sessions\npick it up. Skills keep their first-class `gbrain` CLI paths for anything a\nnarrowed list leaves out.\n\n## Requirements\n\n- gbrain CLI installed: `bun install -g github:garrytan/gbrain#latest-stable`\n (the npm package named `gbrain` is unrelated — never `npm install -g gbrain`).\n- A brain: `gbrain init` (the bundled `setup` skill walks the full path).\n",
|
||||
"templates/bootstrap/template-repo/README.md": "# gbrain agent workspace — template\n\n<!-- gbrain-template-stamp: 0.60.269.0 -->\n\nThis repository is the **\"Use this template\"** distribution artifact for a\n[gbrain](https://github.com/garrytan/gbrain) personal-agent workspace — the same\nfile set `gbrain bootstrap render` produces, with every value still a\n`{{TOKEN}}` placeholder. Nothing in this tree is real data: your agent fills the\nplaceholders from YOUR interview answers, on your machine.\n\n## Use this template\n\n1. Click **Use this template → Create a new repository**, and make the new\n repository **Private**. The bootstrap flow refuses to put identity files in\n a public repository.\n2. Clone your new repository, then open Claude Code or Codex (desktop app or\n CLI) in that folder.\n3. Paste this into your agent:\n\n ```\n Read and follow every step of:\n https://raw.githubusercontent.com/garrytan/gbrain/latest-stable/BOOTSTRAP_FOR_AGENTS.md\n Goal: finish setting up this cloned template as my persistent personal\n agent, with gbrain as your memory. Interview me before writing any\n identity file — never invent answers. You are not done until\n `gbrain bootstrap verify` exits 0.\n ```\n\n Already running the gbrain CLI\n (`bun install -g github:garrytan/gbrain#latest-stable`)? Then the first\n step is always:\n\n ```\n gbrain bootstrap status\n ```\n\n `bootstrap status` hard-fails while this repository's `origin` is public,\n before any identity file lands.\n\n## What's in this tree\n\n- `agent.json` — workspace manifest with `initialized: false`; `gbrain\n bootstrap render` flips it to `true` on your machine. That flag (never the\n file's mere presence) is what distinguishes a fresh template clone from a\n machine-two clone of a live workspace.\n- Identity files (`SOUL.md`, `USER.md`, `MEMORY.md`, …) and operating\n contracts (`AGENTS.md`, `HEARTBEAT.md`, `ACCESS_POLICY.md`, `GITHUB.md`) —\n placeholder-only until your interview.\n- `.gitignore` — pre-configured so the local brain database, env files, and\n machine-local state never reach this repository.\n\nThis README is generated by gbrain's release pipeline; edits made here are\noverwritten on the next gbrain release. The stamp at the top records the\ngbrain version that generated this tree — `gbrain bootstrap status` compares\nit to your installed binary and warns on skew.\n"
|
||||
},
|
||||
"stamp_diff": "diff --git a/.claude-plugin/plugin.json b/.claude-plugin/plugin.json\nindex d624525846..f07db3983f 100644\n--- a/.claude-plugin/plugin.json\n+++ b/.claude-plugin/plugin.json\n@@ -1,6 +1,6 @@\n {\n \"name\": \"gbrain\",\n- \"version\": \"0.60.269.0\",\n+ \"version\": \"0.60.270.0\",\n \"description\": \"Personal knowledge brain for your coding agent — hybrid search, synthesis, graph traversal, and durable cross-session memory over Postgres/PGLite with pgvector, plus a curated brain-first skill set.\",\n \"author\": {\n \"name\": \"Garry Tan\",\ndiff --git a/.codex-plugin/plugin.json b/.codex-plugin/plugin.json\nindex b09a13b223..89a5e8aaa3 100644\n--- a/.codex-plugin/plugin.json\n+++ b/.codex-plugin/plugin.json\n@@ -1,6 +1,6 @@\n {\n \"name\": \"gbrain\",\n- \"version\": \"0.60.269.0\",\n+ \"version\": \"0.60.270.0\",\n \"description\": \"Personal knowledge brain for your coding agent — hybrid search, synthesis, graph traversal, and durable cross-session memory over Postgres/PGLite with pgvector, plus a curated brain-first skill set.\",\n \"author\": {\n \"name\": \"Garry Tan\",\ndiff --git a/BOOTSTRAP_FOR_AGENTS.md b/BOOTSTRAP_FOR_AGENTS.md\nindex bdf32f0f26..98b9788881 100644\n--- a/BOOTSTRAP_FOR_AGENTS.md\n+++ b/BOOTSTRAP_FOR_AGENTS.md\n@@ -1,4 +1,4 @@\n-<!-- gbrain-runbook-stamp: 0.60.269.0 -->\n+<!-- gbrain-runbook-stamp: 0.60.270.0 -->\n <!-- This stamp must equal the VERSION file at every release; CI enforces it\n (scripts/check-bootstrap-tag.sh). `gbrain bootstrap status` compares it to\n the installed binary and warns on skew. -->\ndiff --git a/VERSION b/VERSION\nindex f8c08a1cd2..3abf5505bd 100644\n--- a/VERSION\n+++ b/VERSION\n@@ -1 +1 @@\n-0.60.269.0\n+0.60.270.0\ndiff --git a/openclaw.plugin.json b/openclaw.plugin.json\nindex 767c75beef..1581a4201f 100644\n--- a/openclaw.plugin.json\n+++ b/openclaw.plugin.json\n@@ -1,7 +1,7 @@\n {\n \"id\": \"gbrain-context-engine\",\n \"name\": \"gbrain\",\n- \"version\": \"0.60.269.0\",\n+ \"version\": \"0.60.270.0\",\n \"description\": \"Personal knowledge brain with Postgres + pgvector hybrid search\",\n \"family\": \"bundle-plugin\",\n \"kind\": \"context-engine\",\ndiff --git a/package.json b/package.json\nindex 7f91d7bdd1..0f5f1f7018 100644\n--- a/package.json\n+++ b/package.json\n@@ -238,7 +238,7 @@\n \"bun\": \">=1.4.0\"\n },\n \"license\": \"MIT\",\n- \"version\": \"0.60.269.0\",\n+ \"version\": \"0.60.270.0\",\n \"overrides\": {\n \"@ai-sdk/provider-utils\": \"4.0.56\",\n \"@hono/node-server\": \"^2.0.5\",\ndiff --git a/plugin-variants/gbrain-coding/.claude-plugin/plugin.json b/plugin-variants/gbrain-coding/.claude-plugin/plugin.json\nindex 1e78079b00..681de7cc89 100644\n--- a/plugin-variants/gbrain-coding/.claude-plugin/plugin.json\n+++ b/plugin-variants/gbrain-coding/.claude-plugin/plugin.json\n@@ -1,6 +1,6 @@\n {\n \"name\": \"gbrain-coding\",\n- \"version\": \"0.60.269.0\",\n+ \"version\": \"0.60.270.0\",\n \"description\": \"Brain-first coding agent working inside a repo: retrieval, routing, ingest discipline, correction hygiene. Default persona for the claude-code harness bridge; also published as the gbrain-coding marketplace variant. (persona variant of the gbrain plugin — 21 skills)\",\n \"author\": {\n \"name\": \"Garry Tan\",\ndiff --git a/plugin-variants/gbrain-coding/.codex-plugin/plugin.json b/plugin-variants/gbrain-coding/.codex-plugin/plugin.json\nindex dbde499618..e1c48f33ab 100644\n--- a/plugin-variants/gbrain-coding/.codex-plugin/plugin.json\n+++ b/plugin-variants/gbrain-coding/.codex-plugin/plugin.json\n@@ -1,6 +1,6 @@\n {\n \"name\": \"gbrain-coding\",\n- \"version\": \"0.60.269.0\",\n+ \"version\": \"0.60.270.0\",\n \"description\": \"Brain-first coding agent working inside a repo: retrieval, routing, ingest discipline, correction hygiene. Default persona for the claude-code harness bridge; also published as the gbrain-coding marketplace variant. (persona variant of the gbrain plugin — 21 skills)\",\n \"author\": {\n \"name\": \"Garry Tan\",\ndiff --git a/plugin-variants/gbrain-coding/README.md b/plugin-variants/gbrain-coding/README.md\nindex b1930d5d09..9eca046758 100644\n--- a/plugin-variants/gbrain-coding/README.md\n+++ b/plugin-variants/gbrain-coding/README.md\n@@ -1,4 +1,4 @@\n-<!-- gbrain-plugin-tree-stamp: 0.60.269.0 -->\n+<!-- gbrain-plugin-tree-stamp: 0.60.270.0 -->\n # gbrain-coding (generated persona variant — do not hand-edit)\n \n Brain-first coding agent working inside a repo: retrieval, routing, ingest discipline, correction hygiene. Default persona for the claude-code harness bridge; also published as the gbrain-coding marketplace variant.\ndiff --git a/plugin-variants/gbrain-daily/.claude-plugin/plugin.json b/plugin-variants/gbrain-daily/.claude-plugin/plugin.json\nindex d0c9e119eb..bbbc9d3b63 100644\n--- a/plugin-variants/gbrain-daily/.claude-plugin/plugin.json\n+++ b/plugin-variants/gbrain-daily/Line truncated
|
||||
}
|
||||
@@ -0,0 +1,76 @@
|
||||
/**
|
||||
* Fixtures for gstack-ship-queue and the gbrain stamp-pair acceptance: a
|
||||
* hermetic repo (bare origin plus working clone under os.tmpdir(), its own git
|
||||
* identity) seeded from test/fixtures/ship-queue/gbrain-stamp-pair.json, the
|
||||
* stamp files of a real gbrain stamp commit at its parent plus that commit's
|
||||
* diff and gbrain's committed .gstack/ship-policy.json, byte for byte.
|
||||
*/
|
||||
import { spawnSync } from 'node:child_process';
|
||||
import * as fs from 'node:fs';
|
||||
import * as os from 'node:os';
|
||||
import * as path from 'node:path';
|
||||
import { gitArgvIn } from './scratch-repo';
|
||||
import type { FixtureRepo } from './restamp-fixture';
|
||||
|
||||
export const ROOT = path.resolve(import.meta.dir, '..', '..');
|
||||
|
||||
export interface GbrainPair {
|
||||
source: { repo: string; gated_commit: string; stamp_commit: string; stamp_subject: string; policy_commit: string; note: string };
|
||||
policy: string;
|
||||
gated: Record<string, string>;
|
||||
stamp_diff: string;
|
||||
}
|
||||
|
||||
export function loadGbrainPair(): GbrainPair {
|
||||
return JSON.parse(fs.readFileSync(path.join(ROOT, 'test', 'fixtures', 'ship-queue', 'gbrain-stamp-pair.json'), 'utf8'));
|
||||
}
|
||||
|
||||
/** A bare origin plus working clone with its own git identity; nothing committed yet. */
|
||||
export function emptyRepo(prefix: string): FixtureRepo {
|
||||
const root = fs.mkdtempSync(path.join(os.tmpdir(), prefix));
|
||||
const origin = path.join(root, 'origin.git');
|
||||
const work = path.join(root, 'work');
|
||||
const home = path.join(root, 'home');
|
||||
fs.mkdirSync(home, { recursive: true });
|
||||
fs.mkdirSync(work, { recursive: true });
|
||||
const env = { GSTACK_HOME: home, GSTACK_STATE_DIR: home, HOME: home, GIT_CONFIG_GLOBAL: path.join(root, 'gitconfig'), GIT_CONFIG_NOSYSTEM: '1' };
|
||||
fs.writeFileSync(env.GIT_CONFIG_GLOBAL, '[user]\n\tname = t\n\temail = t@test\n[commit]\n\tgpgsign = false\n[init]\n\tdefaultBranch = main\n');
|
||||
const git = (...args: string[]): string => {
|
||||
const r = gitArgvIn(work, args, 30_000, { ...process.env, ...env });
|
||||
if (r.status !== 0) throw new Error(`git ${args.join(' ')} failed: ${r.stderr?.toString()}`);
|
||||
return r.stdout?.toString().trim() ?? '';
|
||||
};
|
||||
spawnSync('git', ['init', '-q', '--bare', origin], { timeout: 30_000, env: { ...process.env, ...env } });
|
||||
git('init', '-q', '-b', 'main');
|
||||
git('remote', 'add', 'origin', origin);
|
||||
return { root, work, origin, home, git, env };
|
||||
}
|
||||
|
||||
/**
|
||||
* main holds gbrain's policy and the stamp files at the gated commit; HEAD
|
||||
* is that commit (the gated head). Returns the repo and a function that
|
||||
* commits the real stamp diff on top (the stamped head).
|
||||
*/
|
||||
export function gbrainPairRepo(): { repo: FixtureRepo; pair: GbrainPair; gated: string; stamp: () => string } {
|
||||
const pair = loadGbrainPair();
|
||||
const repo = emptyRepo('gstack-gbrain-pair-');
|
||||
for (const [rel, text] of Object.entries(pair.gated)) {
|
||||
fs.mkdirSync(path.dirname(path.join(repo.work, rel)), { recursive: true });
|
||||
fs.writeFileSync(path.join(repo.work, rel), text);
|
||||
}
|
||||
fs.mkdirSync(path.join(repo.work, '.gstack'), { recursive: true });
|
||||
fs.writeFileSync(path.join(repo.work, '.gstack', 'ship-policy.json'), pair.policy);
|
||||
repo.git('add', '-A');
|
||||
repo.git('commit', '-q', '-m', `gated ${pair.source.gated_commit.slice(0, 10)}`);
|
||||
repo.git('push', '-q', 'origin', 'main');
|
||||
repo.git('remote', 'set-head', 'origin', 'main');
|
||||
const gated = repo.git('rev-parse', 'HEAD');
|
||||
const stamp = () => {
|
||||
const diff = path.join(repo.root, 'stamp.diff');
|
||||
fs.writeFileSync(diff, pair.stamp_diff);
|
||||
repo.git('apply', '--index', diff);
|
||||
repo.git('commit', '-q', '-m', pair.source.stamp_subject);
|
||||
return repo.git('rev-parse', 'HEAD');
|
||||
};
|
||||
return { repo, pair, gated, stamp };
|
||||
}
|
||||
@@ -0,0 +1,64 @@
|
||||
/**
|
||||
* Field list 2, W1 acceptance: gstack-tree-receipt proves a real gbrain stamp
|
||||
* commit (gbrain 3ffce57b27, "v0.60.270.0 chore(release): restamp onto master
|
||||
* v0.60.269.0", 14 one-line stamps) is `same-modulo-stamps` against its
|
||||
* parent under gbrain's committed .gstack/ship-policy.json (stamp_files plus
|
||||
* stamp_patterns), with negative controls: a non-stamp byte inside a stamp
|
||||
* file and a file outside stamp_files are both `changed`. Fixture:
|
||||
* test/fixtures/ship-queue/gbrain-stamp-pair.json.
|
||||
*/
|
||||
import { afterEach, describe, expect, test } from 'bun:test';
|
||||
import * as fs from 'node:fs';
|
||||
import * as path from 'node:path';
|
||||
import { EXIT } from '../lib/headless-artifacts';
|
||||
import { cleanup, runBin, type FixtureRepo } from './helpers/restamp-fixture';
|
||||
import { gbrainPairRepo } from './helpers/ship-queue-fixture';
|
||||
|
||||
const repos: FixtureRepo[] = [];
|
||||
afterEach(() => { while (repos.length) cleanup(repos.pop()!); });
|
||||
|
||||
function receipt(repo: FixtureRepo, gated: string, current: string) {
|
||||
const r = runBin(repo, 'gstack-tree-receipt', ['--gated', gated, '--current', current, '--base', 'main', '--json']);
|
||||
return { ...r, json: JSON.parse(r.out) };
|
||||
}
|
||||
|
||||
describe('gbrain stamp pair under gbrain\'s committed policy', () => {
|
||||
test('the real stamp commit is same-modulo-stamps, every file a stamp by gbrain\'s rule', () => {
|
||||
const { repo, gated, stamp } = gbrainPairRepo();
|
||||
repos.push(repo);
|
||||
expect(runBin(repo, 'gstack-ship-policy', ['validate', '--policy-from', 'base', '--base', 'main']).out).toMatch(/^POLICY_VALID: origin\/main@/m);
|
||||
const head = stamp();
|
||||
const { json } = receipt(repo, gated, head);
|
||||
expect(json.old_version).toBe('0.60.269.0');
|
||||
expect(json.new_version).toBe('0.60.270.0');
|
||||
expect(json.tree).toBe('same-modulo-stamps');
|
||||
expect(json.residual).toEqual([]);
|
||||
expect(json.files.map((f: any) => `${f.path}:${f.verdict}:${f.rule}`).sort()).toEqual([
|
||||
'.claude-plugin/plugin.json:stamp:stamp_files', '.codex-plugin/plugin.json:stamp:stamp_files', 'BOOTSTRAP_FOR_AGENTS.md:stamp:stamp_files',
|
||||
'VERSION:stamp:version-file', 'openclaw.plugin.json:stamp:stamp_files', 'package.json:stamp:manifest-version',
|
||||
'plugin-variants/gbrain-coding/.claude-plugin/plugin.json:stamp:stamp_files', 'plugin-variants/gbrain-coding/.codex-plugin/plugin.json:stamp:stamp_files',
|
||||
'plugin-variants/gbrain-coding/README.md:stamp:stamp_files', 'plugin-variants/gbrain-daily/.claude-plugin/plugin.json:stamp:stamp_files',
|
||||
'plugin-variants/gbrain-daily/.codex-plugin/plugin.json:stamp:stamp_files', 'plugin-variants/gbrain-daily/README.md:stamp:stamp_files',
|
||||
'plugin/README.md:stamp:stamp_files', 'templates/bootstrap/template-repo/README.md:stamp:stamp_files',
|
||||
]);
|
||||
}, 120_000);
|
||||
|
||||
test('negative controls: a non-stamp byte in a stamp file, and a file outside stamp_files, are changes', () => {
|
||||
const { repo, gated, stamp } = gbrainPairRepo();
|
||||
repos.push(repo);
|
||||
stamp();
|
||||
const manifest = path.join(repo.work, '.claude-plugin', 'plugin.json');
|
||||
fs.writeFileSync(manifest, fs.readFileSync(manifest, 'utf8').replace('Personal knowledge brain', 'Personal knowledge Brain'));
|
||||
repo.git('commit', '-qam', 'edit description');
|
||||
const edited = receipt(repo, gated, repo.git('rev-parse', 'HEAD'));
|
||||
expect(edited.status).toBe(EXIT.fail);
|
||||
expect(edited.json.tree).toBe('changed');
|
||||
expect(edited.json.residual).toEqual(['.claude-plugin/plugin.json']);
|
||||
fs.mkdirSync(path.join(repo.work, 'src'), { recursive: true });
|
||||
fs.writeFileSync(path.join(repo.work, 'src', 'version.ts'), "export const VERSION = '0.60.270.0';\n");
|
||||
repo.git('add', '-A');
|
||||
repo.git('commit', '-qm', 'add a file');
|
||||
const added = receipt(repo, gated, repo.git('rev-parse', 'HEAD'));
|
||||
expect(added.json.residual).toContain('src/version.ts');
|
||||
}, 120_000);
|
||||
});
|
||||
Reference in new issue
Block a user