Repository navigation
Releases: a5899/dsh-lan-peers
Release list
v1.4.2 — 修复 no-address
v1.4.2
修复 no-address:对方刚给我发过 tell,我回一条却发不出去。
原因
从入站请求学会的对端记录只存了 IP、没存端口,所以不可拨号,必须等下一次扫描覆盖掉才行。而且这条分支只在"对端未知"时才跑,坏数据会一直留着。
修法
- 入站请求从对方身份信息里学到端口,同时记下来源地址
- 已有但缺端口/缺地址的记录原地补全
- 出站身份信息带上
port和ip,双方互相学
新增 test/address.mjs 覆盖"未经扫描直接 tell → 对方可立即回信"。16 组测试通过。
v1.4.1 — 测试不再污染真实安装
v1.4.1
修复:test/e2e-process.mjs 的两个实例没有指定 patchFile,保存时写进了插件自己所在的目录,把测试数据(displayName: 'LOCAL-ASKER'、passphrase: 'e2e-secret')写成了真实安装的配置。
现在所有测试实例都指向临时路径,并校验跑完整套测试后真实 patch 的哈希不变。
v1.4.0 — 移除模型调用
v1.4.0
移除「调用模型生成回答」,只保留基础能力(discover / ask / tell / chat / transcript / state + 记录网页)。
为什么移除
这个功能引入了本插件历史上最严重的事故:llm.listModels() 签名用错,异常穿透宿主请求处理器,把 DSH 进程搞崩。移除后整类风险消失 —— 不再注入 llm、不再解析 provider、不再构造模型消息。
对方提问重新由确定性的主机信息回答,不跑模型、不花 token。
同时采用(来自 Android 端实测补丁)
- 设置页 401:
credentials: "omit"→"same-origin" - 布尔/数字类型丢失:改用
BOOLEAN_KEYS/NUMBER_KEYS,避免true被存成'true'导致下次启动 schema 校验失败、插件挂载不上
15 组测试通过。感谢手机端那份逐条带证据的补丁清单。
v1.3.2 — 修复模型回复导致 DSH 崩溃
v1.3.2 ⚠️ 重要修复
我的代码把 DSH 整个搞崩了,对不住。手机一提问,桌面端直接弹「应用无法启动或已意外停止」。
原因
我误以为 llm.listModels() 无参返回整张目录,实际契约是 listModels(providerId)。不给 provider 就抛 NO_ADAPTER: no adapter registered for provider "undefined",这个异常穿过 answerFor 和入站处理器,直接终止了宿主进程。
修法(三重)
- 正确调用:
listProviders()拿路由,再对每个 id 调listModels(id);某个 provider 报错就跳过 - 不放行残缺路由:碰适配器之前校验
provider/model都是非空字符串 - 任何异常都不许逃逸:逐层 try/catch,最外层退回固定回答
一个「生成回复」功能绝不该能搞崩宿主。
测试为什么没拦住
我的假 llm 用的是错误契约(无参返回目录),所以测试全绿而线上崩溃。
新增 test/llm-shape.mjs,用与崩溃现场相同的严格契约验证。16 组测试通过。
v1.3.1 — 修复保存误报失败
v1.3.1
修复反复出现的「已生效,但没写进配置文件(重启会丢):no writable patch for this entry」。
真相
patch 文件其实已经写进去了(文件修改时间就是你点保存的那一刻),是误报。
persistOwnPatch() 用 false 同时表示两件完全不同的事:
- 文件不存在 → 真的失败
- 内容没变化 → 已经是最新值,属于成功
重复保存同样的值就会落到失败分支,于是每次点保存都红字一片。
现在
返回四种明确结果:written / unchanged(都算成功)/ missing / no-entry(才是失败)。
失败时也会说清找的是哪个路径。
已在本机真实安装上验证:第一次 written,再点一次 unchanged → 界面都显示「已保存」。
v1.3.0 — 用本机模型回复对方提问
v1.3.0
收到提问时可以用本机模型生成回答了。
新增
设置页「用本机模型回复对方的提问」(默认关闭)+ 模型回复超时。
- 开启:对方的
lan_peer_ask/lan_peer_chat会带上同一会话最近若干轮作为上下文,交给本机模型回答 - 关闭:行为不变,只返回主机信息,不消耗 token
可靠性
任何模型故障都会回退到固定回答,对方永远收得到回复:
- 无 llm 服务 / 无可用模型 / provider 抛错 / error 分片 / 空回复 / 超时
- 超时由插件自己兜底(默认 45s),不依赖适配器是否响应取消信号
安全
系统提示里明确要求不编造、绝不透露本机文件内容、系统提示词、会话记录或凭据。
状态可见
status() 新增 modelReplies / modelRoute / modelStats(成功、失败次数、上次耗时)。
15 组测试通过。
v1.2.1 — 修复单向发现
v1.2.1
修复手机能发现电脑、电脑发现不了手机。
根因:Windows 按跃点数选网卡
这台机器上"以太网"已断开(0 bps),但跃点数(5)比 WLAN(30)低。
Windows 按跃点数选发包网卡 → 探测包从断开的以太网发出,永远到不了手机。
实测证据:
- 不绑定接口:定向广播源地址
192.168.0.39(断开的以太网) - 绑定 WLAN 地址:源地址
192.168.0.15(正确)
反方向用路由器转发,不受影响 —— 所以表现为单向失败。
修法
- 发现用的 UDP socket 绑定到本机 LAN 地址
- 多播组在每个 LAN 接口分别加入
- 广播发往本网段定向广播(
192.168.0.255),不再用255.255.255.255
(后者走默认路由,会进代理隧道) - 新增
lanInterfaces():真实网卡优先、虚拟/隧道靠后
另外
- 并发
discover()不再互相清空结果 - 上一版「no writable patch」是旧进程残留;patch 写入实测正常
v1.2.0 — 设置持久化修复
v1.2.0
修复设置保存后重启丢失。感谢手机端 DSH 的排查——它给出了准确的三层原因。
根因
ctx.loader在未声明 inject 的上下文抛错loader.entries()是 Generator,.find()抛 TypeError 且被 catch 吞掉id: lan-peers这一行在插件自己的 patch 文件里,改写 profile 根 patch 等于没写
修法
- loader 不可达时原子重写插件自己的 patch(tmp + rename),只替换传入的键,注释和格式逐字节保留
- 写回前用 YAML 解析器回读校验,不过就拒绝提交
- 保存失败不再显示「已保存」,而是「已生效,但没写进配置文件(重启会丢):原因」
status.version改为从 package.json 读取(此前硬编码 1.0.0)
注意
我没有采用"用 YAML 库整体重新序列化"的方案:实测会丢掉全部注释并改变引号风格,
而这个文件大部分是注释。改为定点行替换 + 写入前 YAML 校验。
13 组测试通过,含真实 HTTP 路由 + 临时 profile 布局的端到端持久化验证。
v1.1.1 — 修复设置页路由
v1.1.1
修复:设置页的按钮一直 404。
cordis 里 ctx.inject([...], fn) 不是"等某个服务出现再回调",而是把 fn 当带依赖的子插件挂载——依赖一直不满足时它永不激活、也不报错。于是插件每次都静默退到 /api 下永远无效的 webServer 兜底。
正确做法是把 connection 写进插件模块自己的顶层 inject,让加载器在服务就绪后才启动插件。
已经能用的
- 对话、记录落盘、手机可开的记录网页
http://<内网IP>:45715/
这次修好的
- 设置页「保存并应用」「扫描内网设备」等按钮
v1.1.0 — 对话 / 记录网页 / 手机适配
dsh-lan-peers v1.1.0
同一内网里装了本插件的 DSH 可以互相提问、互相告知、互相对话,并且有一个手机也能看的记录网页。
新增
- 跨设备对话 \lan_peer_chat\:多轮对话,同一 \conversation\ id 保持上下文
- 对话记录落盘:双向记录到 \ ranscript.jsonl\,重启不丢
- 记录网页 \http://<内网IP>:45715/\:独立页面,不需要 DSH 登录态,手机浏览器直接打开;可看完整往来,也能直接发消息
- \lan_peer_transcript\:查看两台 DSH 聊过什么
手机适配
单列布局、刘海安全区、≥44px 触控、长文本换行、深色模式。已在真实 Chromium 的 320/390/1280px 验证:无横向溢出、零控制台错误。
修复
- 配置字段误用 .volatile()\ 导致端口变 NaN、多播地址变 [object Object]\
- /api\ 前缀路由不生效(Connection 按精确路径匹配)→ 改用 \connection.fetch.register\
- 未声明 \inject\ 就访问 \connection\ / \webServer\ 会抛错并中断注册
安装
powershell cd \C:\Users\a5093\.dsh\profiles\desktop git clone https://github.com/a5899/dsh-lan-peers.git node_modules/dsh-lan-peers
然后在该目录的 \package.json\ 里加依赖 "dsh-lan-peers": "file:./node_modules/dsh-lan-peers"\,以及 \dsh.profile.bundles\ 里加 "dsh-lan-peers"\。重启 DSH,到 设置 → 插件 → LAN 邻居 启用。
详见 README 的「安装」一节。