You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
gbrain context-load: list-query filter: blocks in SKILL.md manifests are silently dropped, causing unfiltered cross-repo queries at skill startup #1687
parseSkillManifest (the runtime read path in lib/gstack-memory-helpers.ts) parses every field of a gbrain.context_queries item exceptfilter:. As a result, any kind: list query that declares a filter: block in its SKILL.md manifest runs unfiltered at skill startup, pulling pages of every type from every repo into the agent's context instead of the repo scoped set the manifest asked for.
This silently defeats the F7 design intent documented in bin/gstack-brain-context-load.ts (lines 18-20): "every default query carries an explicit repo: filter so cross-repo contamination is the non-default path."
Affected skills
Four shipped skills declare a filter: block on a kind: list query in their generated SKILL.md (the file the runtime actually reads):
So the query that ships is gbrain list_pages --limit 5 --sort updated_at_desc with no filter, returning the 5 most recently updated pages of any type from any repo, then wrapping and injecting them into the agent's startup context.
Root cause
extractGbrainBlock in lib/gstack-memory-helpers.ts (around lines 388-410) matches id, kind, render_as, query, limit, glob, sort, and tail, but never filter. The GbrainManifestQuery.filter field exists in the type, defaultManifest populates it, and dispatchList consumes it. Only the manifest parser fails to read it, so a declared filter is dropped on the floor.
This is worse than a skip: the query still "succeeds", so no (unavailable) is rendered. Wrong, cross-repo data is injected with no signal that anything went wrong.
Expected behavior
parseSkillManifest should return q.filter populated from the filter: sub-block, so dispatchList emits the declared --filter k=v args and the query stays repo scoped, matching the behavior of the built in defaultManifest queries.
The fixtures in test/gstack-memory-helpers.test.ts ("parses a multi-kind manifest", "ignores incomplete query items") contain no filter: block, so filter parsing is entirely uncovered by tests today.
Confirmed on 920a13a1. parseSkillManifest in lib/gstack-memory-helpers.ts reads every gbrain.context_queries field exceptfilter:, causing all kind: list queries with filter declarations to run unfiltered at skill startup. Silent cross-repo contamination with no (unavailable) signal.
Reproduction (Copy-Paste)
# On main branch (920a13a1)
bun -e 'import { parseSkillManifest } from "./lib/gstack-memory-helpers.ts";const m = parseSkillManifest("investigate/SKILL.md");const q = m.context_queries.find(q => q.id === "prior-investigations");console.log("Declared in SKILL.md:");console.log(" filter: { type: timeline, tags_contains: repo:{repo_slug}, ... }");console.log("\nParsed by runtime:");console.log(" filter:", q.filter); // → undefined'
dispatchList in bin/gstack-brain-context-load.tsonly adds --filter args when q.filter is truthy:
if(q.filter){// ← always false when parseSkillManifest drops itfor(const[k,v]ofObject.entries(q.filter)){const{resolved: rv}=substituteTemplateVars(String(v),args);cliArgs.push("--filter",`${k}=${rv}`);}}
Result: gbrain list_pages --limit 5 --sort updated_at_desc (no --filter repo=X) → pulls from all repos, wraps results in "## Prior investigations in this repo", injects into agent context. Agent believes it's looking at repo-scoped history when it's actually seeing random cross-repo pages.
Affected Skills (Production Impact)
4 shipped skills declare filter: on kind: list queries:
investigate/SKILL.md (prior-investigations)
office-hours/SKILL.md
plan-ceo-review/SKILL.md
design-consultation/SKILL.md
All silently pull unfiltered data today.
Fix Path
extractGbrainBlock (lines 388-410) needs one addition:
Memory context leakage is a memory sovereignty violation — the skill manifest is the contract, runtime must honor declared filters or fail loudly. Built with SwarmAI. Discussion: T-MEM
@16francej Please close this issue as resolved. The GBrain context loader now reads nested filter settings from skill manifests and applies them to the query, preventing the unfiltered cross-repository search reported here. This shipped in #2264.
parseSkillManifest("investigate/SKILL.md") now returns the nested filter ({"type":"timeline","tags_contains":"repo:{repo_slug}","content_contains":"investigate"}) instead of undefined, so list queries stay repo-scoped.
Fixed by #2264 (on main since v1.60.1.0).
If you still see this on the latest gstack, please reopen with details.
Activity
fix(gbrain): parse nested filter: blocks in SKILL.md context_queries
xg-gh-25 commentedon May 25, 2026
The Bug Is Real (Reproduction + Fix Path)
Confirmed on
920a13a1.parseSkillManifestinlib/gstack-memory-helpers.tsreads everygbrain.context_queriesfield exceptfilter:, causing allkind: listqueries with filter declarations to run unfiltered at skill startup. Silent cross-repo contamination with no(unavailable)signal.Reproduction (Copy-Paste)
Expected:
filter: { type: "timeline", tags_contains: "repo:{repo_slug}", ... }Actual:
filter: undefinedWhy This Is Worse Than A Skip
dispatchListinbin/gstack-brain-context-load.tsonly adds--filterargs whenq.filteris truthy:Result:
gbrain list_pages --limit 5 --sort updated_at_desc(no--filter repo=X) → pulls from all repos, wraps results in "## Prior investigations in this repo", injects into agent context. Agent believes it's looking at repo-scoped history when it's actually seeing random cross-repo pages.Affected Skills (Production Impact)
4 shipped skills declare
filter:onkind: listqueries:investigate/SKILL.md(prior-investigations)office-hours/SKILL.mdplan-ceo-review/SKILL.mddesign-consultation/SKILL.mdAll silently pull unfiltered data today.
Fix Path
extractGbrainBlock(lines 388-410) needs one addition:Then the filter actually flows:
filter:→ parseSkillManifest reads it → dispatchList emits--filterargs → gbrain query stays repo-scopedMemory context leakage is a memory sovereignty violation — the skill manifest is the contract, runtime must honor declared filters or fail loudly. Built with SwarmAI. Discussion: T-MEM
fix(gbrain): parse nested filter: blocks in SKILL.md context_queries
time-attack commentedon Jul 15, 2026
@16francej Please close this issue as resolved. The GBrain context loader now reads nested filter settings from skill manifests and applies them to the query, preventing the unfiltered cross-repository search reported here. This shipped in #2264.
v1.65.0.0 feat: fork port wave 2 — feature fixes, session persistence…
capy-ai commentedon Oct 3, 2026
parseSkillManifest("investigate/SKILL.md")now returns the nested filter ({"type":"timeline","tags_contains":"repo:{repo_slug}","content_contains":"investigate"}) instead ofundefined, so list queries stay repo-scoped.Fixed by #2264 (on main since v1.60.1.0).
If you still see this on the latest gstack, please reopen with details.