Repository navigation
Releases: Caoran1314/dsh-edict
Releases · Caoran1314/dsh-edict
Release list
dsh-edict v0.1.8
[0.1.8] — 2026-10-14
修复
- 独立看板打开是 403 "拒绝访问"。根因是我用错了栅栏:
connection.requestRejection内含 login-token cookie 校验(见 dsh-schedule 源码注释),
而浏览器新标签页的顶层导航不会自动带 cookie —— 拿它当"拒绝外部访问"的栅栏,
必然把用户自己堵在 403。
现在区分对待:- 页面路由
/edict:放行顶层导航(无 Origin 头),只拒跨站 fetch(有 Origin 且与 Host 不符) - 数据路由(
/edict/board/audit/task):保留requestRejection栅栏
- 页面路由
- 独立看板改为服务端渲染:看板数据与最近审计直接内嵌进 HTML,页面首次打开即可用,
不再依赖凭据去 fetch。若能带凭据过栅栏,再自动切换为 3 秒实时刷新(页头会显示"内嵌快照 / 实时")。
状态码速查(写给以后的自己)
| 状态码 | 含义 |
|---|---|
| 401 | 路由不存在(被 DSH 通用认证中间件拦,响应体为空) |
| 403 | 路由存在,是插件自己的栅栏拒绝了该请求 |
dsh-edict v0.1.7
[0.1.7] — 2026-10-14
修复
- 工具调用报
returned invalid output: value is not lossless JSON。
任务对象的可选字段(如active[].org、now、remark)常为undefined,
而宿主对工具返回值做 lossless JSON 校验,遇到undefined直接判为非法(JSON.stringify会静默丢弃,
所以本地自测发现不了)。
新增toLossless()深度清洗:剥掉undefined(字段整体删除)、function/symbol→null、
bigint→ 字符串、Date→ ISO、Buffer→ utf8、NaN/Infinity→null、检测循环引用。
在execute出口与render两处生效。
这个缺陷是作者自己调用工具时发现的 —— 说明"发布后真用一遍"比任何自测都重要。
dsh-edict v0.1.6 — 首次真正可用(修复三个致命缺陷)
dsh-edict v0.1.6
这是首次真正可用的版本。0.1.0–0.1.2 存在致命缺陷,请勿使用。
⚠️ 三个致命缺陷(本版修复)
1. 声明了 dsh.client 却未导出 ./client → 整个 DSH 启动失败
dsh-edict declares dsh.client but exports no "./client" bundle
宿主 ClientModuleRegistry 抛出后,DSH 启动失败并触发自愈逻辑清空 profile 里所有插件层
(用户侧表现为"我的插件怎么全没了")。0.1.0 / 0.1.1 均为此缺陷版本。
2. 15 个工具与 5 条看板路由全部注册失败(且无任何报错)
两个叠加原因:
| 问题 | 后果 |
|---|---|
工具缺少必需的 output { schema, render } |
tools.register() 抛 must declare output ...,异常被静默吞掉 |
apply() 时 tools/webServer 服务尚未就绪,取不到即永久放弃 |
看板路由 0 条 → /edict 返回裸 401 |
现改为:统一 withOutput() 补齐契约 + 监听 internal/service 事件 + 1.5 秒定时重试双保险。
3. 独立看板无法打开(新标签页不带凭据)
window.open('/edict') 是顶层导航,不携带 DSH 浏览器凭据,被认证中间件拦掉。
新增 GET /edict/url,由宿主用 connection.authenticatedUrl 生成带 token 的地址。
(签名是从 dsh-host-frontend-static 里挖出来的:要传完整 base URL。)
修复清单(按版本)
| 版本 | 修复 |
|---|---|
| 0.1.2 | 补 exports["./client"](致命启动缺陷) |
| 0.1.3 | 工具 output 契约 + 服务晚到重试;edict_role 用错 store 实例 |
| 0.1.4 | 新增 /edict/url(带凭据地址) |
| 0.1.5 | last-load.json 写入 store.dir(此前测试会覆盖真实加载证据,造成误判) |
| 0.1.6 | 修正 authenticatedUrl 调用签名 |
新增的诊断能力
~/.dsh/edict/last-load.json—— 记录每次加载的tools/routes数量,
用于区分"插件没加载"与"加载了但没注册"- 注册失败不再静默:走
logger.warn
测试
- 单元测试 28/28 通过(状态机转换表与上游
task.py的EXPECTED_TRANSITIONS逐条对齐) - 冒烟测试新增 3 条回归守卫(本版的三类缺陷各一条):
- 每个工具必须声明
output { schema, render }与execute - 5 条看板路由必须注册
- 服务晚到时必须能补注册(模拟
apply时服务未就绪)
- 每个工具必须声明
- mock 宿主已改为符合真实契约(
ctx.get('tools')+ctx.effect+internal/service事件)
安装
dsh plugin --profile desktop add dsh-edict完整变更
见 CHANGELOG.md。
踩坑记录见 docs/RELEASE.md
与 docs/PLUGIN-RELEASE-CHECKLIST.md。
v0.1.0 — 三省六部审核流程 DSH 插件
把 edict(OpenClaw 三省六部制多智能体编排,MIT)的审核流程逻辑移植为 DeepSeek Harness 插件,规则逐条对齐。
规则(与原版一致)
- 12 状态状态机 —— 转换表对齐上游
task.py的STATE_TRANSITIONS;终态{Done, Cancelled}无出边 - 门下省封驳 ——
Menxia → Zhongshu打回重做;confirm reject退回Review复审 - 高风险操作确认 ——
Review→Done(menxia)、Doing→Cancelled(shangshu)、Menxia→Cancelled(zhongshu) 先落PendingConfirm - 越权矩阵 —— 11 个衙门角色的命令白名单(六部不能改状态、门下省不能 create 等)
done前置硬校验 —— 状态须为Doing/Next且 todos 全部完成- 单一 in-progress 约束 / 委派防死锁(深度≤3、成环拒绝、权限链)
- 审计留痕 ——
ts/task/agent/action/from/to/reason,上限 5000 条,拒绝也记录
提供的能力
- 15 个工具:
edict_create/move/flow/progress/todo/done/block/confirm/delegate/delegate_result/memory/task_memo/shared_memo/status/role - 3 个命令:
edict(看板)、edict-audit、edict-reset-role - 军机处看板 UI:设置页「三省六部」面板 + 独立看板页
/edict - 零依赖 —— 只用 Node 内置模块;数据存
~/.dsh/edict/,原子写 + 跨进程锁
安装
dsh plugin --profile desktop add dsh-edict测试
- 28 项单元测试(
node test/edict.test.mjs),含从上游test_state_machine_consistency.py移植的状态机守卫 - 冒烟测试(
node test/smoke.mjs):mock ctx 加载插件并跑通完整旨意
相比上游的两处行为增强
| 项 | 上游 | 本版 | 原因 |
|---|---|---|---|
progress 替换 todos 后 |
不重算 ready_to_close |
重算 | 上游内部不一致 |
| todos 清单解析 | item[:-1] 截断 |
按码位删除 | emoji 是代理对,JS 里会留半个字符 |
致谢
流程设计来自 cft0808/edict(MIT)。本移植保留其规则语义并注明出处,实现代码独立编写。
完整变更见 CHANGELOG.md