Skip to content

docs: document opencode web-search opt-in + add coder restraint guardrail#64

Merged
AbirAbbas merged 1 commit into
mainfrom
docs/web-search-via-opencode-exa
May 6, 2026
Merged

docs: document opencode web-search opt-in + add coder restraint guardrail#64
AbirAbbas merged 1 commit into
mainfrom
docs/web-search-via-opencode-exa

Conversation

@AbirAbbas

Copy link
Copy Markdown
Collaborator

Summary

Documents how to enable web search on this stack (set OPENCODE_ENABLE_EXA=1 + EXA_API_KEY in the deployment env — that's the whole knob) and adds one targeted prompt-level guardrail on run_coder.

The actual capability is already wired: opencode's built-in websearch/webfetch activate when those env vars are set, opencode's subprocess inherits them via agentfield/run_cli, and the model learns about the tools via the standard tool-definition layer (no system-prompt injection from us required for awareness). Verified end-to-end via the agentfield SDK against opencode — the model autonomously invoked Exa Web Search when asked a question that required current information.

What's in the diff

  • .env.example — adds the two env vars with brief docs
  • README.md — adds an "Optional: web search" subsection in Quick Start
  • swe_af/tools/web_search.py — single helper maybe_apply_coder_guardrail(prompt) plus the WEB_SEARCH_CODER_GUARDRAIL text. Helper appends the restraint snippet to a system prompt only when both env vars are set; otherwise returns the prompt unchanged so we don't tell the model about a tool it can't use.
  • run_coder only — one-line change: system_prompt=maybe_apply_coder_guardrail(CODER_SYSTEM_PROMPT).

Why only run_coder

The coder reasoner runs many turns inside a single coding loop — that's the one place an unrestrained model could rabbit-hole on searches for things it could read from the codebase. Every other reasoner is short / single-shot / analytic, where the model's own judgment plus opencode's tool advertisement is sufficient. Add per-reasoner restraint guidance later only if a specific reasoner is observed over-searching.

What's deliberately NOT added

  • No "you have web search" boilerplate on every reasoner. opencode advertises tools natively; verified the model picks them up autonomously without prompt injection. Adding boilerplate would just eat context.
  • No agentfield framework changes. The opencode-tools-allow-list gap (where tools=[...] is silently ignored on opencode/codex/gemini) is a real bug but not blocking web search — opencode enables tools by default, so no allow-list needed for them to function.

Tests

7 unit tests on the helper covering env-var gating, the restraint snippet text contract, and edge cases (only one var set, empty string key, non-1 flag value). All sub-second, no API keys required.

🤖 Generated with Claude Code

…rdrail

What enables web search on this stack: setting OPENCODE_ENABLE_EXA=1 and
EXA_API_KEY in the deployment env. opencode's built-in `websearch` and
`webfetch` tools then activate, and the model picks them up via the
standard tool-definition layer (no system-prompt injection needed for
awareness — opencode handles it). The opencode subprocess inherits these
vars from agentfield's run_cli, so no SWE-AF code is required to turn it
on.

What's added here:
- `.env.example` documents the two env vars
- README gets a short "Optional: web search" subsection in Quick Start
- `swe_af/tools/web_search.py` exposes one helper, `maybe_apply_coder_guardrail`,
  that conditionally appends a restraint snippet to run_coder's system
  prompt when the env vars are set. Why only run_coder: it's the one
  reasoner with a long iterative loop where a model could plausibly
  rabbit-hole on searches it could answer by reading the codebase. Other
  reasoners are short or single-shot — the model's own judgment plus
  opencode's tool advertisement is sufficient.
- 7 unit tests covering env-var gating (both vars required, empty key
  treated as absent, no append when off, append when on, guardrail text
  contract).

What's NOT added (deliberately):
- No "you have web search" prompt boilerplate on every reasoner. opencode
  already advertises tools to the model via the tool-definition layer —
  verified by autonomous tool use in a smoke test where the model invoked
  websearch without being told it had a tool. Adding redundant boilerplate
  would just eat context.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@AbirAbbas AbirAbbas merged commit 7b9c1a5 into main May 6, 2026
2 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant