- Accueil
- Plugins
- Intégrations et accès distant
- dsh-whale-reminder
dsh-whale-reminder
shawnzhanggy/dsh-whale-reminder
Windows session-end reminder for DeepSeek Harness: an in-window unread badge that lists session names and jumps to the session when clicked, two Web Audio chimes, taskbar flashing, and a tray badge on the whale icon; only visible sessions are counted, and the settings page has seven options including a zh/en switch.
Installer
dsh plugin --profile web add github:shawnzhanggy/dsh-whale-reminderREADME
dsh-whale-reminder
会话结束后提醒你 —— 不再守着窗口等结果。
DeepSeek Harness 桌面版(Windows)插件:一轮会话跑完后,系统通知 + 声音 + 窗口内浮层 + 任务栏闪烁 + 托盘徽章五路提醒,QQ/微信式未读体验。
解决的问题
DeepSeek Harness 桌面版一轮会话跑完后不会主动叫你,你只能自己反复切回来瞄进度。本插件在任务完成、需要你回答、或出错时主动提醒:Windows 系统通知横幅、任务栏闪烁、托盘徽章、窗口内浮层与提示音,QQ/微信式未读体验。系统通知拥有独立应用身份,可在 Windows「设置 → 系统 → 通知」里单独开关,不影响宿主应用本身的通知。
安装
本插件只支持 Windows 桌面端(依赖 Win32 任务栏/托盘 API 与 WinRT 通知)。
它装进桌面端的 desktop profile。先把 DSH 完全退出(含系统托盘),然后在终端执行:
dsh plugin --profile desktop add dsh-whale-reminder
装完重新打开 DSH 即可。也可以不离开 DSH:在会话里让宿主内置的 plugin_manager 装,效果相同。
请使用当前桌面端内置的
plugin_manager安装dsh-whale-reminder,装完告诉我结果以及是否需要重启。
- 首次安装:工具可能返回
"application":"applied",但这不保证当前窗口已经生效。若装完没出现浮层,完全退出客户端(含系统托盘)后重新打开。 - 升级:改的是 client 半区则刷新页面(
Ctrl+F5)即可;改了 host 半区(lib/*.mjs)必须完全退出重开。 - 卸载:同一工具执行
remove_bundle。
主要功能
- Windows 系统通知:会话结束时在通知中心弹出横幅,标题是事件类型(会话已完成/等待你的批准/等待你的回答/会话出错),正文是那一轮你输入的内容。它以自己的应用身份出现,所以在「设置 → 系统 → 通知」里能看到 鲸鱼提醒 这一条,可以单独开关、单独调声音,与宿主应用互不干扰。点击横幅会直接跳转到那条会话,并把窗口唤到最前、把光标放进输入框,可以马上接着打字。
- 盯着 DSH 时不弹横幅:只要 DSH 是当前活动窗口,就跳过系统通知(声音与角落徽章照常),不会在你正看着屏幕时弹一条多余的横幅;被别的窗口盖住或最小化时才弹。该行为由「DSH 在前台时不弹通知」开关控制,默认开启。
- 点击通知的动作可选三档:「点击通知时」可以选 提到最前并聚焦输入框(推荐,可以立即打字,代价是会从其他程序里抢走键盘焦点)、只提到最前,不抢键盘(窗口到最层但不打断你正在输入的内容)、只提醒,不提窗(窗口保持原样、可能还在任务栏里,只切换会话)。三档都不影响会话切换本身。
- 智能触发:只有窗口在后台(失焦/隐藏/切到别的会话)时才出声提醒,正在看的不打扰;三个「什么时候算需要提醒」的开关可独立关闭。
- 双音效:完成「叮—咚」、待回答「叮叮」,音量可调。
- 窗口内常驻浮层:角落红色数字徽章,显示「N 个会话未读」,点击展开会话名列表,点会话名直接跳转到该会话,停靠角可切换四角。
- 任务栏闪烁 + 托盘徽章:任务栏
FlashWindowEx闪烁;托盘小鲸鱼图标叠加红色数字徽章(1–9,超 9 显示「9+」),悬停显示未读缩略文字。 - 设置有两处入口:左侧栏「设置」面板里新增一项 鲸鱼提醒(与「技能」「费用」等插件设置并列);插件管理器里那一行的「配置」按钮也能打开同一张表单。
- 只提醒你看得见的会话:已归档、子代理、空白会话一律不计入未读,与侧栏可见性规则保持一致。
设置项
设置页共 9 组,全部即时生效、无需重启:
| 分组 | 内容 |
|---|---|
| 启用提醒 | 总开关。关闭后不出声、不闪任务栏、不显示浮层、不弹通知(浮层与通知各自的开关仍然保留) |
| 语言 | 中文 / English,默认中文。只影响本插件(浮层、设置页、托盘 tooltip、系统通知),不跟随应用语言 |
| 提醒哪些事件 | 正常完成 / 待回答 / 出错,三个独立开关,默认全开 |
| 什么时候算「需要提醒」 | 窗口被隐藏 / 窗口失焦 / 焦点在别的会话,默认全开。正在看着的那条会话不打扰 |
| 声音音量 | 0–100,默认 60,两个音效共用;旁边有 试听 按钮 |
| 浮层显示会话数 | 1–20,默认 3,同时是 tooltip 字数上限 1–256(默认 127) |
| 浮层停靠角落 | 右下(默认)/左下/右上/左上 |
| 系统通知 | 通知开关;通知带提示音(用 Windows 自带的提示音,与本插件音效相互独立,默认关);DSH 在前台时不弹通知(默认开);点击通知时三档(提到最前并聚焦输入框/只提到最前不抢键盘/只提醒不提窗,默认第一档) |
| 测试提醒 | 一键演练:闪任务栏 + 闪托盘 + 出声 + 浮层出现 + 弹一条通知。点这条通知同样会跳回当前会话,可用来验证点击链路 |
另有一批只存在于配置 schema、未渲染进设置页的进阶参数(闪烁次数与超时、轮询间隔、鼠标一动就停、最长提醒时长、忽略被打断的回合、忽略子代理、托盘闪烁间隔、虚拟主会话点、状态点过期秒数等),共 31 个字段,都带 volatile 标记,需要时可直接在 profile 配置里改。
技术要点
- host 半区(
ELECTRON_RUN_AS_NODE的独立 Node 进程):Windows 原生能力(koffi Win32 API:FlashWindowEx、Shell_NotifyIcon*)负责任务栏闪烁与托盘徽章;系统通知走HKCU\Software\Classes\AppUserModelId\Shawn.DSHWhaleReminder注册独立应用身份 + PowerShell WinRTToastNotificationManager发送 ToastGeneric;监听session/event的turn/end/approval/asked/tool/call(ask_user_question)触发提醒。 - 通知点击跳转:toast 用
activationType="protocol"携带dsh-whale-reminder://open/<会话 id>;注册表里的协议处理器是一个原生小程序assets/activate.exe(C# 编译,不弹控制台窗口),它把收到的 id 通过 loopback HTTP 回传给正在运行的宿主(端口写在注册表命令里),宿主把这次点击广播给所有窗口(每个窗口按单调递增的序号去重,只有序号变新时才导航,刚加载的窗口只记下基线、不重放旧点击),client 半区在窗口处于后台时每 1.5 秒轮询一次,拿到新序号就调用uiWorkspace.openSession,导航确认后再把光标放进输入框([data-composer-input])。处理器不写任何文件——早期用.vbs+%LOCALAPPDATA%落盘的方案在受限令牌下会静默失败,改用 HTTP 后不再受文件权限影响。不新增常驻进程,也不需要宿主配合。 - 为什么提窗口在
activate.exe里做:Windows 只允许「当前持有前台权限的进程」改前台,宿主是后台进程,从它那里唤窗口必然被拒(实测直接调用仅 1/3 成功)。处理器由鼠标点击直接启动、持有该权限,所以工作都在它里面做。三条实测结论决定了实现:①ShowWindowAsync只是把请求投递给窗口线程,而处理器约 1 毫秒就退出,请求随之丢失(从 shell 启动时 12 秒重试仍无法恢复),因此恢复后必须轮询IsIconic确认落定;② 恢复最小化窗口本身就会带来前台,所以这条路径不再额外抬窗,也就不会闪;③ 可见但被覆盖时,SwitchToThisWindow(任务栏点击用的同一个交接)实测 3/3,而SetForegroundWindow只有 1/3,因此首选前者、后者只做一次静默重试;④ 但真实点击通知时,ShellExperienceHost 的通知横幅窗口会持续占用前台锁(实测 9 秒内完全不释放),期间SetForegroundWindow、SwitchToThisWindow、HWND_TOPMOST、最小化横幅、WM_CLOSE/SC_CLOSE全部被拒,只有注入一次真实 Alt+Tab 键击才能解除该锁——因此一旦检测到前台是通知横幅(窗口类Windows.UI.Core.CoreWindow),就跳过全部静默尝试、直接进入解锁——它们注定被拒,而其中BringWindowToTop仍会改 z 序,表现为窗口先冒出来、被横幅压回去、再被抬上来,也就是用户看到的闪烁;解锁本身用「无停顿按下即松开」的 Alt+Tab(不给任务切换器绘制时间),并等前台真的离开横幅(实测:在按键的同一毫秒内就调SetForegroundWindow仍会被拒,表现为「闪一下但没上来」)再反复抬窗直到读回确认;⑤ 抬窗成功还不能立刻退出——前台会随「抢到前台的进程消失」被交还回去(实测:交接成功、进程退出后窗口闪一下又掉下去),所以成功后进程再存活 1 秒,期间一旦发现前台被抢走就重新抢回。所有抬窗 API 的返回值两个方向都不可信,成功与否一律靠轮询GetForegroundWindow读回。不做「先最小化再恢复」的重试循环:它能拿到前台(实测 8/8),但会让窗口明显弹跳,代价高于让用户再点一次,所以拒绝时只闪任务栏,横幅仍留在通知中心可再点。点击动作由宿主在 HTTP 响应里带回(clickAction:raise/show/none),选「只提到最前」时改用SetWindowPos(SWP_NOACTIVATE)只浮上来不抢焦点,选「只提醒」时处理器完全不碰窗口。 - client 半区(浏览器渲染进程):
shell.overlay常驻浮层 + Web Audio 双音效 +settings.section(设置面板侧栏)与plugins.row.config(插件管理器行)双座位共用同一张表单,通过__whale-reminder/*私有路由与 host 半区通信。 - 配置持久化:走官方 Config schema(
@deepseek-ai/schemastery,31 字段全.volatile())+settings.configure({auto:false})+ client 侧configForms。 - 语言:插件自带中文/English 切换(默认中文),浮层、设置页、托盘 tooltip、系统通知四处一致,不跟随应用语言。
- 降级:系统通知不依赖 koffi,所以即使 Win32 绑定失败,通知仍能送达;反之任务栏/托盘失效也不影响通知。
设置页在哪
两个入口,同一张表单:
- 设置面板(左下角头像菜单 → 设置,或
Ctrl+,)→ 左侧导航里的 鲸鱼提醒,位置在「归档会话」与「bili 设置」之间。 - 插件管理器 → 找到
dsh-whale-reminder这一行 → 右侧「配置」控件。
架构参考
复用并改造自 dsh-tray-flash@0.5.2 的已验证架构(win32/tray/dots/attention/koffi-loader/selftest-route),在此基础上新增声音、未读徽章、浮层与设置页。
限制
- 仅 Windows 桌面版(依赖 Win32 托盘/任务栏 API 与 WinRT 通知)。macOS/Linux 上 host 半区会安静降级,只有窗口内浮层与声音可用。
- 托盘图标定位在 Win11 溢出区可能失败(
Shell_NotifyIconGetRect无 rect),此时自动降级为任务栏闪烁兜底。 - 系统通知需要 PowerShell 可用;被组策略禁用的机器上会自动降级为「静默不发」,其余提醒通道不受影响。通知里显示的会话语义取自你那一轮输入的第一行,会话没有人类输入时退化为会话 id 前 8 位。
- 点击通知跳转依赖插件首次启动时写入的协议注册表项(
HKCU\Software\Classes\dsh-whale-reminder,仅当前用户,无需管理员权限),以及%LOCALAPPDATA%\dsh-whale-reminder\activate.exe这个处理器副本(每次启动自动刷新)。若被安全软件清理掉,重启一次客户端即可自动修复;修复前的点击只会把窗口提到前台。点击后若目标会话已不存在或无法导航,客户端日志会留下did not navigate警告,而不是静默失败。 - 点击横幅抬窗口分两条路:最小化时通过恢复动作拿到前台(恢复本身就会带来焦点),最大化但被盖住时走任务栏点击用的同一个交接(
SwitchToThisWindow)。两条路都只做一次,不会闪最小化动画。若前面几步都被前台锁拒绝(最常见的原因是通知横幅仍占着前台),最后会注入一次无停顿的 Alt+Tab 解除锁再提窗;在少数环境下这一下仍可能看到任务切换器一闪,这是 Windows 前台权限规则决定的,无法完全避免。若连这一步也被拒(例如屏幕已锁),会安静失败、只闪任务栏、不再重试——横幅仍留在通知中心,稍后再点即可。抬窗成功后处理器会多存活约 1 秒以稳住前台,因此点完通知到可以打字之间会有一秒左右的间隔。 - 若 DSH 已完全退出,点击通知中心里的旧横幅不会启动它(处理器只在 DSH 运行时才能把点击投递给宿主)。
许可证
MIT © 2026 shawn
Plugins associés
dsh-web (dsh-ssh)
zhu1090093659/dsh-web
dsh-web (dsh-remote-web-ui)
zhu1090093659/dsh-web
dsh-web-ui (dsh-ssh)
zhu1090093659/dsh-web-ui
dsh-purge
kingcharleslzy-ai/dsh-purge