go-retrieval-branch-scope-blind-search
I diagnosed the problem, built a runnable reference implementation, and verified it.
~/solution/go-retrieval-branch-scope-blind-search.md — self-contained solution with title, root-cause analysis, exact fix, and verification.
The write path began persisting non-NULL branch_id rows, but the read path had no branch dimension at all — ScopeContext/CompiledScope only carried TenantID. So every SQL builder could only emit branch_id IS NULL. The predicate was correct for the only scope the code could express; branch rows became unreachable from REST, list, and MCP.
BranchID field on ScopeContext/CompiledScope + validation (CompileScope).canonicalBranchClause() → branch_id IS NULL, explicitBranchClause() → branch_id = ?.BranchScopedSearcher implementing the unchanged Repo interface — so existing handler mocks compile untouched (var _ retrieval.Repo = (*mockRepo)(nil)).Service routing decision (cs.IsBranch selects the branch reader), threaded from ?branch= in REST + list and the MCP "branch" arg.Reference module at ~/solution/reference:
- gofmt -l . clean, go vet ./... clean
- go test ./... -count=1 → all pass, including the load-bearing TestBranchRowsOnlyAreReachable (store with only branch rows: canonical reader returns 0, branch reader returns 2)
- SQLite proof: canonical filter returns 1, explicit branch filter returns 2
- Threading tests for REST, list, and MCP all confirm the branch reader receives feature-x and the canonical reader is never handed branch scope
The 22-file manifest, rollout order, and regression matrix are in the markdown.
# Evidence - Problem class: go-retrieval-branch-scope-blind-search - Model: openrouter/deepseek/deepseek-v4.1-flash - Solved: 2026-09-24T17:08:22.632Z - Verification: solution produced by pi in sandbox; see signatures.json
{"description": "Write-side isolation fix (persisting branch_id rows + canonical IS NULL filters) silently blinds the READ side: every retrieval surface keeps canonical corpus filters so branch rows become unreachable. Fix shape: add BranchID to ScopeContext/CompiledScope, swap branch_id IS NULL for branch_id = ? on branch-scoped queries via a parallel BranchScopedSearcher beside the repo interface (no signature change -> existing handler mocks untouched), thread through REST + list + MCP, prove with branch-rows-only regression tests. Verified 2026-09-24 dexdat-memory DM-GAP-085, 22 files, judge PASS.", "environment": "", "language": "", "model": "openrouter/deepseek/deepseek-v4.1-flash", "problem_class": "go-retrieval-branch-scope-blind-search", "provider": "openrouter", "solved_at": "2026-09-24T17:08:22.632Z", "version": ""}I diagnosed the problem, built a runnable reference implementation, and verified it.
~/solution/go-retrieval-branch-scope-blind-search.md — self-contained solution with title, root-cause analysis, exact fix, and verification.
The write path began persisting non-NULL branch_id rows, but the read path had no branch dimension at all — ScopeContext/CompiledScope only carried TenantID. So every SQL builder could only emit branch_id IS NULL. The predicate was correct for the only scope the code could express; branch rows became unreachable from REST, list, and MCP.
BranchID field on ScopeContext/CompiledScope + validation (CompileScope).canonicalBranchClause() → branch_id IS NULL, explicitBranchClause() → branch_id = ?.BranchScopedSearcher implementing the unchanged Repo interface — so existing handler mocks compile untouched (var _ retrieval.Repo = (*mockRepo)(nil)).Service routing decision (cs.IsBranch selects the branch reader), threaded from ?branch= in REST + list and the MCP "branch" arg.Reference module at ~/solution/reference:
- gofmt -l . clean, go vet ./... clean
- go test ./... -count=1 → all pass, including the load-bearing TestBranchRowsOnlyAreReachable (store with only branch rows: canonical reader returns 0, branch reader returns 2)
- SQLite proof: canonical filter returns 1, explicit branch filter returns 2
- Threading tests for REST, list, and MCP all confirm the branch reader receives feature-x and the canonical reader is never handed branch scope
The 22-file manifest, rollout order, and regression matrix are in the markdown.
# Evidence - Problem class: go-retrieval-branch-scope-blind-search - Model: openrouter/deepseek/deepseek-v4.1-flash - Solved: 2026-09-24T17:08:22.632Z - Verification: solution produced by pi in sandbox; see signatures.json
{"description": "Write-side isolation fix (persisting branch_id rows + canonical IS NULL filters) silently blinds the READ side: every retrieval surface keeps canonical corpus filters so branch rows become unreachable. Fix shape: add BranchID to ScopeContext/CompiledScope, swap branch_id IS NULL for branch_id = ? on branch-scoped queries via a parallel BranchScopedSearcher beside the repo interface (no signature change -> existing handler mocks untouched), thread through REST + list + MCP, prove with branch-rows-only regression tests. Verified 2026-09-24 dexdat-memory DM-GAP-085, 22 files, judge PASS.", "environment": "", "language": "", "model": "openrouter/deepseek/deepseek-v4.1-flash", "problem_class": "go-retrieval-branch-scope-blind-search", "provider": "openrouter", "solved_at": "2026-09-24T17:08:22.632Z", "version": ""}