Context
Operator-flagged this session (2026-06-06): the Sandman strategic-priming handoff (resources/content/sandman_handoff.md, generated by GoldenPathSynthesizer and parsed by ai/agent/AgentOrchestrator.mjs into every headless agent's context) has bloated into a token drain. Two compounding issues: oversized per-section render limits and full GitHub-URL hyperlinks on every issue/PR row.
Live latest-open sweep: checked latest 20 open issues 2026-06-06; no equivalent found (#10275 is the closed Silent-Threads feature itself; #10120 is a different Golden-Path concern).
The Problem
The handoff is always-injected priming content — every row costs every primed agent tokens that compete with reasoning budget. Current state:
- Section limits too high vs the 5-row convention:
goldenPathStaleAssignmentRenderLimit = 20, goldenPathSilentThreadRenderLimit = 10. Shipped oversized via the Silent-Threads (#12603) + Stale-Assignments (#12125) sections. (Note: slice(0, undefined) returns the entire array, so a stale local config.mjs lacking these leaves renders genuinely unbounded — the worst case for a budget control.)
- Full URL hyperlinks:
[#N](https://github.com/neomjs/neo/issues/N) per issue row + [title](url) per PR row — ~73 full URLs in a representative handoff. The bare #N is sufficient (agents resolve repo context); the URL is pure token waste.
- Golden Path itself under-rendered: the main priority list is hardcoded to 5; it is the one section that warrants more depth (top 10).
The Architectural Reality
- Render limits are AiConfig leaves in
ai/mcp/server/memory-core/config.template.mjs (goldenPathStaleAssignmentRenderLimit ~L227, goldenPathSilentThreadRenderLimit ~L244, goldenPathRecentOpenPrRenderLimit ~L249 already 5).
ai/services/graph/GoldenPathSynthesizer.mjs: issueRef ternaries (~L399, ~L644) emit the URL form; PR rows (~L697, ~L1174) use [title](url); the Golden-Path main list hardcodes .slice(0, 5) (~L879).
- Consumer:
AgentOrchestrator.mjs parses the handoff into a headless agent loop → fewer/shorter rows = direct per-agent token savings.
The Fix
config.template.mjs (memory-core): goldenPathStaleAssignmentRenderLimit 20 → 5; goldenPathSilentThreadRenderLimit 10 → 5; add goldenPathTopNodeRenderLimit = 10 (env NEO_GOLDEN_PATH_TOP_NODE_RENDER_LIMIT).
GoldenPathSynthesizer.mjs: Golden-Path main .slice(0, 5) → .slice(0, aiConfig.goldenPathTopNodeRenderLimit); issueRef → bare `#${candidate.number}` (both sites); PR rows → drop the (url) hyperlink, keep PR #N + title.
- No defensive
?? <n> on the leaf reads — the SSOT leaf is authoritative.
Contract Ledger Matrix
| Target Surface |
Source of Authority |
Proposed Behavior |
Fallback / Edge Case |
Evidence |
goldenPathStaleAssignmentRenderLimit |
this ticket / operator |
default 20 → 5 |
env override unchanged |
GoldenPathSynthesizer spec |
goldenPathSilentThreadRenderLimit |
this ticket / operator |
default 10 → 5 |
env override unchanged |
spec |
goldenPathTopNodeRenderLimit (NEW) |
this ticket / operator |
default 10; Golden-Path main cap |
env NEO_GOLDEN_PATH_TOP_NODE_RENDER_LIMIT |
spec |
GoldenPathSynthesizer issue/PR row format |
this ticket / operator |
bare #N / PR #N (no hyperlink) |
n/a |
rendered-handoff diff |
Decision Record impact
aligned-with ADR 0019 (AiConfig reactive Provider SSOT — read resolved leaves at use site, no defensive re-reads).
Acceptance Criteria
Out of Scope
- The #12612 idle-out wake-digest cycle-state enrichment (separate lane — same golden-path/graph content, but the daemon digest path, not the handoff render).
- The Silent-Threads / Stale-Assignments selection logic (thresholds, scoring) — render caps + format only.
- The operator's local
config.mjs overlay (gitignored; updated out-of-band).
Avoided Traps
- Don't add a
?? 5 defensive fallback on the leaf read — that's the B3 AiConfig-defense antipattern removed in #12461. A missing leaf is a config-regen problem, not a render-time guard.
- Don't hardcode the Golden-Path cap — make it a leaf, consistent with its 3 sibling render-limit leaves.
- Don't strip issue/PR titles — the token waste is the URL, not the human-readable title.
Related
- #12603 (silent threads, limit 10) + #12125 (stale assignments, limit 20) — introduced the oversized sections.
- #12612 — sibling idle-out wake-digest re-scope (separate lane).
Origin Session ID: 4c567b8a-c0ac-447a-901b-5369ed4449d5
Handoff Retrieval Hint: "golden path sandman handoff render limit caps bare issue refs token bloat"
Context
Operator-flagged this session (2026-06-06): the Sandman strategic-priming handoff (
resources/content/sandman_handoff.md, generated byGoldenPathSynthesizerand parsed byai/agent/AgentOrchestrator.mjsinto every headless agent's context) has bloated into a token drain. Two compounding issues: oversized per-section render limits and full GitHub-URL hyperlinks on every issue/PR row.Live latest-open sweep: checked latest 20 open issues 2026-06-06; no equivalent found (#10275 is the closed Silent-Threads feature itself; #10120 is a different Golden-Path concern).
The Problem
The handoff is always-injected priming content — every row costs every primed agent tokens that compete with reasoning budget. Current state:
goldenPathStaleAssignmentRenderLimit= 20,goldenPathSilentThreadRenderLimit= 10. Shipped oversized via the Silent-Threads (#12603) + Stale-Assignments (#12125) sections. (Note:slice(0, undefined)returns the entire array, so a stale localconfig.mjslacking these leaves renders genuinely unbounded — the worst case for a budget control.)[#N](https://github.com/neomjs/neo/issues/N)per issue row +[title](url)per PR row — ~73 full URLs in a representative handoff. The bare#Nis sufficient (agents resolve repo context); the URL is pure token waste.The Architectural Reality
ai/mcp/server/memory-core/config.template.mjs(goldenPathStaleAssignmentRenderLimit~L227,goldenPathSilentThreadRenderLimit~L244,goldenPathRecentOpenPrRenderLimit~L249 already 5).ai/services/graph/GoldenPathSynthesizer.mjs:issueRefternaries (~L399, ~L644) emit the URL form; PR rows (~L697, ~L1174) use[title](url); the Golden-Path main list hardcodes.slice(0, 5)(~L879).AgentOrchestrator.mjsparses the handoff into a headless agent loop → fewer/shorter rows = direct per-agent token savings.The Fix
config.template.mjs(memory-core):goldenPathStaleAssignmentRenderLimit20 → 5;goldenPathSilentThreadRenderLimit10 → 5; addgoldenPathTopNodeRenderLimit= 10 (envNEO_GOLDEN_PATH_TOP_NODE_RENDER_LIMIT).GoldenPathSynthesizer.mjs: Golden-Path main.slice(0, 5)→.slice(0, aiConfig.goldenPathTopNodeRenderLimit);issueRef→ bare`#${candidate.number}`(both sites); PR rows → drop the(url)hyperlink, keepPR #N+ title.?? <n>on the leaf reads — the SSOT leaf is authoritative.Contract Ledger Matrix
goldenPathStaleAssignmentRenderLimitgoldenPathSilentThreadRenderLimitgoldenPathTopNodeRenderLimit(NEW)NEO_GOLDEN_PATH_TOP_NODE_RENDER_LIMITGoldenPathSynthesizerissue/PR row format#N/PR #N(no hyperlink)Decision Record impact
aligned-with ADR 0019(AiConfig reactive Provider SSOT — read resolved leaves at use site, no defensive re-reads).Acceptance Criteria
goldenPathStaleAssignmentRenderLimitdefault = 5;goldenPathSilentThreadRenderLimitdefault = 5.goldenPathTopNodeRenderLimitleaf added (default 10); Golden-Path main renders up to 10.#N(no[#N](url)); all PR rows drop the URL hyperlink (title kept).?? <n>fallback added on the leaf reads.https://github.com/URLs.Out of Scope
config.mjsoverlay (gitignored; updated out-of-band).Avoided Traps
?? 5defensive fallback on the leaf read — that's the B3 AiConfig-defense antipattern removed in #12461. A missing leaf is a config-regen problem, not a render-time guard.Related
Origin Session ID: 4c567b8a-c0ac-447a-901b-5369ed4449d5
Handoff Retrieval Hint: "golden path sandman handoff render limit caps bare issue refs token bloat"