From 2accb47e4dd57f1fb788e0635f79f34cf7604d9e Mon Sep 17 00:00:00 2001 From: Neo <54811660+neooriginal@users.noreply.github.com> Date: Fri, 23 Jan 2026 06:00:13 +0100 Subject: [PATCH] fix: follow soul.md more closely (#1434) * Agents: honor SOUL.md persona guidance * fix: harden SOUL.md detection (#1434) (thanks @neooriginal) --------- Co-authored-by: Peter Steinberger --- CHANGELOG.md | 1 + src/agents/system-prompt.test.ts | 14 ++++++++++++++ src/agents/system-prompt.ts | 18 ++++++++++++------ 3 files changed, 27 insertions(+), 6 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 08427aa9f..113d75119 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -33,6 +33,7 @@ Docs: https://docs.clawd.bot - Agents: make OpenAI sessions image-sanitize-only; gate tool-id/repair sanitization by provider. - Doctor: honor CLAWDBOT_GATEWAY_TOKEN for auth checks and security audit token reuse. (#1448) Thanks @azade-c. - Agents: make tool summaries more readable and only show optional params when set. +- Agents: honor SOUL.md guidance even when the file is nested or path-qualified. (#1434) Thanks @neooriginal. - CLI: prefer `~` for home paths in output. - Mattermost (plugin): enforce pairing/allowlist gating, keep @username targets, and clarify plugin-only docs. (#1428) Thanks @damoahdominic. - Agents: centralize transcript sanitization in the runner; keep tags and error turns intact. diff --git a/src/agents/system-prompt.test.ts b/src/agents/system-prompt.test.ts index e37a17008..d1b58c6ab 100644 --- a/src/agents/system-prompt.test.ts +++ b/src/agents/system-prompt.test.ts @@ -237,6 +237,20 @@ describe("buildAgentSystemPrompt", () => { expect(prompt).toContain("Bravo"); }); + it("adds SOUL guidance when a soul file is present", () => { + const prompt = buildAgentSystemPrompt({ + workspaceDir: "/tmp/clawd", + contextFiles: [ + { path: "./SOUL.md", content: "Persona" }, + { path: "dir\\SOUL.md", content: "Persona Windows" }, + ], + }); + + expect(prompt).toContain( + "If SOUL.md is present, embody its persona and tone. Avoid stiff, generic replies; follow its guidance unless higher-priority instructions override it.", + ); + }); + it("summarizes the message tool when available", () => { const prompt = buildAgentSystemPrompt({ workspaceDir: "/tmp/clawd", diff --git a/src/agents/system-prompt.ts b/src/agents/system-prompt.ts index aa13a2748..c2f972f78 100644 --- a/src/agents/system-prompt.ts +++ b/src/agents/system-prompt.ts @@ -517,12 +517,18 @@ export function buildAgentSystemPrompt(params: { const contextFiles = params.contextFiles ?? []; if (contextFiles.length > 0) { - lines.push( - "# Project Context", - "", - "The following project context files have been loaded:", - "", - ); + const hasSoulFile = contextFiles.some((file) => { + const normalizedPath = file.path.trim().replace(/\\/g, "/"); + const baseName = normalizedPath.split("/").pop() ?? normalizedPath; + return baseName.toLowerCase() === "soul.md"; + }); + lines.push("# Project Context", "", "The following project context files have been loaded:"); + if (hasSoulFile) { + lines.push( + "If SOUL.md is present, embody its persona and tone. Avoid stiff, generic replies; follow its guidance unless higher-priority instructions override it.", + ); + } + lines.push(""); for (const file of contextFiles) { lines.push(`## ${file.path}`, "", file.content, ""); }