kenzone
dsh-anysearch
An AnySearch-backed WebSearchProvider plugin for DeepSeek Harness (ctx.web). It calls AnySearch's MCP-style POST /mcp JSON-RPC endpoint with the search tool and parses the rendered Markdown result blocks into the harness web capability seam's normalized WebSearchResult.
- Stars
- 0
- Language
- TypeScript
- Created
- Aug 15, 2026
- Updated
- Aug 15, 2026
Introduction
dsh-anysearch
An AnySearch-backed WebSearchProvider plugin for DeepSeek Harness (ctx.web). It calls AnySearch's MCP-style POST /mcp JSON-RPC endpoint with the search tool and parses the rendered Markdown result blocks into the harness web capability seam's normalized WebSearchResult.
Features
- Web search for the harness
web_searchtool through the AnySearch API - No API key required — anonymous access works at lower rate limits; the provider stays available either way
- Settings card in the official Web GUI — configure the API key and endpoint under Settings → Plugins → AnySearch
- Credential-first key handling — keys go through the credentials domain, never into the settings file
- Vertical search support —
finance,code, and other AnySearch domains via static config - Per-search re-resolution — a changed key or endpoint takes effect on the next search, no restart
This is an implementation plugin: it registers a provider into ctx.web, it does not own the ctx.web key and it does not register a model-facing tool (that is @deepseek-ai/dsh-tool-web). It is a function/namespace plugin (inject: ['web']) that registers its backend, not a default-export service.
Requirements
- DeepSeek Harness 0.1.0-rc.6 or newer (the
@deepseek-ai/dsh-*peer packages this plugin targets are published on npm at0.1.0-rc.6).
Install
From a DeepSeek Harness profile (e.g. web):
dsh plugin --profile web add dsh-anysearch
Then route the model-facing web_search tool through the AnySearch provider by editing the profile's cordis.patch.yml:
- id: web
config:
searchProvider: anysearch
- insert:
- id: web-search-anysearch
name: 'dsh-anysearch'
The official Web GUI ships an AnySearch settings card (Settings → Plugins → Plugin configuration), which appears once the plugin is installed and exposes the API key and endpoint for configuration.
API key
- Create a free key at https://anysearch.com/console/api-keys.
- Configure it in the Web GUI (Settings → Plugins → Plugin configuration → AnySearch → API key), or export
ANYSEARCH_API_KEYin the launch environment, or write it to$DSH_HOME/.env. - Restart
dsh webif you changed the environment (the launch environment is a frozen boot-time snapshot).
Without a key the provider works anonymously at lower rate limits.
Config
| Key | Default | Meaning |
|---|---|---|
apiKey | (unset) | Literal AnySearch API key; prefer apiKeyEnv so no secret enters configuration files. Empty/absent → anonymous access (lower rate limits); the provider stays available either way. |
apiKeyEnv | ANYSEARCH_API_KEY | Credential reference resolved for each search through the credentials domain, falling back to the launch environment (process > project .env > $DSH_HOME/.env). |
baseURL | https://api.anysearch.com | Endpoint base; /mcp is appended. An unparseable value makes the provider unavailable. |
domain | (unset) | Optional vertical-domain name (finance, code, …); sent as AnySearch's domain. Pairs with subDomain. |
subDomain | (unset) | Optional vertical sub-domain; sent as AnySearch's sub_domain. Requires domain. |
subDomainParams | (unset) | Optional structured parameters required by a chosen sub-domain; sent as AnySearch's sub_domain_params. |
numResults | (unset) | Default result count when a request carries no maxResults. Unset sends no default. Must be a positive integer. |
- id: web-search-anysearch
name: 'dsh-anysearch'
config:
apiKeyEnv: ANYSEARCH_API_KEY
The plugin also installs its settings section (web-search-anysearch), which the Web client's Plugins page exposes as the AnySearch card: the key is written through the credentials domain (never into the settings file) and the endpoint can be overridden there. A section edit takes effect on the next search without a restart.
How it works
AnySearch's search tool returns rendered Markdown, not structured JSON, so this provider parses the result blocks (### N. title, - **URL**: url, then snippet lines) into WebSearchSources: url ← the URL line, title ← the numbered heading, snippet ← the folded body lines. A heading without a following URL line is dropped (nothing citeable), and the title is optional because a block may render without one. AnySearch returns no generated answer, so content is omitted. A request's maxResults wins over the configured numResults default and is capped at the API's limit of 10 before being sent as AnySearch's max_results; the final bound is enforced by the seam. Provider failures (HTTP errors, tool isError, network failure, unparseable or wrong-shape bodies) surface as WebError WEB_PROVIDER_ERROR; an aborted request surfaces as WEB_ABORTED. HTTP redirects are rejected before the Location target is contacted and surface as WEB_PROVIDER_ERROR.
Development
npm install
npm run typecheck
npm test
npm run test:e2e # live API smoke (anonymous access)
npm run build
Publishing
npm run build
npm test
npm publish
The package is MIT-licensed. Add the dsh-plugin topic to this GitHub repository so it appears in the DeepSeek Harness community plugin list.