From a4a9c70c65cb1edf7a5bf7a4d73ea862e24f5d43 Mon Sep 17 00:00:00 2001 From: Mikael Hugo Date: Sat, 2 May 2026 02:44:45 +0200 Subject: [PATCH] chore(sf): residual edits in auto-post-unit + auto-prompts Co-Authored-By: Claude Opus 4.7 (1M context) --- src/resources/extensions/sf/auto-post-unit.ts | 32 +++++++++++++++++++ src/resources/extensions/sf/auto-prompts.ts | 13 ++++++++ 2 files changed, 45 insertions(+) diff --git a/src/resources/extensions/sf/auto-post-unit.ts b/src/resources/extensions/sf/auto-post-unit.ts index bbdb9a6dd..c429ef0f6 100644 --- a/src/resources/extensions/sf/auto-post-unit.ts +++ b/src/resources/extensions/sf/auto-post-unit.ts @@ -1540,6 +1540,38 @@ export async function postUnitPostVerification( } } + // ── Knowledge compounding (Mechanism 4) ── + // After milestone completion, distill high-confidence judgment-log entries + // into .sf/KNOWLEDGE.md so the next milestone benefits from them. + // Failure is always non-fatal. + if (s.currentUnit?.type === "complete-milestone") { + const milestoneIdForCompound = parseUnitId(s.currentUnit.id).milestone; + if (milestoneIdForCompound) { + try { + const { compoundLearningsIntoKnowledge } = await import( + "./knowledge-compounding.js" + ); + const result = compoundLearningsIntoKnowledge( + s.basePath, + milestoneIdForCompound, + ); + if (result.added > 0) { + debugLog("postUnit", { + phase: "knowledge-compounding", + milestoneId: milestoneIdForCompound, + added: result.added, + skipped: result.skipped, + }); + } + } catch (err) { + debugLog("postUnit", { + phase: "knowledge-compounding", + error: (err as Error).message, + }); + } + } + } + // ── Post-unit hooks ── if (s.currentUnit && !s.stepMode) { const hookUnit = checkPostUnitHooks( diff --git a/src/resources/extensions/sf/auto-prompts.ts b/src/resources/extensions/sf/auto-prompts.ts index 21802042c..b27aae8a4 100644 --- a/src/resources/extensions/sf/auto-prompts.ts +++ b/src/resources/extensions/sf/auto-prompts.ts @@ -1757,6 +1757,19 @@ export async function buildPlanMilestonePrompt( `## Inlined Context (preloaded — do not re-read these files)\n\n${inlined.join("\n\n---\n\n")}`, ); + // Milestone framing check — surfaces anti-goal violations and vision-alignment + // concerns in the planning context. Non-blocking: the agent reads and decides. + let framingBlock = ""; + try { + const { checkMilestoneFraming, formatFramingFindings } = await import( + "./milestone-framing-check.js" + ); + const framingFindings = checkMilestoneFraming(base, mid); + framingBlock = formatFramingFindings(mid, framingFindings); + } catch { + // Non-fatal — framing check must never break milestone planning + } + const outputRelPath = relMilestoneFile(base, mid, "ROADMAP"); const researchOutputPath = join( base,