feat(web,desktop): coding agents read the web through the planning model's own hosted search and page read (one runtime 4/n)
Merged
DA
6d ago+335+335+012345678901234567890123456789-41-41-01234567890123456789
One-agent-runtime migration, PR 4 (docs/proposals/one-agent-runtime.md §5, Decision 2: "The hosted search_web and read_web_page for every role, on Luke's key and metered").
What
The planning model and its worker searched the web with Luke's hosted pair (public-research.ts):
search_web: one OpenAI Responses call on Luke's key. The query is screened for anything shaped like a credential and must be one line of public words. It answersfoundonly with at least one cited public URL, and it's budgeted per turn and counted on the account's meter.read_web_page: a GET of one public URL that refuses private, loopback, link-local and reserved addresses, budgeted per turn.
Coding agents and their workers used eve's provider-run web_search and web_fetch instead, with none of that screening, budget or count. Now every role uses the hosted pair:
- Tool files.
coder/tools/search_web.tsandread_web_page.ts, plus the worker's own two, replace the fourweb_search/web_fetchfiles. Each calls the edge doorrunResearchTool(coder/host.ts) under the agent's admission (admitfor the agent,admitDelegatedfor the worker). The door runsCoderHost.research, which builds the sameResearchCallthe brain does: the turn's budget, Luke's OpenAI access (researchOpenAiOf, the brain's own model), and the account's meter. CoderHostSeams.research(userId)supplies that access and the meter.CODER_TOOLandWORKER_TOOL_NAMESnamesearch_webandread_web_page.- Old transcripts keep reading.
RETIRED_CODER_TOOLkeepsweb_searchandweb_fetchinCODER_TOOL_SET, so a transcript written before reads back unchanged. The desktop still draws those rows, and the brain's summary of an agent (coding-agent-tools.ts) still names them. - Context estimate.
context-estimate.tsnow counts the pair's declarations among the authored tools, since they're no longer provider-run. - Prompts. The coder's and its worker's instructions name the pair and the rule the planning worker already had: never put the repository's code, names or paths into a query.
- Desktop.
tool-call-model.tsdrawssearch_webby its query andread_web_pageby the page's name, with its text as the body.
Tests
tests/coder-host.test.ts, new: a coding agent's search on a deployment with no key is refused in the hosted search's own words. A page read ofhttps://127.0.0.1/adminis refused as not public and never fetched.tests/coder-agent.test.ts: the authored tools, plus the retired names and the integrations' calls, are exactly the writer's tool set, and no retired name is authored.tool-call-model.test.ts, new: the hosted pair draws as web reads.- The web suite (154 files, 1,316 tests) and
src/renderer/planningpass. The offline brain and coder evals pass against a local Postgres; the coder eval builds the root with the new tool files. Lint and repository checks pass.
CI could not verify the Mac UI: CI builds nothing for the Mac, and ./scripts/verify.sh was not run (LUKE-159 is the manual Mac pass). The only desktop change is the two new rows' words, covered by the model test.
🤖 Generated with Claude Code