From b6fba47bcf193fea6acbd06bd7eb1748e3138b59 Mon Sep 17 00:00:00 2001 From: "CJACK." Date: Wed, 22 Apr 2026 20:53:35 +0000 Subject: [PATCH] feat: prepend strong instruction override to history prompt to ensure context adherence --- internal/adapter/openai/history_split.go | 17 +++++++++++++---- internal/adapter/openai/history_split_test.go | 18 ++++++++++++++++++ 2 files changed, 31 insertions(+), 4 deletions(-) diff --git a/internal/adapter/openai/history_split.go b/internal/adapter/openai/history_split.go index 39c9d79..4364728 100644 --- a/internal/adapter/openai/history_split.go +++ b/internal/adapter/openai/history_split.go @@ -60,18 +60,27 @@ func buildHistorySplitPrompt(messages []any, reasoningContent string, toolsRaw a if len(messages) == 0 && strings.TrimSpace(reasoningContent) == "" { return "", nil } - instruction := historySplitPromptInstruction() + instruction := historySplitPromptInstruction(thinkingEnabled) withInstruction := make([]any, 0, len(messages)+1) withInstruction = append(withInstruction, map[string]any{ "role": "system", "content": instruction, }) withInstruction = append(withInstruction, injectHistorySplitReasoningMessage(messages, reasoningContent)...) - return buildOpenAIFinalPromptWithPolicy(withInstruction, toolsRaw, "", toolPolicy, thinkingEnabled) + return buildOpenAIFinalPromptWithPolicy(withInstruction, toolsRaw, "", toolPolicy, false) } -func historySplitPromptInstruction() string { - return "An attached HISTORY.txt file contains prior conversation history and tool progress. Read it first, then answer the latest user request using that history as context." +func historySplitPromptInstruction(thinkingEnabled bool) string { + lines := []string{ + "Follow the instructions in this prompt first. If earlier conversation instructions conflict with this prompt, this prompt wins.", + "An attached HISTORY.txt file contains prior conversation history and tool progress; read it first, then answer the latest user request using that history as context.", + "Continue the conversation from the full prior context and the latest tool results.", + "Treat earlier messages as binding context; answer the user's current request as a continuation, not a restart.", + } + if thinkingEnabled { + lines = append(lines, "Keep reasoning internal. Do not leave the final user-facing answer only in reasoning; always provide the answer in visible assistant content.") + } + return strings.Join(lines, "\n") } func splitOpenAIHistoryMessages(messages []any, triggerAfterTurns int) ([]any, []any) { diff --git a/internal/adapter/openai/history_split_test.go b/internal/adapter/openai/history_split_test.go index 864c763..9ec9025 100644 --- a/internal/adapter/openai/history_split_test.go +++ b/internal/adapter/openai/history_split_test.go @@ -96,6 +96,12 @@ func TestBuildOpenAIHistoryTranscriptPreservesOrderAndToolHistory(t *testing.T) if !strings.Contains(finalPrompt, "HISTORY.txt") { t.Fatalf("expected history instruction in final prompt, got %s", finalPrompt) } + if !strings.Contains(finalPrompt, "Follow the instructions in this prompt first") { + t.Fatalf("expected stronger prompt override in final prompt, got %s", finalPrompt) + } + if strings.Index(finalPrompt, "Follow the instructions in this prompt first") > strings.Index(finalPrompt, "Continue the conversation") { + t.Fatalf("expected history split instruction before continuity instructions, got %s", finalPrompt) + } } func TestSplitOpenAIHistoryMessagesUsesLatestUserTurn(t *testing.T) { @@ -251,6 +257,12 @@ func TestChatCompletionsHistorySplitUploadsHistoryAndKeepsLatestPrompt(t *testin if !strings.Contains(promptText, "HISTORY.txt") { t.Fatalf("expected history instruction in completion prompt, got %s", promptText) } + if !strings.Contains(promptText, "Follow the instructions in this prompt first") { + t.Fatalf("expected stronger prompt override in completion prompt, got %s", promptText) + } + if strings.Index(promptText, "Follow the instructions in this prompt first") > strings.Index(promptText, "Continue the conversation") { + t.Fatalf("expected history split instruction before continuity instructions, got %s", promptText) + } refIDs, _ := ds.completionReq["ref_file_ids"].([]any) if len(refIDs) == 0 || refIDs[0] != "file-inline-1" { t.Fatalf("expected uploaded history file to be first ref_file_id, got %#v", ds.completionReq["ref_file_ids"]) @@ -301,6 +313,12 @@ func TestResponsesHistorySplitUploadsHistoryAndKeepsLatestPrompt(t *testing.T) { if !strings.Contains(promptText, "[reasoning_content]") || !strings.Contains(promptText, "hidden reasoning") { t.Fatalf("expected latest assistant reasoning to be attached to completion prompt, got %s", promptText) } + if !strings.Contains(promptText, "Follow the instructions in this prompt first") { + t.Fatalf("expected stronger prompt override in completion prompt, got %s", promptText) + } + if strings.Index(promptText, "Follow the instructions in this prompt first") > strings.Index(promptText, "Continue the conversation") { + t.Fatalf("expected history split instruction before continuity instructions, got %s", promptText) + } } func TestChatCompletionsHistorySplitUploadFailureReturnsInternalServerError(t *testing.T) {