Direct web search button and /search slash command plugin for DeepSeek Harness.
Install
# from GitHub (first run asks for allowBuilds approval — follow the hint, retry)
dsh plugin --profile web add github:swenbo1-web/dsh-web-search-button
Any plugin you install runs third-party code with your own permissions — it can read your files, use your credentials, and reach the network, and tool approvals don’t sandbox it. GitHub-sourced plugins also run build scripts at install time — pnpm blocks those until you allow them, so an install can stop with ERR_PNPM_GIT_DEP_PREPARE_NOT_ALLOWED or ERR_PNPM_IGNORED_BUILDS; dsh prints the exact key to add under allowBuilds in your profile’s pnpm-workspace.yaml, and the install works on the next run. Allowing a build is a trust decision: only install sources you trust, and pin a commit (github:owner/repo#sha).
README
Direct web search button and /search host-level slash command plugin tailored for DeepSeek Harness (DSH) Desktop.
This plugin allows you to directly invoke the built-in host-level web search service (ctx.web) from the conversation input bar without routing through the LLM, returning real-time web search results formatted with titles, snippets, dates, and markdown source links with 0 Token overhead in ~1 second!
🎯 Why This Plugin?
- Overcome Knowledge Cutoffs Instantly
All LLMs have knowledge cutoffs. Standard agent search requires prompting the model, waiting for multi-step reasoning, invoking tools, and synthesizing output—often failing due to prompt drift or proxy instability. - Zero LLM Overhead
- Traditional Agent flow: User prompt ➔ Model thoughts ➔ Call
web_searchtool ➔ Wait for tool result ➔ Model summarizes. Costs thousands of tokens and 10–20 seconds. - This Plugin flow: User prompt ➔ Click button ➔ Direct host execution of DeepSeek Web Search ➔ Results injected immediately. Takes ~1 second, consumes 0 LLM tokens!
- Traditional Agent flow: User prompt ➔ Model thoughts ➔ Call
- Seamless Native UI Integration
Mounts cleanly in the input bar left slot (conversation.input.left), matching DSH--dsw-*design tokens, supporting dark/light mode, live draft detection, and loading states. - Solving Model Laziness & Hallucination (Why a Persistent Toggle?)
“If some agent models can occasionally invoke search on their own, why is a dedicated toggle switch needed?”- Eliminating Cognitive Overconfidence: Without explicit constraints, LLMs frequently hallucinate answers based on outdated pre-training cutoff data instead of actively initiating web retrieval.
- 100% Deterministic Behavioral Constraint: Switching to the 【Lit Up】 state injects a strict system-level prompt constraint, ensuring the model MUST search the web before answering any temporal, factual, or technical query.
- Frictionless Control: Click again to 【Dim】, instantly reverting to normal conversational mode without disrupting text input.
🖥️ UI Mockup
┌─────────────────────────────────────────────────────────────────────────────────┐
│ │
│ User: /search Latest AI model announcements 2026 │
│ │
│ 🌐 **Web Search Results** (Direct Web Tool Execution): │
│ Query: `Latest AI model announcements 2026` │
│ │
│ ### Sources: │
│ 1. [Gemini 3.8 Flash Launch](https://...) (2026-09-02) │
│ > Google officially releases Gemini 3.8 Flash with tool improvements... │
│ 2. [Claude Fable 5.1 Overview](https://...) (2026-06-09) │
│ > Anthropic introduces Fable 5.1 optimized for coding agents... │
│ │
├─────────────────────────────────────────────────────────────────────────────────┤
│ Input: Latest AI model announcements 2026 │
│ │
│ [+] [Standard Mode ▾] [ 🌐 Web Search ] [ Send ⬆]│
│ ▲ │
│ Plugin Search Button │
└─────────────────────────────────────────────────────────────────────────────────┘
✨ Key Features
- 🌐 Dedicated Composer Button: Mounts directly into the DSH conversation input bar via
conversation.input.leftlist slot. - ⚡ Dual Invocation Modes:
- Button Trigger: Detects current composer draft text and dispatches search on click.
- Slash Command: Type
/search <keyword>directly into the input bar and press Enter.
- 🛡️ Pure Cordis Scope Lifecycle:
- Built with
ctx.inject(["slots", "remote.commands", "sessions"], (scope) => ...). - Automatic unmounting and cleanup on plugin reload (HMR) or disable, preventing memory leaks or orphaned DOM nodes.
- Built with
- 🎨 Native Design Tokens: Built with official
--dsw-*CSS variables, perfectly adapting to theme changes.
🏗️ Architecture & Data Flow
【 Client Plane (Browser Window) 】 【 Host Plane (Node Engine) 】
Composer draft: "Latest AI news"
│
(Click 🌐 Button)
│
Read zone.input.draft
│
Via remote.commands channel
Dispatch: "/search Latest AI news" ─────────► Matches ctx.commands("search")
│
Directly calls host service:
ctx.web.search({ query, maxResults: 8 })
│
Formats Markdown & sources
│
Markdown source card injected directly ◄────────────────── Injects into session
into conversation without LLM overhead (command/done)
📂 Project Structure
dsh-web-search-button/
├── src/
│ ├── index.ts # Host-plane TypeScript source (registers /search command)
│ └── client/
│ └── index.tsx # Client-plane TSX source (SearchButton component & scope injection)
├── lib/
│ ├── index.js # Production Host ESM bundle
│ └── client.js # Production Client bundle (wrapped with window.__ModuleLoader__.load)
├── cordis.patch.yml # DSH bundle patch manifest
├── package.json # DSH manifest (dsh.bundle.patch & dsh.client configurations)
├── tsconfig.json # TypeScript build configuration
├── LICENSE # MIT License
├── README.md # English documentation
└── README.zh.md # Chinese documentation
🚀 Installation
Step 1: Clone or Download to Local Disk
git clone https://github.com/swenbo1-web/dsh-web-search-button.git D:/deepseek/dsh-web-search-button
Step 2: Register in DSH Web Profile
DSH Desktop active profile is located at %APPDATA%\dsh-desktop\harness\profiles\web.
Create Directory Junction: Run in PowerShell:
New-Item -ItemType Junction -Path "$env:APPDATA\dsh-desktop\harness\profiles\web\node_modules\dsh-web-search-button" -Target "D:\deepseek\dsh-web-search-button"Declare Bundle in
profiles\web\package.json: Open%APPDATA%\dsh-desktop\harness\profiles\web\package.json, ensuredependenciesanddsh.profile.bundlesincludedsh-web-search-button(save as clean UTF-8 without BOM):{ "dependencies": { "dsh-web-search-button": "link:D:/deepseek/dsh-web-search-button" }, "dsh": { "profile": { "bundles": [ "@deepseek-ai/dsh-base", "@deepseek-ai/dsh-web-app", "dsh-web-search-button" ] } } }
Step 3: Restart & Refresh
- Right-click DSH in system tray and select Exit, then relaunch DSH Desktop.
- In DSH chat window, press
Ctrl + F5(hard refresh) to load the updated client bundle. - Check Settings → Plugins to see
dsh-web-search-buttonenabled!
💡 Usage
Mode 1: Composer Toggle Button (Lit Up / Dimmed)
- Open any session; the
[ 🌐 联网搜索 ]button is displayed on the bottom-left of the input bar. - Click once ➔ Directly Lits Up (Bright green/accent background + white text + subtle glow):
- Web Search Mode is ON;
- Zero dialogs, zero alerts, zero prompt confirmations!
- All subsequent messages in this session will automatically invoke
web_searchfor real-time information; - Focus is smoothly preserved on the text box so you can continue typing without interruption.
- Click again ➔ Directly Dims (Neutral/muted background):
- Web Search Mode is OFF, returning to normal chat.
Mode 2: Slash Command
Type slash commands directly into the input bar and press Enter:
/search <keyword> # One-shot direct web search
/search on # Enable persistent Web Search Mode (turns button ON / Lit up)
/search off # Disable Web Search Mode (turns button OFF / Dimmed)
🛠️ Deep Dive: Why scope?
In DSH, registering slots directly on the root context (ctx) can cause timing crashes if dependencies aren't ready, and leaves orphaned listeners on disable.
Our implementation uses scoped dependency injection:
export function apply(ctx: Context) {
// Guarded: Cordis dispatches scope only when slots and remote.commands are ready
ctx.inject(["slots", "remote.commands", "sessions"], (scope) => {
scope.slots.inject("conversation.input.left", () =>
scope.slots.register(
{
name: "conversation.input.left",
id: "web-search-button", // List slots require unique id & order
order: 10,
inject: (sessionId) => ({ ... })
},
SearchButton
)
);
});
}
Binding the button's lifetime to scope ensures clean, garbage-collected unmounting upon reload or disable.
📄 License
MIT © swenbot
Links
More in this category
zhu1090093659/dsh-web#packages/dsh-task-board★ 9673
Task board for the dsh web GUI: a sidebar multi-column kanban whose cards run in real DSH agent sessions and can also be scheduled with cron expressions, executed host-side even with the browser closed.
zhu1090093659/dsh-web#packages/dsh-web-all★ 9673
Plugin and skin collection for the DSH Web UI: task board, Git graph, right-side panel, remote mobile UI, pet, live token stats, and a skin center.
MeteorNOX/DeepSeek-Balance-Whale-Widget★ 6324
A fixed-corner whale widget for the DSH web GUI — balance, today's usage and per-turn cost with peak/off-peak pricing, editable balance-alert and daily-budget bubbles, a module-based custom bubble queue with A/B weighted choices and random lines or images, 30+ vendor templates (OpenAI, OpenRouter, Kimi, SiliconFlow, Ark, Zhipu, MiniMax and more) with per-model balance and subscription quota, plus task-end sound, imported audio, custom roles and a resource manager. Local-only, no telemetry.
ccch1mneyyy/dsh-TUI★ 6018
Claude Code-style full-screen terminal UI: pixel-whale header, live status line, and streaming thought expansion.
omdsh-dev/DSH-better-sidebar★ 4645
Full sidebar workbench with file rendering and editing, terminal, Git, and subagents; third-party plugins can register new tabs.
Devin-AXIS/deepseek-design#deepseek-idesign★ 1607
Visual design studio for websites, app prototypes, posters, cards, reports, and magazines, with templates, direct element editing, selection-aware AI draft handoff, and export.
Community comments
Comments are public GitHub Discussions. Loading them connects to GitHub and Giscus; a GitHub account is required to post.