Back to home@kenny2077

dsh-web-kimi

Kimi Coding web search + web fetch providers for the DeepSeek Harness with coding plan key

Stars
0
Language
TypeScript
Created
Aug 31, 2026
Updated
Aug 31, 2026

Introduction

dsh-web-kimi

One Kimi Coding key, both halves of the web pipeline — web search and web fetch for the DeepSeek Harness.

CI npm version License: MIT

English | 中文

What it is

A DSH plugin that registers two providers into the ctx.web seam:

  • kimi-coding — a WebSearchProvider backed by the Kimi Coding API search endpoint (POST /v1/search). Search results map to the harness's WebSearchSource shape: url, title, snippet, and publishedAt (from the result date).
  • kimi-coding-fetch — a WebFetchProvider backed by the Kimi Coding API fetch endpoint (POST /v1/fetch). Any http(s) URL is extracted server-side — JavaScript rendering included — and returned as clean markdown.

Both halves authenticate with the same credential and read the same settings section, so a key saved once covers every web operation. A dedicated settings card in the GUI stores the key through the DSH credentials service, and a saved value takes effect on the very next search or fetch — no restart.

                 ┌─────────────────────────────────────────────┐
                 │                ctx.web seam                 │
                 ├──────────────────────┬──────────────────────┤
                 │   web_search tool    │    web_fetch tool     │
                 │  WebSearchProvider   │   WebFetchProvider    │
                 │      kimi-coding     │   kimi-coding-fetch   │
                 └──────────┬───────────┴──────────┬───────────┘
                            │  POST /v1/search     │  POST /v1/fetch
                            ▼                      ▼
                 ┌─────────────────────────────────────────────┐
                 │        api.kimi.com/coding/v1               │
                 │        one Bearer key, one subscription     │
                 └─────────────────────────────────────────────┘

Why

The DSH ecosystem already has search aggregators and OAuth bridges; what it lacked was a vendor-native two-seam integration for Kimi. This package brings the coding-plan subscription you already pay for into both web_search routing and web_fetch routing — no per-call search billing, no second account, no aggregator in the middle.

If you already run Kimi Code (the CLI), it is zero-config: the credential chain falls back through your ~/.kimi-code/config.toml and picks the key up on its own.

How it works

  1. Registration — the plugin injects into ctx.web and registers both providers. The bundle overlay selects searchProvider: kimi-coding and fetchProvider: kimi-coding-fetch on install.

  2. Credential resolution (per operation, no restart) — the card's stored value wins, then the credentials service's secondary reference, then the config literal, then the launching environment, then the Kimi CLI config file:

    settings card  →  KIMI_CODING_API_KEY  →  KIMI_API_KEY  →  config apiKey
         →  launch environment  →  ~/.kimi-code/config.toml  →  ~/.kimi/config.toml
    
  3. Request shapingtext_query plus a server-side limit (clamped to the API's 1–20 bound), enable_page_crawling from the toggle, timeout_seconds, and a fresh X-Msh-Tool-Call-Id correlation id on every call.

  4. Hardening — only absolute http(s) URLs are forwarded or surfaced; search response bodies are bounded at 5 MB before buffering; fetch content is capped at 2 MB with a truncated flag. Every failure surfaces as a typed WebError (WEB_PROVIDER_ERROR, WEB_PROVIDER_CREDENTIAL_MISSING, WEB_ABORTED) with the upstream HTTP status preserved in the message.

The web_fetch tool itself stays gated by dsh-tool-web (the harness keeps fetch off by default over SSRF concerns); this package registers the provider and the routing for when you enable it.

Quick start

dsh plugin --profile web add dsh-web-kimi

Then open Settings → Web Search (Kimi) in the DSH web GUI, paste your Kimi Coding API key, and Save. The key lands in the DSH credentials service (~/.dsh/.credentials.yaml) — never in settings.yaml.

No GUI? Any of these works too:

export KIMI_CODING_API_KEY=sk-...        # launching environment
# or: store through the credentials service under KIMI_CODING_API_KEY / KIMI_API_KEY
# or: ~/.kimi/config.toml with api_key = "..."   (Kimi Code CLI users — picked up automatically)

The provider id kimi-coding deliberately matches quei4r/dsh-host-kimi-search, so installing this package is a drop-in replacement for that script, not a duplicate-id conflict.

Settings GUI card

The card covers three fields, all stored under credential references:

FieldTypeStored as
API keypasswordKIMI_CODING_API_KEY
Base URLtextKIMI_SEARCH_BASE_URL
Page crawlingselect (true / false)KIMI_SEARCH_PAGE_CRAWLING
  • A masked input, a "Get an API key ↗" link straight to the Kimi console, and a live configured/not-configured badge that refreshes on save.
  • Leave a field blank to keep its current value; Reset clears all three references.
  • The CLI-config fallback is read-only — this package never writes ~/.kimi/config.toml.

Configuration

Settings section web-kimi (file-based edits of the same fields the card writes):

FieldDefaultMeaning
apiKeyLiteral key; a stored credential-reference value wins over it
apiKeyEnvKIMI_CODING_API_KEYPrimary credential reference
baseURLhttps://api.kimi.com/coding/v1Endpoint base (/search, /fetch appended)
pageCrawlingfalseSend enable_page_crawling so results carry full content
timeoutSeconds30Server-side timeout_seconds

Wire mapping

Kimi /v1/search fieldWebSearchSource
urlurl (required; non-http(s) results dropped)
titletitle (omitted when blank)
snippet, then contentsnippet (first non-blank wins)
datepublishedAt (omitted when blank)
site_name, icon, mimenot mapped

/v1/fetch responses arrive as markdown and map to WebFetchResult { statusCode, body: { kind: 'text' }, truncated } — content past 2 MB is capped and flagged.

Troubleshooting

Every failure carries the HTTP status in its message, which makes most problems one-glance diagnosable:

You seeWhat it meansWhat to do
url.not_foundThe base URL points at a surface without /search — typically the chat API (https://api.moonshot.cn/v1)Set the base URL to https://api.kimi.com/coding/v1; the coding endpoints need a coding credential
Kimi search error (HTTP 401): …The key was recognized but rejected — it is not a Coding credentialUse a Kimi Coding API key, not a chat/API-platform key
Kimi search error (HTTP 403): …The key is valid, but the plan lacks the search/fetch serviceEnable the search/fetch service on the coding plan
… (HTTP 5xx): … / non-JSON bodyUpstream-side faultRetry; the status tells you it is not your config
WEB_PROVIDER_CREDENTIAL_MISSINGNo key resolved anywhere in the chainPaste it in the settings card, store it under KIMI_CODING_API_KEY / KIMI_API_KEY, export it, or put it in ~/.kimi/config.toml
Results carry no contentPage crawling is offTurn on the page-crawling toggle

How it compares

dsh-web-kimidsh-web-search-doubaodsh-web-search-zaiquei4r/dsh-host-kimi-search
Seams filledsearch + fetchsearchsearchsearch
Credentialone coding-plan keyseparate Doubao Search keyreuses ZAI_API_KEYcoding key chain
Settings GUI cardyesyes
CLI-config fallbackyesyes
Typed error taxonomyyesyesyespartial
On npmyesyesyes

Known limitations

  • Entitlement: the coding-plan account must include the search/fetch service; otherwise the endpoint answers 403.
  • content needs crawling: result bodies stay empty unless pageCrawling is on.
  • Fetch tool gating: enable web_fetch in dsh-tool-web to route fetches through this provider.
  • One searchProvider per profile: installing this plugin switches the profile's selection from any previous search plugin; remove it (or override the config) to switch back.
  • No DeepSeek-key fallback (a deliberate divergence from quei4r's chain): a DeepSeek API key would only 401 at api.kimi.com.

Repository architecture

dsh-web-kimi/
├── package.json            # dsh.bundle.patch + dsh.client manifest, exports ./client
├── tsdown.config.ts        # client-half build (ModuleLoader-wrapped browser bundle)
├── cordis.patch.yml        # searchProvider + fetchProvider selection, insert entry
├── src/
│   ├── index.ts            # node entry: Config, credential chain, apply()
│   ├── provider.ts         # KimiSearchProvider + shared headers/abort plumbing
│   ├── fetch-provider.ts   # KimiFetchProvider (the second seam)
│   ├── types.ts            # wire types
│   ├── invariant.ts        # no-op invariant companion
│   └── client/
│       ├── card.tsx        # reusable settings-card factory
│       └── index.tsx       # Kimi instantiation (refs, locales, console link)
├── tests/                  # 79 unit tests across search, fetch, and card suites
└── lib/                    # committed build output — git installs need no build step

Development

pnpm install
pnpm typecheck && pnpm build && pnpm test
  • Node 22.19+ / 24, pnpm 11 — same floor as the harness.
  • The test suites run against a mocked fetch (79 tests); the live smoke in tests/kimi.e2e.ts self-skips without $KIMI_CODING_API_KEY.
  • CI runs the full gate (typecheck, build, test) on Node 22/24 × Ubuntu/Windows on every push and PR.

Credits

The multi-source credential chain (KIMI_CODING_API_KEYKIMI_API_KEY → Kimi CLI config) and the http(s)-only/size-cap hardening originate from quei4r/dsh-host-kimi-search — this package extends that idea to the fetch seam, a settings card, a test suite, and npm distribution. Card architecture follows the verified settings.section/credential-reference conventions of the sibling DSH search plugins.

License

MIT