yu2025-luo
dsh-file-panel
Right-side file panel for DeepSeek Harness — auto-popup when the agent creates or downloads files, with image/text preview, reveal-in-folder and open actions. Bilingual · MIT
- Stars
- 2
- Language
- JavaScript
- Created
- Aug 14, 2026
- Updated
- Aug 14, 2026
Introduction
dsh-file-panel
A plugin for DeepSeek Harness (dsh web GUI) that watches what the agent creates and downloads during a session, and shows it in a right-side popup panel — like the file viewer in Codex.
When a file or image is written to disk during a session, the panel pops up automatically on the right. Every row lets you:
- 👁 Preview — images render inline; text files show their first 256 KB; other types show metadata.
- 📂 Show in folder — opens the OS file manager with the file selected (
explorer.exe /selecton Windows,open -Ron macOS,xdg-openon Linux). - ↗ Open — opens the file with the OS default application (via the harness's built-in
host.openPathRPC). - 📋 Copy path — copies the absolute path to the clipboard.
Also ships a workspace folder shortcut at the bottom of the panel.
Screenshots
Add screenshots after running it locally (see Development).
Installation
Requires DeepSeek Harness dsh CLI (npm package @deepseek-ai/dsh) and pnpm.
From a local checkout
cd dsh-file-panel
npm install # installs esbuild (dev-only)
npm run build # produces lib/index.js + lib/client.js (committed)
# register in the web profile (link: tracks your checkout live)
dsh plugin --profile web add link:.
From GitHub
dsh plugin --profile web add github:yu2025-luo/dsh-file-panel
The built artifacts are committed, so no build step runs during install.
Activate
Restart the dsh web server (plugin sets take effect on restart), then refresh
http://127.0.0.1:3080. That's it — no configuration required.
Remove with:
dsh plugin --profile web remove dsh-file-panel
Usage
| Gesture | Result |
|---|---|
| Agent creates/downloads a file | Panel pops up automatically (newest files carry a NEW chip) |
| Click a row | Inline preview (image / text / metadata) |
| Row hover actions | Preview, open, show in folder, copy path |
| 🔔 bell | Toggle auto-pop for new files |
– / × | Collapse to a floating launcher button (with new-file badge) or hide |
| Bottom "open workspace folder" | Opens the session's working directory |
Panel state (open/collapsed) and the auto-pop preference persist in
localStorage. The auto-pop baseline is per session: files that already
existed when the panel first saw the session do not re-trigger a popup.
How it works
One npm package with two halves, registered as a single loader row
(cordis.patch.yml → row file-panel):
Host half (src/index.js) Browser half (src/client.jsx)
──────────────────────── ──────────────────────────────
ctx.on('fs/observed') ──┐
write/edit tools report │ shell.overlay slot entry:
files (precise, attributed │ a right-docked floating panel
to the session) ├──▶ FileTracker (per-session lists,
recursive fs.watch per │ ignore rules, caps, fence)
session working directory │ │
(catches shell downloads: ──┘ ▼
curl, Invoke-WebRequest, …) RPC channel /file-panel
authority: 'loopback'
list · readText · readImage
reveal · describe
▲
│ poll every 1.5 s
client: ctx.connection.rpc.call()
open file: built-in api.host.openPath
The client half registers into the shipped shell.overlay slot (additive,
frame-wide floating layer), reads the current session through the standard
useSessions prop, and polls the plugin's own loopback-only RPC channel.
The channel is registered with ctx.connection.rpc.handle, the sanctioned
static-package RPC seam.
Security
- The
/file-panelchannel is registered withauthority: 'loopback', so only pages served from127.0.0.1can call it. When the GUI is accessed over the network (--trusted-host), the panel shows a notice and stays inactive. - Every read/reveal endpoint only accepts absolute paths that the tracker has actually seen (a tool write or a watcher event under a watched working directory) — the RPC can never be used as a generic file-read/reveal primitive.
Project layout
src/
index.js host half: tracker wiring + /file-panel RPC endpoints
tracker.js pure-Node file tracker (fs/observed ingestion, recursive
watcher with debounce, ignore rules, caps, RPC fence)
client.jsx browser half: the right-side panel UI (React, JSX)
build.mjs esbuild build for both halves
cordis.patch.yml the bundle patch inserting the loader row
tests/ node:test unit + host-half smoke tests
lib/ built artifacts (committed, so installs need no build step)
Development
npm install
npm run build # rebuild lib/index.js and lib/client.js
npm test # node --test
For a fast client-side iteration loop after changing src/client.jsx:
npm run build
then hard-refresh the GUI page (lib/client.js is served with
cache-control: no-cache; plugin sets only change on restart, but bundle
content re-hashes per request — see dsh-client-modules). During active
UI development you can also run pnpm run dev:web from the harness checkout
to rebuild client bundles on change.
Compatibility
Built against the public seams of @deepseek-ai/dsh 0.1.0-rc.x:
- host:
ctx.connection.rpc.handle/ctx.on('fs/observed') - client:
shell.overlayslot,useSessionsstandard prop,ctx.connection.rpc.call,ctx.locale
DeepSeek Harness is pre-release: those seams may move. If the panel stops
working after a dsh upgrade, check the pinned version in
package.json and re-run the build.
Known limitations
- The recursive watcher uses
fs.watch({ recursive: true })(Node ≥ 20). On platforms where that is unavailable, the panel still tracks everything the harnesswrite/edittools produce, but shell-side downloads may be missed. - The panel is process-local: it starts empty after a restart (it only records files it actually observed; it does not scan history).
node_modules,.git, and temporary-file noise are ignored by design.revealon headless Linux reportscanReveal: falseand hides the button (no desktop to open).
Publishing to GitHub / npm
-
Create a GitHub repo and push (the repo is already a git repository with a
v0.1.0tag):git remote add origin https://github.com/yu2025-luo/dsh-file-panel.git git push -u origin main --tags -
Add the
dsh-plugintopic on the repo page (About → gear icon → Topics) together withdeepseek-harness,dsh,deepseek, andfile-preview. The repo then appears on the public plugin topic page automatically. -
Users install with
dsh plugin --profile web add github:yu2025-luo/dsh-file-panel#v0.1.0. -
Optionally publish to npm (
npm publish) — then install withdsh plugin --profile web add dsh-file-panel.
Community catalogs that sync from the dsh-plugin topic:
Oh-My-DSH (auto-synced) and
awesome-deepseek-harness
(PR-based).
Remember to bump the version and re-run npm run build before releasing.