DSH Markdown Previewer / DSH Markdown 预览器
DSH web GUI client plugin: sidebar Markdown preview — browse, render, edit & save.
DSH web GUI 客户端插件:侧栏 Markdown 预览 —— 浏览、渲染、编辑与保存。
English
A client plugin for the DSH web GUI: adds an "MD preview" button at the bottom of the sidebar. Clicking it opens a floating preview window where you can browse, render, and edit & save Markdown files.
Features
- Directory browsing: lists subdirectories and
.mdfiles; enter a directory / open a file by clicking,..to go up; - Dual view — rendered / source (built-in zero-dependency Markdown renderer: headings, lists, tables, code blocks, quotes, links, inline styles);
- Editable source view: save via the "Save" button or
Ctrl/Cmd+S; unsaved changes are flagged in the title bar; switching files / closing the window asks for confirmation; - Save with mtime conflict detection: if the file changed on disk in the meantime, you get a 409 prompt to refresh instead of a silent overwrite;
- Path input: type any absolute path (directory or
.mdfile) and press Enter to jump; - Custom backdrop: solid color, local image (auto canvas-compressed above 1.5 MB) or local video (≤ 50 MB, tiled as a muted looping
<video>background, current page session only); - Custom text color: pick the body text color in the backdrop panel; when unset, light/dark is derived from backdrop luminance; applies to body, lists, and the editor — not just headings;
- Image/color backdrop persisted in
localStorage, with a one-click "restore theme default"; - Draggable title bar; double-click to reset to the default dock (position remembered in
sessionStorage); - Opens the current session's workspace directory by default; Esc or ✕ closes; refresh button re-reads the file.
Security boundaries
- The host half registers only
/md-preview-prefixed routes; read/list are GET/HEAD only, write is POST only; - File access is limited to
.md/.markdown/.mdownextensions, content ≤ 2 MB; write request body ≤ 3 MB; - Writes go through temp file + rename atomic replacement — an interrupted write never leaves a half file;
- Writes carry mtime conflict detection (409) to prevent clobbering unsynchronized external edits;
- Directory listings show only directories and md files;
- Accessible paths = whatever the local shell can read/write (the GUI listens on 127.0.0.1 by default).
Files
| File | Role |
|---|---|
package.json |
Package manifest + dsh.bundle (install layer) + dsh.client (browser-half discovery) |
cordis.patch.yml |
Bundle patch layer activated by dsh plugin add; registers the md-preview Loader row |
index.js |
Host half (node): /md-preview/read, /md-preview/list, /md-preview/write routes |
client.js |
Browser half (classic script bundle, no build step) |
Install
Install the official runtime with Node.js:
npx @deepseek-ai/dsh web
Install this plugin into a profile (the ecosystem convention):
dsh plugin --profile web add "github:anitman/dsh-plugin-md-preview#main"
The #<ref> suffix selects a branch, tag, or commit: #main follows the default branch; pin #<sha> or a release tag to make the installed content immutable; omit it to track the repo's default branch.
dsh plugin forwards package operations to pnpm, so npm, Git/GitHub, local path, file: and link: package specs are all supported — e.g. from a local clone:
dsh plugin --profile web add .
Only packages declaring dsh.bundle.patch become active profile layers; this package declares it, so dsh plugin add completes the link and layer activation in one step. Pure JS, no build scripts — a git install needs no allowBuilds approval.
Restart dsh --profile web after installing or updating a bundle: the document icon button then appears at the bottom of the sidebar (above the settings button); manage it under Settings → Plugins.
Uninstall
dsh plugin --profile web remove dsh-plugin-md-preview
Removes the dependency and the patch layer together; restart dsh to take effect.
Manual fallback (without the dsh CLI)
- Create a symlink
dsh-plugin-md-previewin~/.dsh/profiles/web/node_modules/pointing at this directory (or copy the directory if symlinks fail); - Add to
dependenciesin~/.dsh/profiles/web/package.json:"dsh-plugin-md-preview": "file:<absolute path to this repo>"; - Append to the top-level array of
~/.dsh/profiles/web/cordis.patch.yml:- insert: - id: md-preview name: "dsh-plugin-md-preview" - Restart the dsh process (new Loader rows are only scanned at startup; sessions restore automatically).
Updating
- Only
client.jschanged: no restart needed, client-HMR hot-reloads the plugin (requires the host-side watch chain to be active; otherwise refresh the page); index.js(host half) changed: dsh restart required;- Local clone installed via
add .:git pull, then restart dsh; - Installed via
github:: re-run the install command with a new#refto upgrade; - If node_modules holds a copy instead of a symlink: re-copy after changes (or switch back to a symlink).
简体中文
DSH web GUI 客户端插件:侧栏底部多一个「MD 预览」按钮,点开是一个浮动预览窗口,可直接浏览、渲染并编辑保存 Markdown 文件。
功能
- 目录浏览:列出子目录和
.md文件,点击进入 / 点击文件打开,..回上级; - 渲染 / 源码双视图(内置零依赖 Markdown 渲染器:标题、列表、表格、代码块、引用、链接、行内样式);
- 源码视图可编辑:点「保存」或按
Ctrl/Cmd+S写回磁盘;有未保存修改时标题栏显示「保存 ●」,切换文件 / 关窗前会弹确认; - 保存带 mtime 冲突检测:若期间文件被外部改过,返回 409 提示刷新后重试,避免误覆盖;
- 路径输入框:直接输入任意绝对路径(目录或 .md 文件)回车跳转;
- 自定义背景:标题栏「背景」按钮可选纯色、本地图片(>1.5MB 自动 canvas 压缩)或本地视频(≤50MB,
<video>铺底循环静音播放,仅当前页面会话有效); - 自定义文字颜色:背景面板里可选正文文字色,不设则按背景亮度自动取深浅;作用范围覆盖正文 / 列表 / 编辑区,不只标题;
- 图片/颜色背景存
localStorage,可「恢复主题默认」一键还原; - 标题栏可拖动,双击复位到默认停靠位(位置记忆在
sessionStorage); - 默认打开当前会话的工作区目录;Esc 或 ✕ 关闭;刷新按钮重读文件。
安全边界
- 宿主半边只注册
/md-preview前缀路由;read/list 仅 GET/HEAD,write 仅 POST; - 读/写文件都只允许
.md/.markdown/.mdown扩展名,且内容 ≤ 2MB;write 请求体 ≤ 3MB; - write 通过临时文件 + rename 原子替换,中断不会留下半截文件;
- write 带 mtime 冲突检测(409),防止覆盖未同步的外部修改;
- 列目录只显示目录与 md 文件;
- 路径可访问范围 = 本机 shell 可读写范围(GUI 默认只听 127.0.0.1)。
文件
| 文件 | 作用 |
|---|---|
package.json |
包描述 + dsh.bundle(安装层声明)+ dsh.client(浏览器半边发现机制) |
cordis.patch.yml |
组合包补丁层:由 dsh plugin add 激活,注册 md-preview Loader 行 |
index.js |
宿主半边(node):/md-preview/read、/md-preview/list、/md-preview/write 路由 |
client.js |
浏览器半边(classic script bundle,无需构建) |
安装
用 Node.js 安装官方运行时:
npx @deepseek-ai/dsh web
把本插件装进 profile(生态标准写法):
dsh plugin --profile web add "github:anitman/dsh-plugin-md-preview#main"
#<ref> 后缀可选分支、tag 或 commit:#main 跟随默认分支;锁 #<sha> 或 release tag 可让安装内容不可变;省略则跟随仓库默认分支。
dsh plugin 把包操作转发给 pnpm,因此 npm、Git/GitHub、本地路径、file: 与 link: 包规范都支持——例如从本地 clone 安装:
dsh plugin --profile web add .
声明了 dsh.bundle.patch 的包才会成为激活的 profile 层;本包已声明,dsh plugin add 一步完成链接与补丁层激活。纯 JS 无构建脚本,git 安装不需要 allowBuilds 授权。
安装或更新后重启 dsh --profile web:GUI 左侧栏底部(设置按钮上方)会出现文档图标按钮;管理入口在设置 → 插件。
卸载
dsh plugin --profile web remove dsh-plugin-md-preview
同时移除依赖和补丁层,重启 dsh 生效。
手动安装(fallback,无 dsh CLI 时)
- 在
~/.dsh/profiles/web/node_modules/下创建指向本目录的符号链接dsh-plugin-md-preview(失败则直接拷贝本目录); - 在
~/.dsh/profiles/web/package.json的dependencies加:"dsh-plugin-md-preview": "file:<本机此仓库的绝对路径>"; - 在
~/.dsh/profiles/web/cordis.patch.yml顶层数组追加:- insert: - id: md-preview name: "dsh-plugin-md-preview" - 重启 dsh 进程(新增 Loader 条目只在启动时扫描;会话会自动恢复)。
更新
- 只改
client.js:无需重启,client-HMR 会自动热重载插件(需要宿主侧 watch 链生效;否则刷新页面); - 改
index.js(宿主半边):必须重启 dsh; - 本地 clone 通过
add .安装的:git pull后重启 dsh; github:安装的:用新的#ref重新执行安装命令升级;- 若 node_modules 里是拷贝而非符号链接:修改后需重新拷贝(或改回符号链接)。
No comments yet. Be the first to write one.