TL;DR: gstack-memory-ingest --bulk fails on every page with Unknown command: put_page. gstack 1.26.0.0 invokes gbrain put_page (the internal operation name); gbrain v0.18.2 only registers the user-facing alias gbrain put from cliHints.name.
Repro
Fresh install on Linux:
- gstack v1.26.0.0 (commit
bf65487 on garrytan/gstack:main)
- gbrain v0.18.2 (commit
08b3698 on garrytan/gbrain:main)
- PGLite engine, 75 transcripts on disk
$ bun ~/.claude/skills/gstack/bin/gstack-memory-ingest.ts --probe
Total files in window: 75
New (never ingested): 75
Estimate: ~1 min for full --bulk pass.
$ bun ~/.claude/skills/gstack/bin/gstack-memory-ingest.ts --bulk
[put-error] transcripts/codex/.../2026-05-02-019de99d-8ea: Command failed:
gbrain put_page --slug ... --title ... --type transcript --tags transcript,...
Unknown command: put_page
Run gbrain --help for available commands.
... (75 failures, 0 written) ...
Ingest pass complete (bulk):
written: 0
failed: 75
Root cause
bin/gstack-memory-ingest.ts:762-784 builds the args:
const args = [
"put_page",
"--slug", page.slug,
"--title", page.title,
"--type", page.type,
"--tags", page.tags.join(","),
];
execFileSync("gbrain", args, { input: page.body, ... });
But gbrain v0.18.2 src/cli.ts:13-18 only registers user-facing CLI commands from cliHints.name:
for (const op of operations) {
const name = op.cliHints?.name;
if (name && !op.cliHints?.hidden) {
cliOps.set(name, op);
}
}
In src/core/operations.ts:243-244, the operation is name: 'put_page' with cliHints: { name: 'put', positional: ['slug'] }. So gbrain put is registered; gbrain put_page is not.
Same mismatch likely affects bin/gstack-brain-context-load.ts (uses gbrain list_pages per the file's own comment at line 10 — gbrain CLI exposes gbrain list).
Suggested fix
Either:
- gstack side (faster): swap
put_page → put and list_pages → list, adjust args to match the user-facing CLI shape (gbrain put <slug> reads body from stdin, supports --title/--type/--tags via flags).
- gbrain side: register operation
name as a CLI alias alongside cliHints.name so internal names also work as commands. Bigger surface change.
Workaround
gstack-config set transcript_ingest_mode off so preambles stop retrying. The rest of /setup-gbrain (engine init, code import, MCP register, brain-sync wireup, smoke test) works fine — just the V1 transcript/memory ingest pipeline is dead until either side ships the alias.
🤖 Filed by Claude Code via gstack /setup-gbrain on Linux
TL;DR:
gstack-memory-ingest --bulkfails on every page withUnknown command: put_page. gstack 1.26.0.0 invokesgbrain put_page(the internal operation name); gbrain v0.18.2 only registers the user-facing aliasgbrain putfromcliHints.name.Repro
Fresh install on Linux:
bf65487on garrytan/gstack:main)08b3698on garrytan/gbrain:main)Root cause
bin/gstack-memory-ingest.ts:762-784builds the args:But gbrain v0.18.2
src/cli.ts:13-18only registers user-facing CLI commands fromcliHints.name:In
src/core/operations.ts:243-244, the operation isname: 'put_page'withcliHints: { name: 'put', positional: ['slug'] }. Sogbrain putis registered;gbrain put_pageis not.Same mismatch likely affects
bin/gstack-brain-context-load.ts(usesgbrain list_pagesper the file's own comment at line 10 — gbrain CLI exposesgbrain list).Suggested fix
Either:
put_page→putandlist_pages→list, adjust args to match the user-facing CLI shape (gbrain put <slug>reads body from stdin, supports--title/--type/--tagsvia flags).nameas a CLI alias alongsidecliHints.nameso internal names also work as commands. Bigger surface change.Workaround
gstack-config set transcript_ingest_mode offso preambles stop retrying. The rest of/setup-gbrain(engine init, code import, MCP register, brain-sync wireup, smoke test) works fine — just the V1 transcript/memory ingest pipeline is dead until either side ships the alias.🤖 Filed by Claude Code via gstack /setup-gbrain on Linux