KexinCC/dsh-kimi-assemble

dsh-kimi-assemble

Native DSH tools for the Kimi browser extension (your real, signed-in Chrome) and KimiCU Windows desktop control. 17 tools, verified actions, diff reads, zero dependencies.

미분류windows

dsh-kimi-assemble

Native DeepSeek Harness tools for two Kimi bridges that run on your own machine:

Capability · Backend · Tools Drive your real, logged-in browser · Kimi browser extension daemon (WebBridge, 127.0.0.1:10086) · kimi_browser_* Observe and operate real Windows windows · KimiCU native agent (.\pipe\kimi-cu-win-) · kimi_cu_* Diagnose both · — · kimi_status

Once installed the model does not need to read a skill, shell out to curl, or write a node-repl js cell — it calls tools. UTF-8 survives end to end, a bad argument names the exact field, and a connection failure comes with the next step.

Install

Read this first: what you must already have

This plugin is a bridge, not a bundled implementation. It drives two Kimi components that live on your machine; without them the tools answer KIMI_WEBRIDGE_DOWN / KIMI_CU_NOT_INSTALLED on every call — with install instructions attached, because a plugin must not download and execute remote installers by itself.

You want… · You need · How to get it browser control · Chrome or Edge + the Kimi browser extension. The local-Agent path needs no Kimi account (only the sidebar does). · 1) install the "Kimi" extension from the Chrome Web Store or Edge Add-ons (or the manual install); 2) open the extension sidebar → Settings → “本地 Agent 远程控制” → click 去连接 / Connect; 3) copy the install command shown in that dialog into a terminal and run it — this installs the local daemon under ~/.kimi-webbridge. FAQ desktop control · Windows + the KimiCU runtime (kimi-cu.exe) · download and run setup_windows.cmd in a terminal, or set kimicuExePath in the config to an existing copy either · DeepSeek Harness >= 0.2.0 (verified on 0.2.1-rc.2), Node >= 22 · —

Only want the browser half? Set kimicuEnabled: false — the five kimi_cu_* tools then never register, on any OS.

A fresh machine is wired once kimi_status reports both bridges as installed; after that the plugin discovers, starts and reconnects to both components automatically (including clearing a stale daemon pid file left by an unclean shutdown).

Install from npm (simplest):

plugin_manager install_bundle  target=dsh-kimi-assemble@1.1.0

Or from the plugin market: add this index URL under Discover → index sources, then install the plugin from there:

https://raw.githubusercontent.com/KexinCC/dsh-kimi-assemble/main/market/index.json

Or clone and install the checkout directly (no registry involved):

git clone https://github.com/KexinCC/dsh-kimi-assemble.git
plugin_manager install_bundle  target=<absolute path to that clone>

Either way, cordis_inspect_query(Tool.listTools) should then list 17 kimi_* tools.

Let an agent install the prerequisites

A preflight script ships with the package. It prints what is missing and, with --json, a machine-readable list of next actions (kind: "run" = a command an agent may execute; kind: "user" = only a human can do it).

# no install needed — runs straight from the registry
# after the plugin is installed in your DSH profile, run it from there:
node "%USERPROFILE%\.dsh\profiles\desktop\node_modules\dsh-kimi-assemble\scripts\doctor.mjs"

# or install the package once and use the bin:
npm i -g dsh-kimi-assemble && kimi-assemble-doctor

# same command with machine-readable output
kimi-assemble-doctor --json

Exit codes: 0 both bridges ready · 2 something needs a human · 3 only the desktop runtime is missing (and it can be installed).

What an agent can do on its own

Piece · Automatable? · How KimiCU runtime (Windows desktop half) · yes, with explicit consent · kimi-assemble-doctor --install-desktop downloads setup_windows.cmd from cdn.kimi.com, runs it, then re-checks Starting the local WebBridge daemon · yes · kimi-assemble-doctor --start, or the plugin starts it on first use Kimi browser extension (Chrome/Edge) · no · it is a browser-store extension; only the user can add it WebBridge local service under ~/.kimi-webbridge · no · there is no public installer URL (verified: every guessed cdn.kimi.com/…/setup_* path answers 403). The only source is the install command the extension shows in *Settings → local agent remote control → Connect*

So the loop for an agent is: run the doctor → if it says kind: "user", hand those exact steps to the human (install the extension, click Connect, run the command the dialog shows) → re-run the doctor until exit 0.

Safety

  • The plugin never downloads or executes an installer by itself. --install-desktop is opt-in, prints

the URL it is about to fetch, and runs the script with the user watching.

  • Nothing here needs an API key, an account, or admin rights; KimiCU may show its own UAC prompt.

Coming from the old KimiCU MCP? Disable that row. It exposes mcp__kimicu__js / js_reset / js_add_node_module_dir; this plugin covers all 16 KimiCU methods, so keeping both only adds a second path competing for real desktop input:

# in <profile>/cordis.patch.yml, on the existing mcp-kimicu row:
- id: mcp-kimicu
  name: "@deepseek-ai/dsh-mcp-client"
  config: { ... }          # keep the existing config
  disabled: true

Configure

config is replaced wholesale (loader semantics, not a deep merge). Write only the keys you want to change; everything else falls back to the defaults.

Key · Default · Meaning webbridgeEnabled · true · when false, no browser tools are registered webbridgeAddr · '' · empty = read ~/.kimi-webbridge/daemon.addr, else 127.0.0.1:10086 webbridgeAutoStart · true · start the daemon idempotently when it is unreachable webbridgeTimeoutMs · 60000 · per browser action browserGroupTitle · DSH · default tab group title, visible in the user's browser browserReadMaxChars · 20000 · default kimi_browser_read budget browserVerify · auto · auto = verify that each action changed the page; off = fire-and-forget (rollback switch) browserVerifyMs · 600 · how long to watch for a change before reporting "unchanged" (100–10000) browserReadIncludeMeta · true · attach the page-state line (url / load / scroll / focus / counts) to reads kimicuEnabled · true · when false, no desktop tools are registered kimicuExePath · '' · empty = KIMI_CU_WINDOWS_EXE → KIMI_CU_WINDOWS_HOME → %LOCALAPPDATA%\Kimi Computer Use\kimi-cu.exe → legacy KimiCU directory kimicuAutoStart · true · start the agent idempotently when it is unreachable kimicuTimeoutMs · 120000 · per desktop call cuMaxTreeChars · 12000 · default accessibility-tree truncation promptSection · true · contribute the system-prompt section registerSkills · true · register the kimi-webbridge / kimi-cu runtime skills (they shadow the older curl/js-cell skills) language · "auto" · auto → Chinese when the system locale is zh*, else English; en / zh force one disabledTools · [] · tool names to drop (e.g. ["kimi_cu_launch"])

Tool descriptions are always English — they are part of the model-facing tool catalog. language controls the text a human sees: error messages, tool output, the prompt section and the skill bodies.

Tools

Diagnosis

  • `kimi_status {deep?}` — the live state of both bridges (daemon address/version/extension

connection, CU exe/version/agent pid/pipe/permissions) plus hints[] with the concrete next step. First stop after any connection failure.

Browser

  • `kimi_browser_open {url, new_tab=true, wait_until=load|domcontentloaded|none, group_title?, session?}`

→ final URL / title / tabId / page state. Waits for load by default so the next action does not race the page.

  • `kimi_browser_read {mode=read|find|frame|diff, include_meta?, include_screenshot?, ref?, max_chars?, cursor?}`

→ accessibility tree text (with [ref=eNNN]), a page-state line (url / load state / scroll / focused element / element counts), search hits, iframe text, or only what changed since the previous read (mode=diff, typically ~4% of the full payload).

  • `kimi_browser_click {selector, verify?, session?}` — CSS or @eNNN / eNNN / [ref=eNNN].

Reports changed / changeDetail; a stale ref is re-read and retried once.

  • `kimi_browser_fill {selector, value, submit=false, verify?, session?}` — reports whether a

→ submit=true commits for you: it clicks the form submit button (falling back to requestSubmit(), Esc + click, then Enter) and reports submitStrategy. This extension cannot produce real key events, so implicit Enter-to-submit never happens. submit=true Enter actually changed the page (suggestion dropdowns swallow it).

  • `kimi_browser_act {verb, ...}` — press, type, clear, select, check, uncheck, hover,

scroll, drag, mouse_click, upload, each verified, with optional wait_for.

  • `kimi_browser_wait {text|text_gone|selector|url|ready|ms, timeout_ms?}` — wait for a condition

instead of re-reading in a loop; on timeout it returns the current page state.

  • `kimi_browser_eval {code, max_chars?}` — evaluate page JS, JSON result.
  • `kimi_browser_dialog {action=status|accept|dismiss, text?}` — native dialogs freeze the page;

click/fill/act report dialogOpen instead of failing, and this answers them.

  • `kimi_browser_screenshot {selector?, full_page=false, format=png|jpeg, quality?, session?}` →

an image block (a path when the model route has no image input)

  • `kimi_browser_tabs {action=list|list_all|attach|close|close_session, tab_id?}`
  • `kimi_browser_script` — two shapes:
  • single step (escape hatch): {action, args, session?}, covering all 35 daemon actions

(network / upload / pdf / cdp / highlight …)

  • batch: {steps:[{action,args,capture?}], stop_on_error?, max_result_chars?} — 1–25 steps in

one call

  • argument table: references/browser-actions.md

Why actions are verified

Every mutating browser tool reports whether the page actually changed. The extension's click is a DOM-level dispatch: it returns success even when nothing happens, which used to make a wrong click look identical to a right one. browserVerify: 'off' restores the old fire-and-forget behaviour. Measured effect (6 fixtures × 5 runs, see bench/RESULTS.md): silent failures 10 → 0, task success 37% → 100%, at the cost of ~600ms on actions that genuinely do nothing.

Desktop

  • `kimi_cu_windows {filter?, limit?}` → [{id, title, app}]
  • `kimi_cu_observe {window, screenshot=true, text=true, filter?, max_chars?}` →

accessibility tree (with [index]) + focus + screenshot image block + coordinate_space

  • `kimi_cu_act {action, window, ...}` — click (element_index or x/y), type, key,

scroll (`scroll_y > 0` scrolls down), set_value, drag, drag_path, secondary, activate

  • `kimi_cu_launch {app}`
  • `kimi_cu_script` — two shapes:
  • single step: {action, window, ...}, or {action:"call", args:{method,args}} for any of the

16 KimiCU methods (open_panel, list_apps, …)

  • batch: {steps:[...], stop_on_error?, settle_ms?, max_result_chars?} — 1–30 steps **inside one

input lease**; step actions are the 9 input actions above plus windows / observe / launch / wait_window / sleep / call; a later step can address the n-th window of the previous windows step with window:"@n"

  • argument table: references/computer-api.md

Performance: the plugin is fast, the model rounds are the cost

Measured with node test/bench.mjs on the development machine:

Layer · Measured · Meaning HTTP health check / status (cached) · 0.0–2.1 ms · plugin overhead HTTP snapshot / list_tabs / evaluate · 4–10 ms · plugin overhead CU ping / list_windows / get_window · 0.5–2.7 ms · plugin overhead CU lease begin+end · 0.3 ms · negligible browser navigate · ~206 ms · page load — the daemon's job browser screenshot · ~144 ms · Chrome capture CU get_window_state, text only · ~82 ms · UIA tree walk CU get_window_state, with screenshot · ~217 ms · UIA + WGC capture one model round · seconds · the real cost

Local execution is 0.5–220 ms; a model round is seconds. So the optimisation is more work per call, not a faster transport. That is what the batch scripts are for: one tool call is one model round, and six browser steps that used to cost six rounds now finish inside a single 0.6 s call.

Why it does not go wrong

  1. No shell. Browser requests are node:http with a UTF-8 buffer inside the Host process.

Inline JSON through a shell corrupts non-ASCII text on Windows (measured: the daemon answers invalid JSON) — that path was removed.