Clarify MEMORY guidance over generic TTS hints (#81930) · openclaw/openclaw@6821fbc
giodl73-repo
·
2026-05-17
·
via Recent Commits to openclaw:main
File tree
extensions/speech-core/src
| Original file line number | Diff line number | Diff line change |
|---|
@@ -108,6 +108,7 @@ vi.mock("../api.js", async () => {
|
108 | 108 | |
109 | 109 | const { |
110 | 110 | _test, |
| 111 | + buildTtsSystemPromptHint, |
111 | 112 | getTtsPersona, |
112 | 113 | getTtsProvider, |
113 | 114 | maybeApplyTtsToPayload, |
@@ -238,6 +239,18 @@ describe("speech-core native voice-note routing", () => {
|
238 | 239 | expect(_test.supportsNativeVoiceNoteTts(undefined)).toBe(false); |
239 | 240 | }); |
240 | 241 | |
| 242 | +it("tells generic TTS guidance to defer to MEMORY voice-delivery instructions", () => { |
| 243 | +const hint = buildTtsSystemPromptHint(createTtsConfig("openclaw-speech-core-tts-hint-test")); |
| 244 | + |
| 245 | +expect(hint).toContain("Voice (TTS) is enabled."); |
| 246 | +expect(hint).toContain( |
| 247 | +"If workspace context (especially MEMORY.md) tells you not to use [[tts:...]] or to use a local/non-tagged voice workflow, follow that workspace instruction instead.", |
| 248 | +); |
| 249 | +expect(hint).toContain( |
| 250 | +"Use [[tts:...]] and optional [[tts:text]]...[[/tts:text]] to control voice/expressiveness.", |
| 251 | +); |
| 252 | +}); |
| 253 | + |
241 | 254 | it("marks Discord auto TTS replies as native voice messages", async () => { |
242 | 255 | await expectTtsPayloadResult({ |
243 | 256 | channel: "discord", |
|
| Original file line number | Diff line number | Diff line change |
|---|
@@ -557,6 +557,7 @@ export function buildTtsSystemPromptHint(
|
557 | 557 | ? `Active TTS persona: ${persona.label ?? persona.id}${persona.description ? ` - ${persona.description}` : ""}.` |
558 | 558 | : undefined, |
559 | 559 | `Keep spoken text ≤${maxLength} chars to avoid auto-summary (summary ${summarize}).`, |
| 560 | +"If workspace context (especially MEMORY.md) tells you not to use [[tts:...]] or to use a local/non-tagged voice workflow, follow that workspace instruction instead.", |
560 | 561 | "Use [[tts:...]] and optional [[tts:text]]...[[/tts:text]] to control voice/expressiveness.", |
561 | 562 | ] |
562 | 563 | .filter(Boolean) |
|
| Original file line number | Diff line number | Diff line change |
|---|
@@ -734,6 +734,28 @@ describe("buildAgentSystemPrompt", () => {
|
734 | 734 | ); |
735 | 735 | }); |
736 | 736 | |
| 737 | +it("adds MEMORY guidance when a memory file is present", () => { |
| 738 | +const prompt = buildAgentSystemPrompt({ |
| 739 | +workspaceDir: "/tmp/openclaw", |
| 740 | +contextFiles: [ |
| 741 | +{ |
| 742 | +path: "MEMORY.md", |
| 743 | +content: "NEVER use [[tts:...]] or TTS commands; ALWAYS use local Piper.", |
| 744 | +}, |
| 745 | +], |
| 746 | +ttsHint: |
| 747 | +"Voice (TTS) is enabled.\nUse [[tts:...]] and optional [[tts:text]]...[[/tts:text]] to control voice/expressiveness.", |
| 748 | +}); |
| 749 | + |
| 750 | +expect(prompt).toContain( |
| 751 | +"MEMORY.md: durable user preferences and behavior guidance. Keep following it throughout the session unless higher-priority instructions override.", |
| 752 | +); |
| 753 | +expect(prompt.indexOf("NEVER use [[tts:...]]")).toBeGreaterThan(-1); |
| 754 | +expect(prompt.lastIndexOf("## Voice (TTS)")).toBeGreaterThan( |
| 755 | +prompt.indexOf("NEVER use [[tts:...]]"), |
| 756 | +); |
| 757 | +}); |
| 758 | + |
737 | 759 | it("omits project context when no context files are injected", () => { |
738 | 760 | const prompt = buildAgentSystemPrompt({ |
739 | 761 | workspaceDir: "/tmp/openclaw", |
|
| Original file line number | Diff line number | Diff line change |
|---|
@@ -186,10 +186,18 @@ function buildProjectContextSection(params: {
|
186 | 186 | const hasSoulFile = params.files.some( |
187 | 187 | (file) => getContextFileBasename(file.path) === "soul.md", |
188 | 188 | ); |
| 189 | +const hasMemoryFile = params.files.some( |
| 190 | +(file) => getContextFileBasename(file.path) === "memory.md", |
| 191 | +); |
189 | 192 | lines.push("The following project context files have been loaded:"); |
190 | 193 | if (hasSoulFile) { |
191 | 194 | lines.push("SOUL.md: persona/tone. Follow it unless higher-priority instructions override."); |
192 | 195 | } |
| 196 | +if (hasMemoryFile) { |
| 197 | +lines.push( |
| 198 | +"MEMORY.md: durable user preferences and behavior guidance. Keep following it throughout the session unless higher-priority instructions override.", |
| 199 | +); |
| 200 | +} |
193 | 201 | lines.push(""); |
194 | 202 | } |
195 | 203 | for (const file of params.files) { |
|
此内容由惯性聚合(RSS阅读器)自动聚合整理,仅供阅读参考。 原文来自 — 版权归原作者所有。