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
On a Supabase/Postgres + Windows setup, gstack-memory-ingest reports success but imports 0 transcript pages. Root cause is an interaction with gbrain v0.42's git-aware import.
Mechanism
makeStagingDir() stages prepared pages under $GSTACK_HOME (~/.gstack), which is itself a git work tree with .gitignore = * (the gstack-artifacts repo).
gbrain v0.42 import <dir> enumerates files via collectSyncableFiles → gitListSyncableFiles, which runs git ls-files --cached --others --exclude-standard. Inside a .gitignore = * tree this returns zero files.
gbrain prints Found 0 markdown files, imports 0, exits 0, emits valid {"imported":0,...} JSON.
gstack-memory-ingest sees exit 0 + parseable JSON → treats it as success → advances .transcript-ingest-state.json, marking every session ingested. Net: 0 transcript pages ever reach the brain, silently.
This issue is another example of memory-ingest needing a hard output contract.
The failure mode is:
stage pages inside GSTACK_HOME
-> GSTACK_HOME is gitignore=*
-> git-aware import sees 0 files
-> import returns success
-> ingest state advances
That should be impossible.
A standard AISP-style ingest contract could require staged-count and imported-count validation:
[
{
"role": "system",
"content": {
"protocol": "AISP V1.0.0",
"axiom_0": "Human_Sovereignty_and_Wellbeing",
"id": "gstack_memory_ingest_commit_contract_aisp",
"name": "gstack Memory Ingest Commit Contract",
"version": "1.0.0",
"license": "MIT",
"summary": "Machine-checkable contract preventing silent false-success during gbrain memory ingest.",
"flow_format": "mermaid",
"loading_mode": "node",
"tools": ["filesystem", "shell"],
"params": {
"staging_dir": "string",
"gbrain_repo": "string"
},
"system_prompt": ""
}
},
{
"role": "user",
"content": {
"instruction": "STRICTLY OBEY aisp_contract; its non_negotiable rules are inviolable; then RUN aisop.main",
"user_input": "{user_input}",
"aisp_contract": {
"profile": "aisp.skill.v1",
"invocation": {
"mode": "ingest_commit_validation",
"when_to_use": [
"before committing memory-ingest state",
"after staging prepared memory pages",
"after gbrain git-aware import returns"
],
"when_not_to_use": [
"dry-run preview with no state update",
"manual import where user explicitly accepts zero files"
]
},
"non_negotiable": [
{
"rule": "A non-empty staging set must not produce imported=0 with success.",
"enforced_by": "validate_import.step2:sys.assert"
},
{
"rule": "Ingest state must not advance if staged pages were invisible to git-aware import.",
"enforced_by": "commit.step2:sys.assert"
},
{
"rule": "Staging directory must be inside a location visible to the import mechanism or use an import path that bypasses gitignore filtering intentionally.",
"enforced_by": "stage.step2:sys.assert"
}
],
"discovery": {
"category": "memory_ingest",
"tags": ["gstack", "memory-ingest", "gbrain", "gitignore", "silent-success", "aisp"]
},
"risk_level": "high",
"resources": [
{
"id": "staging_dir",
"path": "{staging_dir}",
"kind": "artifact_dir",
"mode": "read_only",
"when": "Read before import validation.",
"scope": "skill"
}
]
},
"aisop": {
"main": "graph TD\n stage[Validate staging location] --> count[Count staged pages] --> import[Run gbrain import] --> validate_import[Validate import counts] --> commit[Commit ingest state] --> end_node((End))"
},
"functions": {
"stage": {
"step1": "Check whether staging_dir is visible to gbrain git-aware import.",
"step2": "sys.assert('staging_dir visible or intentionally bypasses gitignore filtering', 'Staging directory is hidden from import mechanism')",
"output_mapping": "staging_visibility"
},
"count": {
"step1": "Count prepared pages in staging_dir.",
"output_mapping": "staged_count"
},
"import": {
"step1": "Run gbrain import and collect imported, skipped, and errors counts.",
"output_mapping": "import_result"
},
"validate_import": {
"step1": "Compare staged_count with imported/skipped/errors.",
"step2": "sys.assert('not staged_count > 0 with imported=0 and success', 'Silent false-success: staged pages were not imported')",
"output_mapping": "import_validation"
},
"commit": {
"step1": "Advance ingest state only if import_validation passes.",
"step2": "sys.assert('ingest state not advanced on failed or empty import', 'Do not advance state after false-success')",
"output_mapping": "commit_status"
},
"end_node": {
"step1": "Return import_validation and commit_status."
}
}
}
}
]
The practical fix:
1. Stage prepared pages outside ignored GSTACK_HOME, or explicitly import them by path.
2. Check staged_count.
3. Treat staged_count > 0 and imported=0 as failure unless all files are explicitly skipped with reasons.
4. Do not advance ingest state on false-success.
The invariant:
success must mean something was imported, skipped with reason, or errored visibly.
gstack-memory-ingest now runs gbrain import with --include-gitignored and a GIT_CEILING_DIRECTORIES scoped to the staging dir, and it refuses to advance ingest state when gbrain accounts for fewer pages than were staged (bin/gstack-memory-ingest.ts, the accounted-landings check), so a 0-of-N import now fails loudly instead of being recorded as success.
Fixed in v1.65.0.0 (#2577).
If you still see this on the latest gstack, please reopen with details.
Activity
optimization2026 commentedon Jun 30, 2026
This issue is another example of memory-ingest needing a hard output contract.
The failure mode is:
That should be impossible.
A standard AISP-style ingest contract could require staged-count and imported-count validation:
[ { "role": "system", "content": { "protocol": "AISP V1.0.0", "axiom_0": "Human_Sovereignty_and_Wellbeing", "id": "gstack_memory_ingest_commit_contract_aisp", "name": "gstack Memory Ingest Commit Contract", "version": "1.0.0", "license": "MIT", "summary": "Machine-checkable contract preventing silent false-success during gbrain memory ingest.", "flow_format": "mermaid", "loading_mode": "node", "tools": ["filesystem", "shell"], "params": { "staging_dir": "string", "gbrain_repo": "string" }, "system_prompt": "" } }, { "role": "user", "content": { "instruction": "STRICTLY OBEY aisp_contract; its non_negotiable rules are inviolable; then RUN aisop.main", "user_input": "{user_input}", "aisp_contract": { "profile": "aisp.skill.v1", "invocation": { "mode": "ingest_commit_validation", "when_to_use": [ "before committing memory-ingest state", "after staging prepared memory pages", "after gbrain git-aware import returns" ], "when_not_to_use": [ "dry-run preview with no state update", "manual import where user explicitly accepts zero files" ] }, "non_negotiable": [ { "rule": "A non-empty staging set must not produce imported=0 with success.", "enforced_by": "validate_import.step2:sys.assert" }, { "rule": "Ingest state must not advance if staged pages were invisible to git-aware import.", "enforced_by": "commit.step2:sys.assert" }, { "rule": "Staging directory must be inside a location visible to the import mechanism or use an import path that bypasses gitignore filtering intentionally.", "enforced_by": "stage.step2:sys.assert" } ], "discovery": { "category": "memory_ingest", "tags": ["gstack", "memory-ingest", "gbrain", "gitignore", "silent-success", "aisp"] }, "risk_level": "high", "resources": [ { "id": "staging_dir", "path": "{staging_dir}", "kind": "artifact_dir", "mode": "read_only", "when": "Read before import validation.", "scope": "skill" } ] }, "aisop": { "main": "graph TD\n stage[Validate staging location] --> count[Count staged pages] --> import[Run gbrain import] --> validate_import[Validate import counts] --> commit[Commit ingest state] --> end_node((End))" }, "functions": { "stage": { "step1": "Check whether staging_dir is visible to gbrain git-aware import.", "step2": "sys.assert('staging_dir visible or intentionally bypasses gitignore filtering', 'Staging directory is hidden from import mechanism')", "output_mapping": "staging_visibility" }, "count": { "step1": "Count prepared pages in staging_dir.", "output_mapping": "staged_count" }, "import": { "step1": "Run gbrain import and collect imported, skipped, and errors counts.", "output_mapping": "import_result" }, "validate_import": { "step1": "Compare staged_count with imported/skipped/errors.", "step2": "sys.assert('not staged_count > 0 with imported=0 and success', 'Silent false-success: staged pages were not imported')", "output_mapping": "import_validation" }, "commit": { "step1": "Advance ingest state only if import_validation passes.", "step2": "sys.assert('ingest state not advanced on failed or empty import', 'Do not advance state after false-success')", "output_mapping": "commit_status" }, "end_node": { "step1": "Return import_validation and commit_status." } } } } ]The practical fix:
The invariant:
v1.64.0.0 fix wave: full tracker audit — 90 fixes, 52 issues closed, …
v1.67.0.0 fix: the tracker wave — XProtect self-heal, complete instal…
capy-ai commentedon Oct 3, 2026
gstack-memory-ingestnow runsgbrain importwith--include-gitignoredand aGIT_CEILING_DIRECTORIESscoped to the staging dir, and it refuses to advance ingest state when gbrain accounts for fewer pages than were staged (bin/gstack-memory-ingest.ts, the accounted-landings check), so a 0-of-N import now fails loudly instead of being recorded as success.Fixed in v1.65.0.0 (#2577).
If you still see this on the latest gstack, please reopen with details.