From 2c39cd095358a9c501a72949b6531eb6fc3fe8dc Mon Sep 17 00:00:00 2001 From: xingsy97 <87063252+xingsy97@users.noreply.github.com> Date: Fri, 13 Mar 2026 17:37:03 +0800 Subject: [PATCH] fix(agents): rephrase session reset prompt to avoid Azure content filter (#43403) * fix(agents): rephrase session reset prompt to avoid Azure content filter Azure OpenAI's content filter flags the phrase 'Execute your Session Startup sequence now' as potentially harmful, causing /new and /reset to return 400 for all Azure-hosted deployments. Replace 'Execute ... now' with 'Run your Session Startup sequence' in session-reset-prompt.ts and post-compaction-context.ts. The semantics are identical but the softer phrasing avoids the false-positive. Closes #42769 * ci: retrigger checks (windows shard timeout) * fix: add changelog for Azure startup prompt fix (#43403) (thanks @xingsy97) --------- Co-authored-by: Ayaan Zaidi --- CHANGELOG.md | 1 + .../reply.triggers.trigger-handling.test-harness.ts | 2 +- src/auto-reply/reply/post-compaction-context.test.ts | 4 ++-- src/auto-reply/reply/post-compaction-context.ts | 2 +- src/auto-reply/reply/session-reset-prompt.test.ts | 2 +- src/auto-reply/reply/session-reset-prompt.ts | 2 +- src/gateway/server-methods/agent.test.ts | 2 +- src/gateway/server.agent.gateway-server-agent-b.test.ts | 2 +- 8 files changed, 9 insertions(+), 8 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 47fb63e5c39..f8820bea39f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -18,6 +18,7 @@ Docs: https://docs.openclaw.ai - Gateway/session reset: preserve `lastAccountId` and `lastThreadId` across gateway session resets so replies keep routing back to the same account and thread after `/reset`. (#44773) Thanks @Lanfei. - Agents/memory bootstrap: load only one root memory file, preferring `MEMORY.md` and using `memory.md` as a fallback, so case-insensitive Docker mounts no longer inject duplicate memory context. (#26054) Thanks @Lanfei. - Agents/OpenAI-compatible compat overrides: respect explicit user `models[].compat` opt-ins for non-native `openai-completions` endpoints so usage-in-streaming capability overrides no longer get forced off when the endpoint actually supports them. (#44432) Thanks @cheapestinference. +- Agents/Azure OpenAI startup prompts: rephrase the built-in `/new`, `/reset`, and post-compaction startup instruction so Azure OpenAI deployments no longer hit HTTP 400 false positives from the content filter. (#43403) Thanks @xingsy97. ## 2026.3.12 diff --git a/src/auto-reply/reply.triggers.trigger-handling.test-harness.ts b/src/auto-reply/reply.triggers.trigger-handling.test-harness.ts index 69db49e97ee..db8dd5b1fae 100644 --- a/src/auto-reply/reply.triggers.trigger-handling.test-harness.ts +++ b/src/auto-reply/reply.triggers.trigger-handling.test-harness.ts @@ -363,7 +363,7 @@ export async function runGreetingPromptForBareNewOrReset(params: { expect(runEmbeddedPiAgentMock).toHaveBeenCalledOnce(); const prompt = runEmbeddedPiAgentMock.mock.calls.at(-1)?.[0]?.prompt ?? ""; expect(prompt).toContain("A new session was started via /new or /reset"); - expect(prompt).toContain("Execute your Session Startup sequence now"); + expect(prompt).toContain("Run your Session Startup sequence"); } export function installTriggerHandlingE2eTestHooks() { diff --git a/src/auto-reply/reply/post-compaction-context.test.ts b/src/auto-reply/reply/post-compaction-context.test.ts index 0c97df4d50b..02a4a27e6de 100644 --- a/src/auto-reply/reply/post-compaction-context.test.ts +++ b/src/auto-reply/reply/post-compaction-context.test.ts @@ -332,7 +332,7 @@ Read WORKFLOW.md on startup. fs.writeFileSync(path.join(tmpDir, "AGENTS.md"), content); const result = await readPostCompactionContext(tmpDir); expect(result).not.toBeNull(); - expect(result).toContain("Execute your Session Startup sequence now"); + expect(result).toContain("Run your Session Startup sequence"); }); it("falls back to legacy sections when defaults are explicitly configured", async () => { @@ -368,7 +368,7 @@ Read WORKFLOW.md on startup. expect(result).not.toBeNull(); expect(result).toContain("Do startup things"); expect(result).toContain("Be safe"); - expect(result).toContain("Execute your Session Startup sequence now"); + expect(result).toContain("Run your Session Startup sequence"); }); it("custom section names are matched case-insensitively", async () => { diff --git a/src/auto-reply/reply/post-compaction-context.ts b/src/auto-reply/reply/post-compaction-context.ts index 316ac3c29b1..791c1a91a19 100644 --- a/src/auto-reply/reply/post-compaction-context.ts +++ b/src/auto-reply/reply/post-compaction-context.ts @@ -136,7 +136,7 @@ export async function readPostCompactionContext( // would be misleading for deployments that use different section names. const prose = isDefaultSections ? "Session was just compacted. The conversation summary above is a hint, NOT a substitute for your startup sequence. " + - "Execute your Session Startup sequence now — read the required files before responding to the user." + "Run your Session Startup sequence — read the required files before responding to the user." : `Session was just compacted. The conversation summary above is a hint, NOT a substitute for your full startup sequence. ` + `Re-read the sections injected below (${displayNames.join(", ")}) and follow your configured startup procedure before responding to the user.`; diff --git a/src/auto-reply/reply/session-reset-prompt.test.ts b/src/auto-reply/reply/session-reset-prompt.test.ts index c6a1d2d9562..bf038243962 100644 --- a/src/auto-reply/reply/session-reset-prompt.test.ts +++ b/src/auto-reply/reply/session-reset-prompt.test.ts @@ -5,7 +5,7 @@ import { buildBareSessionResetPrompt } from "./session-reset-prompt.js"; describe("buildBareSessionResetPrompt", () => { it("includes the core session startup instruction", () => { const prompt = buildBareSessionResetPrompt(); - expect(prompt).toContain("Execute your Session Startup sequence now"); + expect(prompt).toContain("Run your Session Startup sequence"); expect(prompt).toContain("read the required files before responding to the user"); }); diff --git a/src/auto-reply/reply/session-reset-prompt.ts b/src/auto-reply/reply/session-reset-prompt.ts index 67e693f70b1..c903e3a688a 100644 --- a/src/auto-reply/reply/session-reset-prompt.ts +++ b/src/auto-reply/reply/session-reset-prompt.ts @@ -2,7 +2,7 @@ import { appendCronStyleCurrentTimeLine } from "../../agents/current-time.js"; import type { OpenClawConfig } from "../../config/config.js"; const BARE_SESSION_RESET_PROMPT_BASE = - "A new session was started via /new or /reset. Execute your Session Startup sequence now - read the required files before responding to the user. Then greet the user in your configured persona, if one is provided. Be yourself - use your defined voice, mannerisms, and mood. Keep it to 1-3 sentences and ask what they want to do. If the runtime model differs from default_model in the system prompt, mention the default model. Do not mention internal steps, files, tools, or reasoning."; + "A new session was started via /new or /reset. Run your Session Startup sequence - read the required files before responding to the user. Then greet the user in your configured persona, if one is provided. Be yourself - use your defined voice, mannerisms, and mood. Keep it to 1-3 sentences and ask what they want to do. If the runtime model differs from default_model in the system prompt, mention the default model. Do not mention internal steps, files, tools, or reasoning."; /** * Build the bare session reset prompt, appending the current date/time so agents diff --git a/src/gateway/server-methods/agent.test.ts b/src/gateway/server-methods/agent.test.ts index 5dfa27b20ce..f3b74416c70 100644 --- a/src/gateway/server-methods/agent.test.ts +++ b/src/gateway/server-methods/agent.test.ts @@ -582,7 +582,7 @@ describe("gateway agent handler", () => { expect(mocks.performGatewaySessionReset).toHaveBeenCalledTimes(1); const call = readLastAgentCommandCall(); // Message is now dynamically built with current date — check key substrings - expect(call?.message).toContain("Execute your Session Startup sequence now"); + expect(call?.message).toContain("Run your Session Startup sequence"); expect(call?.message).toContain("Current time:"); expect(call?.message).not.toBe(BARE_SESSION_RESET_PROMPT); expect(call?.sessionId).toBe("reset-session-id"); diff --git a/src/gateway/server.agent.gateway-server-agent-b.test.ts b/src/gateway/server.agent.gateway-server-agent-b.test.ts index 755186080ba..61fff855a8f 100644 --- a/src/gateway/server.agent.gateway-server-agent-b.test.ts +++ b/src/gateway/server.agent.gateway-server-agent-b.test.ts @@ -287,7 +287,7 @@ describe("gateway server agent", () => { await vi.waitFor(() => expect(calls.length).toBeGreaterThan(callsBefore)); const call = (calls.at(-1)?.[0] ?? {}) as Record; expect(call.message).toBeTypeOf("string"); - expect(call.message).toContain("Execute your Session Startup sequence now"); + expect(call.message).toContain("Run your Session Startup sequence"); expect(call.message).toContain("Current time:"); expect(typeof call.sessionId).toBe("string"); expect(call.sessionId).not.toBe("sess-main-before-reset");