按单元格读写 Jupyter 笔记本,避免改坏文件
30/100
综合分
0
GitHub 星标
—
npm 周下载
—/5
用户评分
数据截至 2026/10/15 · 周下载取自 npm 全网(含 CI / 镜像),非本站安装数;综合分由星标、活跃度与兼容性检查合成。
安装命令 · 需先装 dsh CLI 引擎
dsh plugin --profile web add Boenxia/dsh-plugin-notebook-tools该包不可直接 npm 安装,改从 GitHub 源安装(明细见下方安装检查)
状态速览
判定依据:实装验证 · 静态安装检查 · 自动扫描 · 仓库维护状态信任档位:待复验
是什么
dsh 原生插件 · dev
安全吗
本站尚未对该插件做风险分级
暂未覆盖,不等同于无风险
还在维护吗
活跃:最近一次提交在 17 天前
档位由哪些信号合成
本站实装验证(真实安装 L4 覆盖全站;L5 为运行时冒烟或实机截图,覆盖范围小于 L4) · 验证所用 dsh 版本 · 静态安装检查 · 风险分级 · 仓库维护状态。 下方各区块是它的证据明细。
社区实装还没有人打卡 · 装过的第一个就是你
安全扫描自动 · 静态分析源码v2.7.0🔵 扫描:含敏感能力尚无人工评估展开查看扫描说明与证据 ↓
安全扫描自动 · 静态分析源码
v2.7.0静态扫描发现插件具备触达本地系统的能力:执行外部命令、读写/删除本地文件、读取剪贴板或密钥类环境变量(至少其一)。这是能力清单,不是危险判定——具体能力项与证据见下方,安装前请自行判断是否需要。
读写/删除本地文件
查看扫描证据(共 9 处,展示前 9 条)
- 读取本地文件lib/tools/notebook_create.js:135
await access(p); - 读取本地文件lib/tools/notebook_create.js:152
const s = await stat(parent); - 读取本地文件lib/tools/notebook_list_cells.js:41
const stats = await stat(path); - 读取本地文件lib/tools/notebook_read.js:74
const stats = await stat(path); - 读取本地文件lib/tools/notebook_validate.js:44
raw = await readFile(path, 'utf-8'); - 读取本地文件lib/nb/load.js:25
return await stat(path); - 读取本地文件lib/nb/load.js:58
bytes = await readFile(path); - 写入本地文件lib/nb/save.js:73
await rename(tempPath, path); - 删除本地文件lib/nb/save.js:85
await unlink(tempPath);
扫描于 2026/10/31(1 天前) · 范围 入口闭包 + 发布文件清单 · 来源 GitHub 仓库
静态扫描只反映源码中出现的调用,不构成安全背书;人工评估与自动扫描相互独立、互不覆盖。
给这个插件打分还没有人投票↓
用户评分
还没有人投票,来当第一个
面向 DSH 智能体的单元格感知 Jupyter notebook 工具
README
由 DeepSeek 最新模型翻译生成dsh-plugin-notebook-tools
面向 DSH 智能体的单元格感知 Jupyter notebook 工具。零依赖 Node ESM 插件,把 OpenClaw 的 notebook-tools 插件(9 个工具)移植到 DSH 宿主上。
核心的 read / write / edit 工具把 .ipynb 文件当成不透明的 JSON 处理,容易出错、耗费 token,还很容易损坏文件。这个插件提供结构化、单元格感知的 API:稳定的单元格 id、感知输出的截断、过期编辑防护,以及保留格式的原子写入。
安装
dsh plugin --profile desktop add --config.minimumReleaseAge=0 F:\path\to\dsh-plugin-notebook-tools
dsh plugin 会转发给 DSH 自带的 pnpm,--profile 是必填项。当目标配置档现有的 lockfile 条目比 pnpm 默认的 minimumReleaseAge 截止时间更新时,需要加上 --config.minimumReleaseAge=0 覆盖(即使配置档的 pnpm-workspace.yaml 在 minimumReleaseAgeExclude 里列出了同样的包,pnpm 11.7.0 仍会强制执行这个默认值)。
展开完整文档(README 剩余 1 节)
dsh-plugin-notebook-tools
面向 DSH 智能体的单元格感知 Jupyter notebook 工具。零依赖 Node ESM 插件,把 OpenClaw 的 notebook-tools 插件(9 个工具)移植到 DSH 宿主上。
核心的 read / write / edit 工具把 .ipynb 文件当成不透明的 JSON 处理,容易出错、耗费 token,还很容易损坏文件。这个插件提供结构化、单元格感知的 API:稳定的单元格 id、感知输出的截断、过期编辑防护,以及保留格式的原子写入。
安装
dsh plugin --profile desktop add --config.minimumReleaseAge=0 F:\path\to\dsh-plugin-notebook-tools
dsh plugin 会转发给 DSH 自带的 pnpm,--profile 是必填项。当目标配置档现有的 lockfile 条目比 pnpm 默认的 minimumReleaseAge 截止时间更新时,需要加上 --config.minimumReleaseAge=0 覆盖(即使配置档的 pnpm-workspace.yaml 在 minimumReleaseAgeExclude 里列出了同样的包,pnpm 11.7.0 仍会强制执行这个默认值)。不加这个参数,你会看到 ERR_PNPM_MINIMUM_RELEASE_AGE_VIOLATION,报的却是你没碰过的包。
安装成功后,包会被追加到 <DSH_HOME>\profiles\<profile>\package.json 里的 dependencies 和 dsh.profile.bundles 两处 —— 不用手动改。失败的运行仍可能在 node_modules 里留下链接,所以判断依据是 package.json 里的条目,不是 node_modules。
插件自带 cordis.patch.yml,会以 notebook-tools 这个 id 插入自身。DSH 在启动时组装这一行,所以要重启 DSH 应用,工具才会出现在已经运行的会话里。
不安装任何依赖:不需要 pnpm install,包只导入 node: 内置模块。
配套技能
skill/notebook-tools/SKILL.md 是对应的 DSH 技能:它告诉智能体什么时候该用这些工具、哪些工具会改动 notebook、单元格 id 到底有多稳定。把它复制到技能目录:
Copy-Item -Recurse skill\notebook-tools "$env:USERPROFILE\.dsh\skills\notebook-tools" -Force
DSH 会热重载技能目录,所以技能不用重启就会出现 —— 这点和插件本身不同,插件在启动时组装。
工具
| 工具 | 是否写入 | 用途 |
| notebook_create | 是 | 从结构化单元格创建 notebook |
| notebook_read | 否 | 结构化读取,可选带输出 |
| notebook_list_cells | 否 | 轻量索引:id、类型、预览、计数 |
| notebook_search | 否 | 按文本或正则查找单元格 |
| notebook_validate | 否 | 校验结构并报告事实 |
| notebook_edit_cell | 是 | 替换单元格的源码 / 类型 |
| notebook_insert_cell | 是 | 在指定位置插入新单元格 |
| notebook_delete_cell | 是 | 按 id 或索引删除单元格 |
| notebook_clear_outputs | 是 | 清除输出(全部或单个单元格) |
保证
- 写入保留文件自身的格式。 插件会探测布局……
notebook 已经在用的格式——JSON 缩进(0/1/2/4)、CRLF 还是 LF、末尾换行——都会原样写回,不做改动。所以 JupyterLab、nbformat.writes 或文本编辑器生成的 notebook 不会被重新格式化。source 是普通字符串的单元格,写回后仍是字符串;原本不存在的键(outputs、execution_count、metadata)不会被凭空造出来。
只读不写、不做编辑时,字节完全一致。不保留的内容:制表符缩进、\uXXXX 转义的非 ASCII 字符(Python 的 ensure_ascii=True),以及多于一个的末尾换行。
- 原子保存。 修改会先序列化到同目录下的临时文件(.‹basename›.tmp-‹pid›-‹counter›-‹random›),fsync 之后再 rename 覆盖目标文件。
进程被杀也绝不会留下写了一半的 notebook,临时文件也绝不会落到系统临时目录里。
- 每次写入前都做校验。 深度审计不通过的 notebook——单元格 id 不符合
^[A-Za-z0-9_-]{1,64}$ 或有重复、metadata 不是对象、outputs 不是数组、
source 元素不是字符串——写入操作会直接拒绝,并由 notebook_validate 报告,而不是悄悄改写。
- 用 id,不用索引。 notebook_read、notebook_list_cells 和 notebook_search 始终返回 id。太老、存不下 id 的 notebook(nbformat < 4.5)会用
sha256("v1|<ordinal>|") 推导出 id,这样同一个单元格在不同加载、不同进程里
都保持同一个 id;只有当文件格式支持 id 时,推导出的 id 才会被持久化。
nbformat_minor 永远不会被提升。索引在每次插入/删除后都会变——优先用 id。
- 编辑代码单元格会清空 outputs 和 execution_count, 响应文本里也会说明这一点。
- 每个会修改的工具都有三道防陈旧编辑的关卡。 expected_file_sha256 能抓住磁盘上字节的任何变化——包括同一毫秒内的重写,这是 expected_file_mtime_ms 看不到的;expected_source_sha256 能抓住操作所依赖的那个单元格的变化(插入时的锚点单元格,编辑、删除或清空时的目标单元格); mtime 检查最省事,能容忍亚毫秒级的抖动。这些检查全部在写入之前失败。
notebook_read 和 notebook_list_cells 都会返回 mtime_ms 和 file_sha256;只有 notebook_read 返回每个单元格的 source_sha256。
- 只支持 nbformat 4。 v3 及更早版本一律拒绝。
- 绝不执行内核。
- 失败就抛异常,抛出的是 NotebookError 的子类,带有稳定的 code (NOTEBOOK_NOT_FOUND、STALE_NOTEBOOK、CELL_NOT_FOUND……)。DSH 工具结果契约里没有 isError 字段。
用法
notebook_list_cells { path: "~/analysis.ipynb" }
notebook_read { path: "~/analysis.ipynb", cell_ids: ["a1b2c3d4"] }
notebook_search { path: "~/analysis.ipynb", query: "train_test_split" }
notebook_edit_cell { path: "~/analysis.ipynb", cell_id: "a1b2c3d4",
new_source: "model.fit(X, y)\n",
expected_source_sha256: "…", expected_file_sha256: "…" }
notebook_validate { path: "~/analysis.ipynb" }
把守卫值直接从产生它们的那次读取原样传回——file_sha256 来自 notebook_read 或 notebook_list_cells,source_sha256 只来自 notebook_read。
开发
node --test # from this directory
测试使用 node:test + node:assert/strict,要求 Node >= 22(已在 Node 24 上验证)。
发布
发布只需一条命令,在干净的 main 上运行,且该分支已包含版本号变更:
npm run release -- --title "v0.2.1 - short one-line summary"
除非满足以下条件,否则它会拒绝运行:CHANGELOG.md 中有非空的 ## [<version>] 小节,并且针对 package.json 里的版本有对应的 [<version>]: 链接引用;工作区干净;HEAD 就是承载版本号变更的那次提交。满足后,它会运行 node --test,推送发布分支,创建附注标签 v<version>,推送该标签,并创建 GitHub Release:标签附注作为发布标题,CHANGELOG 小节作为正文。凭据来自 GITHUB_TOKEN / GH_TOKEN,若没有则回退到 github.com 已存储的 git credential(全程不打印任何内容);不需要 GitHub CLI。
其他参数:--dry-run(打印计划,不做任何改动)、--skip-tests、--branch <name>(默认 main)、--remote <name>(默认 origin)。
目录结构
lib/index.js composition only — registers the 9 tools on ctx.tools lib/nb/.js pure domain; node: builtins only, no host SDK imports lib/tools/.js adapters: JSON Schema params, error mapping, response text scripts/release.mjs the release command behind "npm run release" test/*.test.js node:test suites cordis.patch.yml the composition row DSH merges at boot skill/notebook-tools/ the companion skill (SKILL.md)
领域层(lib/nb/)对 DSH 一无所知——它只懂 notebook,因此可以单独做单元测试。
致谢与许可
MIT。这是一个移植版,不是 fork:领域层和全部九个工具适配器,都是依据原插件已记录的行为,为 DSH 插件宿主重新实现的。
- 上游:Lightbridge-KS/openclaw-notebook-tools,作者 Kittipos Sirivongrungson(MIT)。工具接口、其 docs/Notebook-Tools-Spec.md 中的行为规范,以及配套技能,均源自该项目。
- 本移植版:DSH 打包部分(cordis.patch.yml、dsh.bundle.patch 钩子)、零依赖的纯对象工具描述符,以及各测试套件。
LICENSE 同时包含两份版权声明。预览分享卡片长什么样 ↓
分享 · DeepSeek Harness Hub
Boenxia/dsh-plugin-notebook-tools
按单元格读写 Jupyter 笔记本,避免改坏文件
相关插件 · 开发 / 工程
隐私简历生成器reactive-resume/reactive-resume
Reactive Resume 已迁至 GitHub 上的…
★ 45,125已汉化MCP
71.7
AI 架构文档生成器sopaco/deepwiki-rs
🚀 Litho 已进化为 Terrain —— 给你的 AI 智能体一张会呼吸的代码库地图。
★ 3,157已汉化DSH
70.8
长时任务执行闭环AMAP-ML/LongHorizon-Harness
面向 Computer-Use Agent 的 Loop Engineering
★ 1,764已汉化DSH
70.5
AI 编程纪律方法包GanyuanRan/Aegis
让 AI 编程 agent 变得可信:少返工、更安全、说“完成”前先给证据。
★ 1,384已汉化DSH
69.6
多代理编排运行时Enderfga/claw-orchestrator
面向编程智能体的运行时。把 Claude Code、Codex、Antigravity、Grok…
★ 586已汉化MCP
69.4
记忆进化插件csyangwen/dsh-memory-evolve
dsh-memory-evolve 使用场景指南
★ 461已汉化DSH
67.9