docs: reserve seam for complete capabilities

This commit is contained in:
Turtle
2026-08-09 15:34:32 +08:00
parent 27ac49e687
commit dda02250f5
966 changed files with 2166 additions and 2159 deletions

View File

@@ -2,5 +2,5 @@
# side as of the last confirmed-consistent state. Both languages carry equal authority;
# after editing either side, bring the other along and re-record with:
# pnpm run verify-translation-pairing --write packages/web/tool-web/README.md
README.md: 646601bb5bd6c27876918b7aca49962ae34bae33
README.zh.md: 135c75831045225a0ac6d4637ff5c8b4105336c0
README.md: 643da4e2f083c2efabd39a462290559ddbd291c8
README.zh.md: 7b52f2b08f393a584258dea1a216d9124ec8760a

View File

@@ -15,7 +15,7 @@ Each tool is registered independently; a product that wants only one disables th
Both tools opt into concurrent scheduling because provider reads return content without mutating parent-agent state.
The normalized seam results are also the canonical tool values: `WebSearchResult` and `WebFetchResult`. Native renderers preserve the answer/source and fetched-body text below; provider search/body caps remain acquisition limits rather than presentation-only truncation.
The normalized service results are also the canonical tool values: `WebSearchResult` and `WebFetchResult`. Native renderers preserve the answer/source and fetched-body text below; provider search/body caps remain acquisition limits rather than presentation-only truncation.
## Config

View File

@@ -15,7 +15,7 @@
两个工具都选择并发调度,因为提供方读取会返回内容,不会修改父 agent智能体的状态。
规范化后的 seam 结果也是标准工具值:`WebSearchResult``WebFetchResult`。原生渲染器会保留下文所述的答案、来源和抓取正文文本;提供方对搜索结果数量和正文大小的上限仍属于获取限制,而非仅用于呈现的截断。
规范化后的服务结果也是标准工具值:`WebSearchResult``WebFetchResult`。原生渲染器会保留下文所述的答案、来源和抓取正文文本;提供方对搜索结果数量和正文大小的上限仍属于获取限制,而非仅用于呈现的截断。
## 配置

View File

@@ -2,7 +2,7 @@
* The model-facing `web_fetch` tool. This module owns its schema, validation, and presentation;
* `ctx.web` owns retrieval. Timeout is deployment policy, not a model argument: config becomes
* `ToolDefinition.timeoutMs`, timeout policy enforces it, and this tool forwards the resulting
* signal. A provider timeout remains a backstop for direct seam callers.
* signal. A provider timeout remains a backstop for direct service callers.
*/
import type { Context } from 'cordis'

View File

@@ -2,5 +2,5 @@
# side as of the last confirmed-consistent state. Both languages carry equal authority;
# after editing either side, bring the other along and re-record with:
# pnpm run verify-translation-pairing --write packages/web/web-fetch-local/README.md
README.md: 531bfc94a4b2867b1a81d2e0b398ec403186b347
README.zh.md: 260227679b72ec993dbb9e42a9d2a814bf691e2c
README.md: 03d6d2a96b04528b33cd063736e8618e66932058
README.zh.md: 66a8ebe0839c8ba494c3a30b761025fb6b3f75bb

View File

@@ -12,7 +12,7 @@ The provider owns **safe resource retrieval**: URL validation, HTTP transport, r
The provider's `timeoutMs` is a resource backstop for direct `ctx.web.fetch()` callers and misconfigured deployments, not the model-facing tool-call budget. [`dsh-timeout-policy`](../../guard/timeout-policy/README.md) owns the `web_fetch` tool-call budget by arming `exec.signal`.
A shipping web-tool deployment sets the provider backstop above the tool budget, so model calls normally return `TOOL_TIMEOUT`. If the outer deadline reaches the provider first, the provider reports `WEB_ABORTED` and the outer policy replaces it with `TOOL_TIMEOUT`. `WEB_FETCH_TIMEOUT` therefore identifies a direct seam caller whose provider budget elapsed.
A shipping web-tool deployment sets the provider backstop above the tool budget, so model calls normally return `TOOL_TIMEOUT`. If the outer deadline reaches the provider first, the provider reports `WEB_ABORTED` and the outer policy replaces it with `TOOL_TIMEOUT`. `WEB_FETCH_TIMEOUT` therefore identifies a direct service caller whose provider budget elapsed.
## Transport hygiene

View File

@@ -12,7 +12,7 @@
提供方的 `timeoutMs` 是直接 `ctx.web.fetch()` 调用方和配置有误的部署所用的资源兜底,不是面向模型的工具调用预算。[`dsh-timeout-policy`](../../guard/timeout-policy/README.md) 拥有 `web_fetch` 工具调用预算,并让 `exec.signal` 在超时时触发,以强制执行该预算。
已交付的 web 工具部署会把提供方兜底设为高于工具预算,因此模型调用通常返回 `TOOL_TIMEOUT`。如果外层截止期限先于提供方的兜底超时触发,提供方会报告 `WEB_ABORTED`,外层策略再将其替换为 `TOOL_TIMEOUT`。因此,`WEB_FETCH_TIMEOUT` 表明直接 seam 调用方的提供方预算已经耗尽。
已交付的 web 工具部署会把提供方兜底设为高于工具预算,因此模型调用通常返回 `TOOL_TIMEOUT`。如果外层截止期限先于提供方的兜底超时触发,提供方会报告 `WEB_ABORTED`,外层策略再将其替换为 `TOOL_TIMEOUT`。因此,`WEB_FETCH_TIMEOUT` 表明直接服务调用方的提供方预算已经耗尽。
## 传输卫生

View File

@@ -135,7 +135,7 @@ export function citationSnippets(blocks: readonly ContentBlock[]): Map<string, s
* Map a DeepSeek Anthropic Messages response to a normalized search result. Walks
* `web_search_tool_result` blocks for citeable `web_search_result` items, joins each to its
* citation excerpt as `snippet`, and dedupes by `url` (a `max_uses > 1` request can surface
* the same URL across searches). The seam owns the final `maxResults` truncation, so
* the same URL across searches). The web service owns the final `maxResults` truncation, so
* `truncated` is always `false` here.
*
* @param response - the parsed Messages response body.

View File

@@ -2,5 +2,5 @@
# side as of the last confirmed-consistent state. Both languages carry equal authority;
# after editing either side, bring the other along and re-record with:
# pnpm run verify-translation-pairing --write packages/web/web-search-exa/README.md
README.md: c24f952eede90aae6fa23eec976255cb99625c19
README.zh.md: 58255a564601ae4d57f1916507a76a55cdbabf44
README.md: 5b1212c1fb210a3aca7836875cc295fad87e7437
README.zh.md: fc9afbe44dcb5dd55c7007a11b35048217143351

View File

@@ -38,5 +38,5 @@ No direct invalidation; the named consumer owns any request-prefix changes.
## Known Limitations and Deferred Work
- **A result with no non-blank highlight is dropped entirely** — no portable snippet to map, so fewer sources than the requested count can return.
- **Only `searchType`/`numResults`/`highlightsPerResult` are exposed** — Exa's other controls (livecrawl, category, domain/date filters, full-text contents) wait on provider-neutral seam fields ([seam Agent Note](../../../.agents/notes/implemented/architecture/2026-06-24-web-capability-seam.md)).
- **Only `searchType`/`numResults`/`highlightsPerResult` are exposed** — Exa's other controls (livecrawl, category, domain/date filters, full-text contents) wait on provider-neutral Service Definition fields ([seam Agent Note](../../../.agents/notes/implemented/architecture/2026-06-24-web-capability-seam.md)).
- **Abort classification is error-shape-based** — only a `DOMException` named `AbortError` maps to `WEB_ABORTED`; an abort carrying a custom reason (e.g. `dsh-timeout`'s `TimeoutReason`) surfaces as `WEB_PROVIDER_ERROR`.

View File

@@ -38,5 +38,5 @@ Exa 返回扁平 `results[]`,不返回生成答案,因此省略 `content`。
## 已知限制与暂缓事项
- **没有非空白高亮摘要的结果会被整个丢弃**:没有可映射的可移植 snippet因此返回源可能少于请求数量。
- **只公开 `searchType``numResults``highlightsPerResult`**Exa 的其他控制项livecrawl、category、域名日期过滤条件、全文内容等待提供方无关 seam 字段(见 [seam Agent Note](../../../.agents/notes/implemented/architecture/2026-06-24-web-capability-seam.md))。
- **只公开 `searchType``numResults``highlightsPerResult`**Exa 的其他控制项livecrawl、category、域名日期过滤条件、全文内容等待提供方无关的 Service Definition 字段(见 [seam Agent Note](../../../.agents/notes/implemented/architecture/2026-06-24-web-capability-seam.md))。
- **按错误形状分类中止**:只有 `DOMException` 且名为 `AbortError` 时才映射为 `WEB_ABORTED`;携带自定义原因的中止(例如 `dsh-timeout``TimeoutReason`)会呈现为 `WEB_PROVIDER_ERROR`

View File

@@ -75,7 +75,7 @@ export function mapExaResponse(response: ExaSearchResponse): WebSearchResult {
const sources = (response.results ?? [])
.map(mapExaResult)
.filter((source): source is WebSearchSource => source !== undefined)
// Exa returns no generated answer, so `content` is omitted. The seam owns the
// Exa returns no generated answer, so `content` is omitted. The web service owns the
// final `maxResults` truncation, so this provider reports `truncated: false`.
return { sources, truncated: false }
}

View File

@@ -2,5 +2,5 @@
# side as of the last confirmed-consistent state. Both languages carry equal authority;
# after editing either side, bring the other along and re-record with:
# pnpm run verify-translation-pairing --write packages/web/web-search-perplexity/README.md
README.md: 80f6d34d63ddf0cc7d1f0d4f6744d64c91f9a269
README.zh.md: 485ba992a6fbc7bb6e4bb4a6753b7c34e9f61292
README.md: 8800609a05e99d3fa8a61e12b2360e633f0fd330
README.zh.md: fb20d796e9e943a5254b1d22eac3650e45ec95bf

View File

@@ -51,7 +51,7 @@ Through [`dsh-tool-web`](../tool-web/README.md), the conversation model sees the
#### Token effect
Zero direct conversation tokens from registration. Answer and source tokens are data-dependent, source count is seam-bounded, and the retained result or error is resent until compaction.
Zero direct conversation tokens from registration. Answer and source tokens are data-dependent, source count is service-bounded, and the retained result or error is resent until compaction.
#### KV Cache effect
@@ -61,5 +61,5 @@ Append-only; newly visible content follows the reusable request prefix and does
- **Citation-fallback sources are URL-only** — when Perplexity omits structured `search_results[]`, sources carry no `title`/`snippet`/`publishedAt`, so the tool renders bare hostname labels.
- **Over-returned sources still cost tokens and latency** — with no result-count control on the wire, `maxResults` is enforced only post-hoc by seam truncation.
- **Only `model`/`maxTokens`/`searchRecency` are exposed** — Perplexity's other search controls (domain filters, `web_search_options` context size, images) wait on provider-neutral seam fields ([seam Agent Note](../../../.agents/notes/implemented/architecture/2026-06-24-web-capability-seam.md)).
- **Only `model`/`maxTokens`/`searchRecency` are exposed** — Perplexity's other search controls (domain filters, `web_search_options` context size, images) wait on provider-neutral Service Definition fields ([seam Agent Note](../../../.agents/notes/implemented/architecture/2026-06-24-web-capability-seam.md)).
- **Abort classification is error-shape-based** — only a `DOMException` named `AbortError` maps to `WEB_ABORTED`; an abort carrying a custom reason (e.g. `dsh-timeout`'s `TimeoutReason`) surfaces as `WEB_PROVIDER_ERROR`.

View File

@@ -51,7 +51,7 @@
#### Token 影响
注册不会直接产生会话 token。答案与源 token 取决于数据,源数量受 seam 限制保留的结果或错误会重复发送直到发生压缩compaction
注册不会直接产生会话 token。答案与源 token 取决于数据,源数量受服务限制保留的结果或错误会重复发送直到发生压缩compaction
#### KV Cache 影响
@@ -61,5 +61,5 @@
- **引用回退源只含 URL**Perplexity 省略结构化 `search_results[]` 时,源不含 `title``snippet``publishedAt`,因此工具只渲染纯主机名标签。
- **超量返回的来源仍会增加 token 消耗和延迟**:协议没有结果数量控制,`maxResults` 只能由 seam 在事后截断。
- **只公开 `model``maxTokens``searchRecency`**Perplexity 的其他搜索控制项(域名过滤条件、`web_search_options` 上下文大小、图片)等待提供方无关 seam 字段(见 [seam Agent Note](../../../.agents/notes/implemented/architecture/2026-06-24-web-capability-seam.md))。
- **只公开 `model``maxTokens``searchRecency`**Perplexity 的其他搜索控制项(域名过滤条件、`web_search_options` 上下文大小、图片)等待提供方无关的 Service Definition 字段(见 [seam Agent Note](../../../.agents/notes/implemented/architecture/2026-06-24-web-capability-seam.md))。
- **按错误形状分类中止**:只有 `DOMException` 且名为 `AbortError` 时才映射为 `WEB_ABORTED`;携带自定义原因的中止(例如 `dsh-timeout``TimeoutReason`)会呈现为 `WEB_PROVIDER_ERROR`

View File

@@ -2,5 +2,5 @@
# side as of the last confirmed-consistent state. Both languages carry equal authority;
# after editing either side, bring the other along and re-record with:
# pnpm run verify-translation-pairing --write packages/web/web/README.md
README.md: c05965478a049b4145a94075e42bd9602675628f
README.zh.md: 686157cc87ff456ccc535e3f92fd6524758b35f4
README.md: 22301a144b2e06ab42e1d503e8f8c554f7886330
README.zh.md: 027b863cd7835f378de5f5c5d41166938b8cfe1a

View File

@@ -4,15 +4,15 @@ English | [中文](README.zh.md)
The **`WebService`** (`ctx.web`) defines WHAT web access the harness has — search the web, fetch a URL — over multiple providers, without binding the model contract to one vendor's API shape.
This package is the interface third of the web capability. Unlike bash/fs it spans two capabilities (search and fetch) on one seam, with potentially multiple providers each:
This package owns the Service Definition role of the web capability. Unlike bash/fs it spans two operations (search and fetch) on one seam, with potentially multiple providers each:
| Package | Role |
|---|---|
| `@deepseek-ai/dsh-web` (this) | the interface: the service, provider registries, selection policy, request/result vocabulary, the `WebError` taxonomy |
| `@deepseek-ai/dsh-web-search-exa` | a search implementation: Exa |
| `@deepseek-ai/dsh-web-search-perplexity` | a search implementation: Perplexity |
| `@deepseek-ai/dsh-web-fetch-local` | a fetch implementation: anonymous public HTTP(S) |
| `@deepseek-ai/dsh-tool-web` | the model-facing `web_search` / `web_fetch` tool schemas over `ctx.web` |
| `@deepseek-ai/dsh-web` (this) | Service Definition: the service, provider registries, selection policy, request/result vocabulary, the `WebError` taxonomy |
| `@deepseek-ai/dsh-web-search-exa` | Search provider: Exa |
| `@deepseek-ai/dsh-web-search-perplexity` | Search provider: Perplexity |
| `@deepseek-ai/dsh-web-fetch-local` | Fetch provider: anonymous public HTTP(S) |
| `@deepseek-ai/dsh-tool-web` | Consumer: the model-facing `web_search` / `web_fetch` tool schemas over `ctx.web` |
Search and fetch share no request schema and no business logic, but they are deliberately one seam: `ctx.web` is a single web-access middle layer with one provider-selection policy owner, one abort/error vocabulary, and one product-facing "how this harness reaches the web" config surface. The cost is the parallel `Search`/`Fetch` method pairs; that parallelism is intentional, not a missed extraction.
@@ -58,4 +58,4 @@ No direct invalidation; the named consumer owns any request-prefix changes.
- **No observation surface** — no provider-change event and no capability-status query; availability is observed only by executing `search()`/`fetch()` and routing the thrown `WebError` codes, and the no-provider failure is the generic `WEB_PROVIDER_UNAVAILABLE` with no per-provider reason enumeration ([Agent Note](../../../.agents/notes/archived/simplification/2026-07-04-drop-unconsumed-web-observation-surface.md)).
- **`WebSearchRequest` carries only `query` + `maxResults`** — provider-neutral controls (recency, domain filters, regional hints, search depth) are deferred until Exa and Perplexity can both honor them honestly ([seam Agent Note](../../../.agents/notes/implemented/architecture/2026-06-24-web-capability-seam.md)).
- **`WebFetchBody` has no `pdf` arm** — text-extractable PDF support is named deferred work; the closed union makes adding it a compile-enforced change across the three web packages.
- **Provider-backed page extraction is out of scope of `fetch()`** — a Firecrawl/Tavily-style `web_extract` capability is deferred rather than widening the fetch seam.
- **Provider-backed page extraction is out of scope of `fetch()`** — a Firecrawl/Tavily-style `web_extract` capability is deferred rather than widening the fetch operation.

View File

@@ -2,17 +2,17 @@
[English](README.md) | 中文
**`WebService`**`ctx.web`)定义 harness 具备哪些 web 访问能力(搜索 web、抓取 URL并通过多个提供方实现不把模型约绑定到某个厂商的 API 形状。
**`WebService`**`ctx.web`)定义 harness 具备哪些 web 访问能力(搜索 web、抓取 URL并通过多个提供方实现不把模型约绑定到某个厂商的 API 形状。
该包是 web 能力中负责接口的三分之一。与 bash/fs 不同,它在一个 seam 上跨越搜索与抓取两种能力,每种能力都可能有多个提供方:
本包承担 web 能力的 Service Definition 角色。与 bash/fs 不同,它在一个 seam 上跨越搜索与抓取两种操作,每种操作都可能有多个提供方:
| 包 | 职责 |
|---|---|
| `@deepseek-ai/dsh-web`(本包) | 接口:服务、提供方注册表、选择策略、请求/结果词汇、`WebError` 分类体系 |
| `@deepseek-ai/dsh-web-search-exa` | 搜索实现Exa |
| `@deepseek-ai/dsh-web-search-perplexity` | 搜索实现Perplexity |
| `@deepseek-ai/dsh-web-fetch-local` | 抓取实现:匿名公共 HTTP(S) |
| `@deepseek-ai/dsh-tool-web` | 面向模型的 `web_search``web_fetch` 工具 schema构建于 `ctx.web` 之上 |
| `@deepseek-ai/dsh-web`(本包) | Service Definition:服务、提供方注册表、选择策略、请求/结果词汇、`WebError` 分类体系 |
| `@deepseek-ai/dsh-web-search-exa` | 搜索提供方Exa |
| `@deepseek-ai/dsh-web-search-perplexity` | 搜索提供方Perplexity |
| `@deepseek-ai/dsh-web-fetch-local` | 抓取提供方:匿名公共 HTTP(S) |
| `@deepseek-ai/dsh-tool-web` | Consumer面向模型的 `web_search``web_fetch` 工具 schema构建于 `ctx.web` 之上 |
搜索与抓取没有共享请求 schema 或业务逻辑,但有意共用一个 seam`ctx.web` 是单一 web 访问中间层,拥有一项提供方选择策略、一套中止/错误词汇和一个面向产品的「该 harness 如何访问 web」配置接口。代价是成对的并行 `Search``Fetch` 方法;这种并行是有意设计,并非遗漏了可抽取的共性。
@@ -58,4 +58,4 @@
- **没有观测接口**:没有提供方变更事件或能力状态查询;可用性只能通过执行 `search()``fetch()` 并按抛出的 `WebError` code 路由来观测,无提供方失败是通用的 `WEB_PROVIDER_UNAVAILABLE`,不会枚举逐提供方原因(见 [Agent Note](../../../.agents/notes/archived/simplification/2026-07-04-drop-unconsumed-web-observation-surface.md))。
- **`WebSearchRequest` 只携带 `query` + `maxResults`**:提供方无关的控制项(新近程度、域名过滤条件、区域提示、搜索深度)暂缓至 Exa 与 Perplexity 都能诚实支持时(见 [seam Agent Note](../../../.agents/notes/implemented/architecture/2026-06-24-web-capability-seam.md))。
- **`WebFetchBody` 没有 `pdf` 分支**:可提取文本的 PDF 支持属于明确的暂缓工作;封闭联合会使新增该分支成为三个 web 包中由编译强制执行的变更。
- **提供方支持的页面提取不属于 `fetch()` 范围**Firecrawl/Tavily 风格的 `web_extract` 能力暂缓,而不会扩展抓取 seam
- **提供方支持的页面提取不属于 `fetch()` 范围**Firecrawl/Tavily 风格的 `web_extract` 能力暂缓,而不会扩展抓取操作

View File

@@ -1,5 +1,5 @@
/**
* The web access seam (`ctx.web`): registries and provider-selecting execution for search and
* Service Definition for the web access capability seam (`ctx.web`): registries and provider-selecting execution for search and
* fetch. Duplicate ids are rejected. At execution time, a configured provider must exist and
* be usable; without one, exactly one usable provider is required, so selection never depends
* on registration order.