From d0bedf265e45bfe3360666e3701c5c4c1f976013 Mon Sep 17 00:00:00 2001 From: Mason Daugherty <61371264+mdrxy@users.noreply.github.com> Date: Tue, 18 Aug 2026 17:27:01 +0000 Subject: [PATCH] fix(code): omit unavailable web-search prompt guidance Co-authored-by: open-swe[bot] --- libs/code/deepagents_code/agent.py | 17 ++++++++++++ libs/code/deepagents_code/system_prompt.md | 15 +---------- .../system_prompt_interactive_local.md | 13 ---------- .../smoke_tests/test_system_prompt.py | 1 + libs/code/tests/unit_tests/test_agent.py | 26 +++++++++++++++++++ 5 files changed, 45 insertions(+), 27 deletions(-) diff --git a/libs/code/deepagents_code/agent.py b/libs/code/deepagents_code/agent.py index fa9e086909..f03209d49e 100644 --- a/libs/code/deepagents_code/agent.py +++ b/libs/code/deepagents_code/agent.py @@ -1377,6 +1377,21 @@ def reset_agent( ) """dcode filesystem-tool preferences included in the generated prompt.""" +_WEB_SEARCH_TOOL_GUIDANCE = ( + "\n\n### Web Search Tool Usage\n\n" + "When you use the web_search tool:\n\n" + "1. The tool will return search results with titles, URLs, and content excerpts\n" + "2. You MUST read and process these results, then respond naturally to the user\n" + "3. NEVER show raw JSON or tool results directly to the user\n" + "4. Synthesize the information from multiple sources into a coherent answer\n" + "5. Cite your sources by mentioning page titles or URLs when relevant\n" + "6. If the search doesn't find what you need, explain what you found and ask " + "clarifying questions\n\n" + "The user only sees your text responses - not tool results. Always provide a " + "complete, natural language answer after using web_search." +) +"""Usage guidance included only when the Tavily-backed tool is available.""" + def _build_fs_tool_prompt_guidance(fs_tools: list[FsToolName] | None) -> str: """Build dcode prompt guidance for the enabled filesystem tools. @@ -1530,6 +1545,7 @@ def get_system_prompt( unsupported_modalities=settings.model_unsupported_modalities, ) filesystem_tool_guidance = _build_fs_tool_prompt_guidance(fs_tools) + web_search_tool_guidance = _WEB_SEARCH_TOOL_GUIDANCE if settings.has_tavily else "" # Build working directory section (local vs sandbox) if sandbox_type: @@ -1583,6 +1599,7 @@ def get_system_prompt( .replace("{working_dir_section}", working_dir_section) .replace("{skills_path}", skills_path) .replace("{filesystem_tool_guidance}", filesystem_tool_guidance) + .replace("{web_search_tool_guidance}", web_search_tool_guidance) ) # Detect unreplaced placeholders (defense-in-depth for template typos) diff --git a/libs/code/deepagents_code/system_prompt.md b/libs/code/deepagents_code/system_prompt.md index 56f5d0d7b8..376d06e1a4 100644 --- a/libs/code/deepagents_code/system_prompt.md +++ b/libs/code/deepagents_code/system_prompt.md @@ -181,17 +181,4 @@ Some tool calls require user approval before execution. When a tool call is reje 3. Suggest an alternative approach or ask for clarification 4. Never attempt the exact same rejected command again -Respect the user's decisions and work with them collaboratively. - -### Web Search Tool Usage - -When you use the web_search tool: - -1. The tool will return search results with titles, URLs, and content excerpts -2. You MUST read and process these results, then respond naturally to the user -3. NEVER show raw JSON or tool results directly to the user -4. Synthesize the information from multiple sources into a coherent answer -5. Cite your sources by mentioning page titles or URLs when relevant -6. If the search doesn't find what you need, explain what you found and ask clarifying questions - -The user only sees your text responses - not tool results. Always provide a complete, natural language answer after using web_search. +Respect the user's decisions and work with them collaboratively.{web_search_tool_guidance} diff --git a/libs/code/tests/unit_tests/smoke_tests/snapshots/system_prompt_interactive_local.md b/libs/code/tests/unit_tests/smoke_tests/snapshots/system_prompt_interactive_local.md index 34345a3898..5ca6ef6807 100644 --- a/libs/code/tests/unit_tests/smoke_tests/snapshots/system_prompt_interactive_local.md +++ b/libs/code/tests/unit_tests/smoke_tests/snapshots/system_prompt_interactive_local.md @@ -204,19 +204,6 @@ Some tool calls require user approval before execution. When a tool call is reje Respect the user's decisions and work with them collaboratively. -### Web Search Tool Usage - -When you use the web_search tool: - -1. The tool will return search results with titles, URLs, and content excerpts -2. You MUST read and process these results, then respond naturally to the user -3. NEVER show raw JSON or tool results directly to the user -4. Synthesize the information from multiple sources into a coherent answer -5. Cite your sources by mentioning page titles or URLs when relevant -6. If the search doesn't find what you need, explain what you found and ask clarifying questions - -The user only sees your text responses - not tool results. Always provide a complete, natural language answer after using web_search. - ## Shell paths vs. virtual paths diff --git a/libs/code/tests/unit_tests/smoke_tests/test_system_prompt.py b/libs/code/tests/unit_tests/smoke_tests/test_system_prompt.py index eed3b72a1a..f296778128 100644 --- a/libs/code/tests/unit_tests/smoke_tests/test_system_prompt.py +++ b/libs/code/tests/unit_tests/smoke_tests/test_system_prompt.py @@ -129,6 +129,7 @@ def _mock_settings(tmp_path: Path) -> Generator[None, None, None]: mock_s.model_provider = _FIXED_MODEL_PROVIDER mock_s.model_context_limit = _FIXED_CONTEXT_LIMIT mock_s.model_unsupported_modalities = frozenset() + mock_s.has_tavily = False mock_s.project_root = None mock_s.user_langchain_project = None mock_s.shell_allow_list = None diff --git a/libs/code/tests/unit_tests/test_agent.py b/libs/code/tests/unit_tests/test_agent.py index 41a1427848..db2ecd57fb 100644 --- a/libs/code/tests/unit_tests/test_agent.py +++ b/libs/code/tests/unit_tests/test_agent.py @@ -1496,6 +1496,32 @@ def test_no_modality_warning_when_all_supported(self) -> None: assert "may not be available" not in prompt +class TestGetSystemPromptWebSearch: + """Tests for conditional web-search guidance.""" + + def test_omits_guidance_without_tavily(self) -> None: + mock_settings = Mock() + mock_settings.model_name = None + mock_settings.has_tavily = False + + with patch("deepagents_code.agent.settings", mock_settings): + prompt = get_system_prompt("test-agent") + + assert "### Web Search Tool Usage" not in prompt + assert "{web_search_tool_guidance}" not in prompt + + def test_includes_guidance_with_tavily(self) -> None: + mock_settings = Mock() + mock_settings.model_name = None + mock_settings.has_tavily = True + + with patch("deepagents_code.agent.settings", mock_settings): + prompt = get_system_prompt("test-agent") + + assert "### Web Search Tool Usage" in prompt + assert "When you use the web_search tool:" in prompt + + class TestGetSystemPromptNonInteractive: """Tests for interactive vs non-interactive system prompt."""