发送时把预设提示词拼到消息最前面,输入框保持干净
30.7/100
综合分
1
GitHub 星标
—
npm 周下载
—/5
用户评分
数据截至 2026/10/12 · 周下载取自 npm 全网(含 CI / 镜像),非本站安装数;综合分由星标、活跃度与兼容性检查合成。
自动兼容检查有告警:未发布到 npm registry,仅可从源码安装。
安装命令 · 需先装 dsh CLI 引擎
dsh plugin --profile web add yukk4159-bit/dsh-prompt-injector该包不可直接 npm 安装,改从 GitHub 源安装(明细见下方安装检查)
状态速览
判定依据:实装验证 · 静态安装检查 · 自动扫描 · 仓库维护状态信任档位:待复验
是什么
dsh 原生插件 · skill
安全吗
本站尚未对该插件做风险分级
暂未覆盖,不等同于无风险
还在维护吗
活跃:最近一次提交在 21 天前
档位由哪些信号合成
本站实装验证(真实安装 L4 覆盖全站;L5 为运行时冒烟或实机截图,覆盖范围小于 L4) · 验证所用 dsh 版本 · 静态安装检查 · 风险分级 · 仓库维护状态。 下方各区块是它的证据明细。
社区实装还没有人打卡 · 装过的第一个就是你
安装兼容性检查⚠ 装前注意未发布到 npm registry,仅可从源码安装
展开查看检查明细 ↓
以下结论由程序自动检查 npm 包、engines 声明与入口文件得出,未做人工实机验证——能装不等于用着没问题。
✗npm 包dsh-prompt-injector(未发布到 npm,仅可源码安装)
✓Node 引擎要求 >=22.5 · 基线 Node 22.19 满足
✓dsh CLI 依赖未声明 dsh 版本约束
✓入口文件main/exports/bin 已声明
验证方式:npm registry 存在性 + package.json 静态校验 · 最后检查 2026/10/13 09:38:35
安全扫描自动 · 静态分析源码v2.7.0🔵 扫描:含敏感能力尚无人工评估展开查看扫描说明与证据 ↓
安全扫描自动 · 静态分析源码
v2.7.0静态扫描发现插件具备触达本地系统的能力:执行外部命令、读写/删除本地文件、读取剪贴板或密钥类环境变量(至少其一)。这是能力清单,不是危险判定——具体能力项与证据见下方,安装前请自行判断是否需要。
读写/删除本地文件发起外部网络请求
查看扫描证据(共 6 处,展示前 6 条)
- 发起网络请求client/client.js:166
const response = await fetch(`/prompt-injector/${CONFIG.id}${path}`, { - 读取本地文件lib/store.js:40
const body = await readFile(path, 'utf8') - 写入本地文件lib/store.js:55
await mkdir(dirname(path), { recursive: true }) - 写入本地文件lib/store.js:57
await writeFile(temporary, `${JSON.stringify(value, null, 2)}\n`, 'utf8') - 写入本地文件lib/store.js:58
await rename(temporary, path) - 发起网络请求client/index.js:124
const response = await fetch(`/prompt-injector/${CONFIG.id}${path}`, {
扫描于 2026/11/1(0 天前) · 范围 入口闭包 + 发布文件清单 · 来源 GitHub 仓库
静态扫描只反映源码中出现的调用,不构成安全背书;人工评估与自动扫描相互独立、互不覆盖。
给这个插件打分还没有人投票↓
用户评分
还没有人投票,来当第一个
功能亮点
- 发送时拼接预设提示词
- 仅下一条生效
- 每轮持续注入
DeepSeek Harness 插件:发送消息时把可复用的提示词预设插到消息最前面,可选仅下一条消息或每轮都注入。提示词注入器
README
由 DeepSeek 最新模型翻译生成dsh-prompt-injector · 提示词注入器
一个 DeepSeek Harness Web 插件:把可复用的提示词预设在发送的那一刻注入到消息首部,而不是填进输入框。
注入几次由你决定:💌 只注入下一条(默认)或 💖 每轮都注入。
萌系二次元画面风格:🌸 粉紫渐变、圆角卡片、会呼吸的小表情。
在 DeepSeek Harness 0.2.0-rc.2 上实测可用(Host 侧 67 个用例,浏览器半在真实 GUI 里跑通,见已验证)。
长什么样
先选注入方式,再点预设:
选预设:面板顶部先选「只注入下一条」或「每轮都注入」
选好之后 chip 变成 💌 名字 下一条,输入框里一个字符都不会多:
只注入下一条:chip 显示 💌 … 下一条,输入框内容不动
发送时才是注入发生的时刻。
展开完整文档(README 剩余 1 节)
dsh-prompt-injector · 提示词注入器
一个 DeepSeek Harness Web 插件:把可复用的提示词预设在发送的那一刻注入到消息首部,而不是填进输入框。
注入几次由你决定:💌 只注入下一条(默认)或 💖 每轮都注入。
萌系二次元画面风格:🌸 粉紫渐变、圆角卡片、会呼吸的小表情。
在 DeepSeek Harness 0.2.0-rc.2 上实测可用(Host 侧 67 个用例,浏览器半在真实 GUI 里跑通,见已验证)。
长什么样
先选注入方式,再点预设:
选预设:面板顶部先选「只注入下一条」或「每轮都注入」
选好之后 chip 变成 💌 名字 下一条,输入框里一个字符都不会多:
只注入下一条:chip 显示 💌 … 下一条,输入框内容不动
发送时才是注入发生的时刻。下面是「每轮都注入」连发两条的结果——两条消息都带上了预设块,而输入框始终只有你自己写的话:
每轮都注入:两条消息都带预设块,输入框依然是空的
和「提示词预设」类插件的区别
| | 常见的预设插件 | 提示词注入器 |
| 选中预设后 | 把提示词填进输入框 | 只在输入框左侧显示一个 💌 / 💖 徽章,输入框内容完全不动 |
| 你打字时 | 要在一大段提示词后面接着写 | 输入框里只有你自己写的话 |
| 注入几条 | 选中就一直生效 | 默认只注入下一条,发完自动松开;想每轮都注入得自己切 |
| 发送时 | 提示词就是消息的一部分(你在输入框里看得见) | Host 端在 agent/pre-step 把提示词拼到消息最前面 |
| 对话记录 | 提示词和你的话混在一起 | 记录里是完整的注入后文本(模型看到什么,记录就是什么) |
实现位置:lib/inject.js 的 applyInjection(),注册在 agent/pre-step 瀑布事件上——这是消息进入会话日志之前的最后一个接缝。
为什么不是「往输入框塞标记」
最初的设计是往 composer 草稿里写一个不可见的选取标记,随消息一起送到 Host。实测下来这条路在当前版本走不通:
- DSH 的 composer 是 Lexical 编辑器,没有任何公开的草稿写入服务;
- Lexical 自己拥有文档状态,直接改 DOM 会被它下一次 reconcile 覆盖;
- 通过 DOM 事件(execCommand('insertText'))写入也依赖当前选区,而打开面板后焦点已经不在编辑器上。
所以选择改由 Host 侧按会话记录:浏览器半把「这个会话选了哪个预设、注入到什么时候」通过插件的 HTTP 接口告诉 Host(lib/http.js 的 /selection),Host 在发送瞬间查表注入。这样完全不依赖编辑器的内部实现,也不需要污染消息文本——顺带还让「只注入一条」变得容易实现:Host 注入完就把这条选择丢掉。
早期版本还写了一套「尽力而为」的草稿写入代码,已经删掉了:它写得进去也不起决定作用(真正生效的是 Host 侧的选择),留着只会让「到底谁说了算」变模糊。现在插件完全不碰输入框。
安装
插件是「bundle」形态(根目录有 cordis.patch.yml),用 dsh plugin 安装:
dsh plugin --profile web add "github:yukk4159-bit/dsh-prompt-injector"
dsh plugin 把包管理转发给 pnpm,所以也可以装本地路径或指定分支:
本地检出(改代码时用这个,改完重启就生效)
dsh plugin --profile web add "/path/to/prompt-injector"
指定分支或 tag
dsh plugin --profile web add "github:yukk4159-bit/dsh-prompt-injector#main"
或者在没有全局 dsh 的环境里:
npx -p @deepseek-ai/dsh dsh plugin --profile web add "github:yukk4159-bit/dsh-prompt-injector"
装完重启该 profile,然后打开 Web GUI:
- 输入框左边会多一个 🌸 预设 按钮 —— 点开挑预设;
- 左侧边栏 → 设置 → 提示词注入器 —— 管理预设库(增删改查、搜索、标签过滤)。
用法
1. 设置页写预设:名字、ID(可选)、标签、注入内容 → 保存。
保存会写进该 profile 的配置文件(cordis.patch.yml 的 config.presets),重启、切会话都不会丢。
2. 在输入框左边点 🌸,面板顶部先选注入方式,再点一个预设:
- 💌 只注入下一条(默认)——只有你紧接着发送的那一条会被注入,Host 注入完就把这条选择丢掉,再发就干干净净;
- 💖 每轮都注入——一直生效,直到你点「取消」。
面板顶部的切换是立刻生效的:已经选了预设时改方式,等于同时把那条选择改成新方式。
chip 上会写清楚现在是哪种(💌 名字 下一条 / 💖 名字 每轮),不会出现「以为只注入一次、其实一直在注入」。
3. 正常写你的话,回车发送。
4. 发送瞬间,Host 把预设正文按模板拼到消息最前面再交给模型。
5. 默认方式下,发完那一条之后 chip 自己回到 🌸(面板打开时每 3 秒问一次 Host,因为一次性选择是 Host 释放的,它没法主动通知页面)。
再点一次同一个预设、或点面板里的「取消」即取消。
不点面板也能用:{{ID}}
在消息里直接写 {{code}}(code 是这个预设的 ID),那一条就会用对应预设,发完即止——这本来就是一次性的,和 chip 的选择互不干扰。
- 写了一个库里有的 ID:注入并把这处 {{code}} 从消息里拿走;
- 写了一个库里没有的 ID:当成普通文字原样发出去,也不会挡住 chip 的选择;
- 指向已停用的预设:不注入,文字原样保留。
注入取值的优先级
1. 消息正文里的选取标记({{id}},或早期版本写入的私有区标记);
2. 本会话的选择(就是上面第 2 步记录的那个);
3. config.defaultPresetId。
私有区标记若指向一个不存在或已停用的预设,会刻意压掉后两级回退——你点名要它,就不该偷偷换成别的。手打的 {{id}} 没这个特权,因为它可能只是普通的文字。
关系
- 选择是按会话的:不同会话可以选不同预设,互不干扰。
- 「注入几条」记在浏览器里(localStorage),下次打开面板还是你上次选的方式。
- 选择本身存在 Host 进程内存里,重启即清空——它表达的是「这一轮我想用哪个」,不是持久配置。想常驻就用 defaultPresetId(它按定义就是每轮都注入)。
预设长什么样
presets:
- id: code
name: 代码评审 text: 请以资深工程师视角严格评审这段代码,指出风险与改进点。
tags: [work, code]
enabled: true
注入模板
config.template 决定包装形式,支持 {{name}}、{{id}}、{{text}}:
[{{name}}]
{{text}}
[/{{name}}]
配 config.separator(默认两个换行)拼在你自己的文字和预设块之间。
config.position 从 prefix(默认,消息首部)改成 suffix 就改成拼到末尾。
全部配置项
| 配置 | 默认 | 说明 |
| enabled | true | 总开关。关掉后 UI 还在,但不再注入。 |
| position | prefix | prefix 拼到消息首部,suffix 拼到末尾。 |
| template | [{{name}}]\n{{text}}\n[/{{name}}] | 预设正文外面的包装。 |
| separator | 两个换行 | 预设块与你自己的文字之间的连接串。 |
| defaultPresetId | 空 | 兜底预设:没人选、消息里也没有标记时用它。它按定义是每轮都注入;留空表示不注入。 |
| agentPresets | [] | 只对这些 agent preset 生效;留空表示全部。 |
| libraryPath | 空 | 可选的 JSON 副本路径(默认 <DSH_HOME>/prompt-injector/prompt-injector.json)。 |
| presets | [] | 预设库本体。 |
「注入几条」不是配置项:它是每次挑选时的一个手势,所以留在界面和浏览器里,不写进配置。
数据存在哪
1. 预设库主存储:该 profile 的 cordis.patch.yml 里的 config.presets。
设置页保存时通过 Harness 的 settings.update() 写回,所以它同时是「插件配置」和「预设库」,设置页的自动表单也能直接编辑它。
2. 可选 JSON 副本:设置在 settings 提供方不可用时(或者你想让库跟着仓库走)会退化写到 libraryPath;用一个 profile 里没有的 agent 跑时也能从这里读起来。
3. 会话选择:只在 Host 进程内存里,不落盘(见上)。
HTTP 接口
浏览器半用这三条路由和 Host 半对话;它们挂在组合后的 Host Web 服务器上,因此同样受该服务器的浏览器信任栅栏与鉴权保护。
| 方法 | 路径 | 作用 |
| GET | /prompt-injector/prompt-injector/library | 读预设库、标签和全部会话选择 |
| PUT | /prompt-injector/prompt-injector/library | 整库覆盖写入 |
| PUT | /prompt-injector/prompt-injector/preset | 新增或更新一条(按 id) |
| DELETE | /prompt-injector/prompt-injector/preset?id=… | 删除一条 |
| GET | /prompt-injector/prompt-injector/selection | 只读会话选择(面板的轮询用这条) |
| PUT | /prompt-injector/prompt-injector/selection | 记录/清空某会话的选择,body 为 {sessionId, presetId, mode},mode 取 once / sticky |
GET /library 返回的 selections 形如 {"session-…": {"presetId": "code", "mode": "once"}}。当 mode 是 once 时,Host 注入完那一条就会把这一项删掉——所以下一次 GET 里它就没了,面板据此把 chip 还原成 🌸。
路径里的 prompt-injector 是插件条目 id,两个实例不会互相覆盖。
项目结构
prompt-injector/
├─ cordis.patch.yml # bundle 入口:一行 insert ├─ package.json # dsh.bundle + dsh.client 声明 ├─ lib/ # Host 半(Node) │ ├─ index.js # 插件入口:Config、pre-step 注入、一次性选择的释放、路由与存储装配 │ ├─ config.js # Config schema(单独一个文件,为了隔离 schemastery 依赖) │ ├─ core.js # 纯函数:预设规范化、标记编解码、注入方式、模板渲染、拼接 │ ├─ inject.js # agent/pre-step 的注入逻辑(纯函数 + 消息重写) │ ├─ store.js # 预设库存储 + 会话选择(含 once/sticky):settings 写透 + JSON 原子副本 │ ├─ http.js # /prompt-injector/<id>/library、/preset、/selection │ └─ client/client.js # 构建产物:浏览器半 ├─ client/ # 浏览器半(手写 lazy-CJS 工厂,无需打包器) │ ├─ index.js # 入口:apply/inject、槽位注册、库与选择同步、方式偏好 │ └─ src/ # config / core / styles / composer / settings-page ├─ scripts/build-client.mjs # 把 client/ 组装成 client/client.js ├─ docs/ # README 里的截图 └─ test/ # node:test,无第三方依赖
client/client.js 是提交进仓库的构建产物:Harness 直接加载它,所以别人 clone 下来不需要构建就能装。
构建浏览器半 sh
node scripts/build-client.mjs
脚本自己做四件事:解析相对的 import、把 react / react-dom 转成平台 require、把每个源文件包进各自的闭包、最后包成模块加载器要的
window.__ModuleLoader__.load({ id, factory })。没有打包器依赖。
测试 sh
node --test --experimental-test-isolation=none "test/.test.js"
或
node scripts/build-client.mjs && node --test --experimental-test-isolation=none "test/.test.js"
必须写文件通配符:--experimental-test-isolation=none 下不能直接传目录。
在受限沙箱(workspace-write)里也必须保留 --experimental-test-isolation=none——默认的测试运行器会用管道 spawn 子进程,被沙箱拒绝(EPERM)。
覆盖:预设规范化 / 标记编解码(含手打 {{id}})/ 注入方式归一化 / 模板与拼接 / 消息重写(含非人类消息的排除、禁用预设、
allow-list、{{id}} 命中与否)/ 会话选择与一次性释放 / 存储写透与 JSON 原子副本 /
浏览器 bundle 的注册与槽位贡献 / Host 端 apply() 的完整 pre-step 路径。
共 67 个用例;其中「Config 默认值」需要 @deepseek-ai/schemastery 可解析,在纯仓库检出里会跳过。
已验证 / 待验证
已经实测:
- 注入真的发生在发送时、并且真的到了模型请求里。用一个临时观察插件监听 llm/stream,对 agent/pre-step 改写后的消息取证:请求里拿到的是 [PROBE-INJECTED] Reply with exactly: PROBE-OK,说明改写后的内容就是模型收到的那一条。
- 插件能被真实 profile 加载:dsh plugin --profile <name> add <本目录> 之后 bundle 层出现 - id: prompt-injector,Host 半正常 apply,禁用预设被过滤,HTTP 路由注册成功。
- 浏览器半在真实 GUI 里跑通:输入框左侧出现 🌸 预设 chip;面板能打开、搜索、按标签过滤;选中后 chip 显示预设名与方式;Host 侧 /library 的 selections 里能看到该会话的选择;「取消」后选择被清空。
- 「只注入下一条」真的只注入一条:在预览 profile 里真的打字 + 回车发送 4 条消息(该 profile 用的是假密钥,请求会 401,但注入发生在 agent/pre-step,即请求之前)。Host trace 与写进会话日志的正文分别是:
- 第 1 条(💌 选 code-review):changed=true preset=code-review source=session
- 第 2 条:changed=false source=none —— 选择已被释放
- 第 3 条(切到 💖 novel):changed=true preset=novel source=session
- 第 4 条:changed=true preset=novel source=session —— 每轮模式下继续注入会话日志里逐条对应:第 1 条带 [严格代码评审]… 块,第 2 条原样,第 3、4 条都带 [小说续写]… 块。发完之后 GET /selection 返回 {},chip 自己回到 🌸。
- 手打 {{id}} 也对:发一条 {{code-review}} 顺手看看 {{nope}} 这个写法,日志里记下的是预设块 + 顺手看看 {{nope}} 这个写法——命中的被注入并摘掉,没命中的原样留着。
- 设置页能读能写:左侧「设置 → 提示词注入器」列出 6 条预设(含停用项,标 🚫),搜索与标签过滤正常,保存后 Host 的 /library 确实返回了改动后的库。
- 选择 → 注入的完整链路(自动化用例):test/host.test.js 里一条测试直接走 HTTP 路由写选择,再驱动 agent/pre-step,断言消息首部出现 [小说续写],并断言 sticky 会连续两条都注入、once 只注入第一条且随后被释放。
- Host 端 67 个用例,66 通过、1 跳过(跳过的那条需要本机可解析 @deepseek-ai/schemastery)。
没验证的:真机上模型真的回话(预览 profile 没有可用密钥)、以及 DeepSeek 官方路由以外 provider 的行为——这两件都和注入逻辑无关。
调试开关
DSH_PROMPT_INJECTOR_TRACE=1 会在 stderr 打出 Host 半每一步(apply、库大小、webServer 等待、pre-step 决策、注入结果)。
实现要点
- 注入点是 agent/pre-step。它以 waterfall 方式运行,本插件先调用 next(),再改写返回的 messages,因此能和压缩等其它 pre-step 策略组合,而不是覆盖它们。
- 只改写「人类写的」用户消息:source.kind === 'user'。运行上下文快照、技能提醒、工具追加都不会被注入。
- 每个 step 最多改写一条,避免同一个预设被乘上多份。
- 标记用私有区字符,正常文本里不可能出现,因此不会误伤。
- 失败即放行:任何注入异常都会被记录并原样放行消息,绝不因为插件问题丢失你发出去的内容。
- 资源都有归属:路由、效果、样式表都注册在插件 fiber 的 effect 上,插件卸载自动回收。
已知限制
- 选择只在 Host 进程内存里,重启 DSH 会清空。它是「这一轮用哪个」的意图,不是持久配置;想常驻请配 defaultPresetId。
- 预设库的写入依赖 Harness 的 settings 服务。该服务不可用时退化为 JSON 副本,此时设置页的修改只在当前进程内生效。
- 注入后的文本会进入会话日志——这是有意为之:记录应当等于模型真正收到的东西。
- 一次性选择由 Host 释放,页面只能事后知道:面板打开时每 3 秒 GET /selection 一次(只在有一次性选择待发时轮询)。所以发完消息后 chip 可能需要最多 3 秒才从 💌 变回 🌸——这不影响注入,只是徽章慢一拍。
- {{id}} 只在 ID 命中库里的预设时才当作引用,所以预设 ID 起得越像普通词(例如 code),越有可能误伤正文里的 {{code}} 写法。介意的话把 ID 起得独特一点(例如 pi-code)。
贡献
欢迎开 issue 报 bug、提想法,或者直接 PR。改浏览器半的代码之后记得跑一次 node scripts/build-client.mjs——client/client.js 是要一起提交的构建产物。
许可
MIT,见 LICENSE。预览分享卡片长什么样 ↓
分享 · DeepSeek Harness Hub
yukk4159-bit/dsh-prompt-injector
发送时把预设提示词拼到消息最前面,输入框保持干净
相关插件 · 技能 / 提示词
人设统管ZiChuanLan/agent-purge
一份系统提示词,喂给多个 coding…
★ 931已汉化DSH
73.8
人物画像蒸馏titanwings/distilly
Distilly — 把他们的思考方式提炼成可复用的技能,供任何智能体或机器人使用。原名 Colleague Skill(原同事 Skill)。
★ 25,659已汉化DSH
71.3
推理工作空间套件Tiger3807861189/J-Space-Cognition-Suite
J-Space 是面向复杂推理、大型仓库工程、子代理协作与授权安全分析的推理时工作空间和控制套件。
★ 2,957已汉化DSH
70.5
两阶段工具锚定预设xiaobright/dsh-anchored-standard
实验性 DeepSeek Harness agent preset…
★ 3,742已汉化DSH
70.1
智能体工作流编排nrslib/takt
不再日夜盯着 AI 编码智能体。
★ 1,402已汉化DSH
70
Agent 运行时手册Electricitysheep/dsh-handbook
DeepSeek Harness dsh 从 0 到 1 深度手册:安装/插件开发/性能调优/实测案例/同模型多…
★ 827已汉化DSH
68.7