🎁 福利专区全网大模型免费应用 + 新用户福利 + 注册活动入口,低成本玩转 AI

日历日记 liwangzimo/dsh-calendar-diary

DeepSeek Harness
liwangzimo13 天前有提交已提供中文文档扫描:含敏感能力

在侧栏月历上按天写日记,存进自己的 Excel 文件

30.6/100
综合分
1
GitHub 星标
—
npm 周下载
—/5
用户评分

数据截至 2026/10/23 · 周下载取自 npm 全网(含 CI / 镜像),非本站安装数;综合分由星标、活跃度与兼容性检查合成。

安装命令 · 需先装 dsh CLI 引擎
dsh plugin --profile web add liwangzimo/dsh-calendar-diary
该包不可直接 npm 安装,改从 GitHub 源安装(明细见下方安装检查)

状态速览

判定依据:实装验证 · 静态安装检查 · 自动扫描 · 仓库维护状态
信任档位:已验证
是什么[目录]—
dsh 原生插件 · other
暂无时间戳·判据 →
装得上吗[实装验证]✓
本站已在 dsh 0.2.1-rc.2 下真实安装成功
非静态推断
L5 · 运行时冒烟等级说明 →
数据截至 2026/10/27·判据 →
安全吗[自动扫描]—
本站尚未对该插件做风险分级
暂未覆盖,不等同于无风险
数据截至 2026/11/03·判据 →
还在维护吗[仓库]✓
活跃:最近一次提交在 13 天前
暂无时间戳·判据 →
图例:✓ 通过! 需注意— 未判定 / 无数据· 「未判定」= 本站尚无数据,不代表插件有问题
档位由哪些信号合成

本站实装验证(真实安装 L4 覆盖全站;L5 为运行时冒烟或实机截图,覆盖范围小于 L4) · 验证所用 dsh 版本 · 静态安装检查 · 风险分级 · 仓库维护状态。 下方各区块是它的证据明细。

验证判据与等级说明 →

可信度证据

安全扫描自动 · 静态分析源码
v2.7.0
🔵 扫描:含敏感能力尚无人工评估
展开查看扫描说明与证据 ↓

静态扫描发现插件具备触达本地系统的能力:执行外部命令、读写/删除本地文件、读取剪贴板或密钥类环境变量(至少其一)。这是能力清单,不是危险判定——具体能力项与证据见下方,安装前请自行判断是否需要。

读写/删除本地文件发起外部网络请求
查看扫描证据(共 36 处,展示前 22 条)
  • 读取本地文件
    index.js:143
    const raw = JSON.parse(readFileSync(configPath, 'utf8'))
  • 写入本地文件
    index.js:151
    mkdirSync(dirname(configPath), { recursive: true })
  • 写入本地文件
    index.js:153
    writeFileSync(temporary, `${JSON.stringify(config, null, 2)}\n`, 'utf8')
  • 写入本地文件
    index.js:154
    renameSync(temporary, configPath)
  • 读取本地文件
    index.js:242
    const read = existsSync(path) ? readDiary(path) : { exists: false, entries: [] }
  • 读取本地文件
    index.js:271
    const current = existsSync(path) ? readDiary(path).entries : []
  • 读取本地文件
    index.js:293
    const current = existsSync(path) ? readDiary(path).entries : []
  • 读取本地文件
    index.js:369
    const current = existsSync(path) ? readDiary(path).entries : []
  • 读取本地文件
    index.js:397
    const current = existsSync(path) ? readDiary(path).entries : []
  • 写入本地文件
    index.js:499
    mkdirSync(dirname(CONFIG_PATH), { recursive: true })
  • 写入本地文件
    index.js:500
    writeFileSync(CONFIG_PATH, `${JSON.stringify({ dataPath: DEFAULT_DATA_PATH }, null, 2)}\n`, 'utf8')
  • 发起网络请求
    client.js:269
    response = await fetch(`${ROUTE_BASE}${path}`, init);
  • 读取本地文件
    diary-io.js:85
    directoryExists: existsSync(dirname(path)),
  • 读取本地文件
    diary-io.js:88
    const stats = statSync(path)
  • 读取本地文件
    diary-io.js:98
    if (facts.exists) accessSync(path, fsConstants.W_OK)
  • 读取本地文件
    diary-io.js:101
    while (!existsSync(probe) && dirname(probe) !== probe) probe = dirname(probe)
  • 读取本地文件
    diary-io.js:102
    accessSync(probe, fsConstants.W_OK)
  • 读取本地文件
    diary-io.js:124
    if (existsSync(path) && statSync(path).isDirectory()) {
  • 写入本地文件
    diary-io.js:228
    copyFileSync(path, target)
  • 写入本地文件
    diary-io.js:241
    mkdirSync(dirname(path), { recursive: true })
  • 写入本地文件
    diary-io.js:261
    renameSync(temporary, path)
  • 删除本地文件
    diary-io.js:266
    rmSync(temporary, { force: true })
扫描于 2026/11/3(1 天前) · 范围 入口闭包 + 发布文件清单 · 来源 GitHub 仓库

静态扫描只反映源码中出现的调用,不构成安全背书;人工评估与自动扫描相互独立、互不覆盖。

社区实装还没有人打卡 · 装过的第一个就是你
给这个插件打分还没有人投票↓
用户评分
还没有人投票,来当第一个

README

由 DeepSeek 最新模型翻译生成
dsh-calendar-diary(日历日记) 一个纯记事本式的 DSH 插件:一天一条,写在你自己的一个 .xlsx 里。侧栏一个月历面板(一次显示 10 周)。 没有提醒、没有通知、没有标签、没有搜索、没有云同步,也不联动官方「自动化任务」。除了你指定的那个 .xlsx 和插件自己的配置目录,它不写别的地方,也不联网。 功能 - 侧栏「日历日记」:月历网格一次显示 10 周(10 行 × 7 天,周一开头),格子里直接显示当天内容(超出一格的部分裁切,鼠标悬停看全文);有记录的日子带标记;可左右切月、回到今天;点某天打开编辑框写 / 改 / 删(保存、Ctrl+Enter、删除本条)。 - 数据文件一栏:显示当前数据文件路径,「更改…」可换(只换指向,不搬数据)。 - 导入:选 .xlsx / .xls → 先预览(来源、行数、日期范围、新增 / 冲突 / 未变 / 跳过,冲突逐条列出)→ 选冲突策略(默认保留现有)→ 确认后才写盘,写前自动备份。 - 导出:范围「全部 / 某年 / 某月」→ 写出同构的 .xlsx,只写新文件、绝不动数据文件;目标若就是当前数据文件本身会被拒绝(导出不备份,覆盖等于把范围外的天数一次删光)。 安装 需要 DSH(桌面版或网页版均可;本插件同时有宿主半与客户端半)。
展开完整文档(README 剩余 1 节)
dsh-calendar-diary(日历日记)

一个纯记事本式的 DSH 插件:一天一条,写在你自己的一个 .xlsx 里。侧栏一个月历面板(一次显示 10 周)。

没有提醒、没有通知、没有标签、没有搜索、没有云同步,也不联动官方「自动化任务」。除了你指定的那个 .xlsx 和插件自己的配置目录,它不写别的地方,也不联网。

功能

- 侧栏「日历日记」:月历网格一次显示 10 周(10 行 × 7 天,周一开头),格子里直接显示当天内容(超出一格的部分裁切,鼠标悬停看全文);有记录的日子带标记;可左右切月、回到今天;点某天打开编辑框写 / 改 / 删(保存、Ctrl+Enter、删除本条)。
- 数据文件一栏:显示当前数据文件路径,「更改…」可换(只换指向,不搬数据)。
- 导入:选 .xlsx / .xls → 先预览(来源、行数、日期范围、新增 / 冲突 / 未变 / 跳过,冲突逐条列出)→ 选冲突策略(默认保留现有)→ 确认后才写盘,写前自动备份。
- 导出:范围「全部 / 某年 / 某月」→ 写出同构的 .xlsx,只写新文件、绝不动数据文件;目标若就是当前数据文件本身会被拒绝(导出不备份,覆盖等于把范围外的天数一次删光)。

安装

需要 DSH(桌面版或网页版均可;本插件同时有宿主半与客户端半)。dsh plugin 会把剩余参数原样转发给 profile 目录里的 pnpm,所以 --profile 是它自己的选项,必须写在 add 之前(写成 plugin add … --profile desktop 会报 required option '--profile <name>' not specified)。

方式一:从 GitHub

& '<DSH 安装目录>\resources\runtime\cli\bin\dsh.cmd' plugin --profile <profile> add "github:liwangzimo/dsh-calendar-diary" --config.minimumReleaseAge=0

方式二:克隆到本地后按目录安装(改代码即生效,但要重启)

git clone https://github.com/liwangzimo/dsh-calendar-diary.git
& '<DSH 安装目录>\resources\runtime\cli\bin\dsh.cmd' plugin --profile <profile> add "link:<克隆下来的目录>" --config.minimumReleaseAge=0

--config.minimumReleaseAge=0 只放宽这一次命令的供应链策略(DSH 的 profile 默认拒绝"太新"的包)。不加可能因 ERR_PNPM_MINIMUM_RELEASE_AGE_VIOLATION 失败。

装完必须再做一步:注册 bundle

dsh plugin add 只加依赖。还要在 profile 的 package.json 里把插件登记进 dsh.profile.bundles,即在这个数组里加一行字符串:

"dsh": {
"profile": {
"bundles": [
"…", "dsh-calendar-diary" ] } }

只装依赖不登记 bundle 是不会加载的。 两处都改完后,完全退出并重开 DSH——本插件不支持热更新(刷新页面、关窗重开都无效,客户端代码是在启动时打包进图的)。

重启后确认生效:侧栏出现「日历日记」面板,或打开 http://<DSH 地址>/dsh-calendar-diary/state 看到 JSON。

回滚

& '<DSH 安装目录>\resources\runtime\cli\bin\dsh.cmd' plugin --profile <profile> remove dsh-calendar-diary

再把 dsh.profile.bundles 里那行删掉,重启。

数据格式

数据文件是一个 .xlsx,默认位置是你用户目录下的 .dsh/dsh-calendar-diary/diary.xlsx(第一次运行时创建;面板里可改):

| 项 | 值 |
| 工作表 | DesktopCal |
| A 列 | 整数 Excel 日期序列号(1900 系统),单元格格式固定 m/d/yy(显示成 11/25/26) |
| B 列 | 自由文本,可多行(\r\n),时间直接写在文本里 |
| 行序 | 日期降序;一天最多一行 |

这个形状与桌面日历软件 DesktopCal 导出的两列表一致,所以老数据可以直接导入。

为什么数据文件只写 .xlsx 而不是 .xls:把上千行写回 .xls 会静默截断长度超过 255 字符的单元格,不报错、不提示。写 .xlsx 实测 0 处值差异、0 处格式差异、0 处文本差异。所以导入收 .xls,但数据文件只写 .xlsx。

HTTP 路由(宿主半注册,客户端同源 fetch)

客户端不依赖任何会话或命令通道,只用相对路径 fetch(..., { cache: 'no-store' }) 调这些路由:

| 方法 | 路径 | 说明 |
| GET | /dsh-calendar-diary/state | 数据文件路径、是否存在 / 可写、总行数、有记录的月份(降序)、今天 |
| GET | /dsh-calendar-diary/entries?month=YYYY-MM | 该月条目 [{ date, serial, text }] |
| POST | /dsh-calendar-diary/entries | { date, text } 写入 / 覆盖一天;text:'' 置空但保留行 |
| POST | /dsh-calendar-diary/entries/remove | { date } 删掉该行 |
| POST | /dsh-calendar-diary/path | { dataPath } 换数据文件(校验是可用日记、拒绝 .xls) |
| POST | /dsh-calendar-diary/pick-dir | 原生文件夹对话框(不可用时返回 {ok:false,error},界面回退到手输) |
| POST | /dsh-calendar-diary/list-files | { dir } 列出候选 .xlsx / .xls |
| POST | /dsh-calendar-diary/import/scan | 只读预览导入,不写盘 |
| POST | /dsh-calendar-diary/import/apply | { sourcePath, policy } 执行导入(先备份再原子写) |
| POST | /dsh-calendar-diary/export | { scope, value, outPath } 导出新 .xlsx |

错误一律返回 JSON:{ ok:false, error:'' } + 4xx/5xx。方法不匹配返回 405,并在 JSON 里给出 allow。

文件

| 文件 | 作用 |
| index.js | 宿主半:注册上面 10 条路由,持有全部文件读写 |
| diary-io.js | I/O 层:读 / 原子写 / 备份 / 导入 / 导出(只用 node:fs + xlsx,不碰 ctx,所以能在纯 Node 里验证) |
| diary-store.js | 纯数据层:序列号↔日期、解析、排序、upsert / remove、导入合并策略(无 I/O、无时钟) |
| client.js | 浏览器半:月历面板 + 日编辑框 + 导入导出 |
| locale/zh.json、locale/en.json | 界面文案(键集合两边完全一致) |
| cordis.patch.yml | loader 补丁:一行把宿主半挂上(package.json 的 dsh.bundle.patch 指向它) |
| tests/diary-store.test.mjs | 数据层单测(含用真实 DesktopCal 导出测出的序列号锚点) |
| tools/migrate.mjs | 从 .xls 迁移到 .xlsx 并做 0 差异校验的一次性工具 |

开发与自测

node --test tests/diary-store.test.mjs # 数据层单测(纯函数,无 I/O)
node tools/migrate.mjs --help # 迁移工具用法

宿主半的路由可以用假 req/res 在纯 Node 里驱动,不需要启动 DSH。

已知边界(都是有意的,不是待办)

- 一天只保留一行。如果数据文件里同一天被人手工塞了两行,读取时按「首行优先」取一行;下一次任何写入都会按这个结果重写整个文件,也就是那一行会从正式文件里消失。它仍在那一次写入生成的 .bak-<时间戳> 里,所以可恢复。本插件自己不会产生重复行。
- 「必须先预览再导入」是客户端门槛。宿主半按设计无状态:/import/apply 单独调用也会执行(但不支持按天逐个决策)。这条防线在 UI 上,不在协议上。
- 相对路径按插件主目录(~/.dsh/dsh-calendar-diary)解析,不按宿主进程的工作目录——否则同一个相对路径会随启动方式指向不同地方。
- 写入失败不会留下垃圾:临时文件在失败时被清掉,数据文件本身只在最后一步 rename 时才会被替换,所以「写失败」永远不等于「文件损坏」。失败时仍可能已经生成了一份 .bak-。
- 两位数年份的文本日期(如 11/25/26)一律按 20xx 解释,与 Excel 在这段日期范围内的行为一致。
- 每个进程首次写入前做一次备份(diary.xlsx.bak-<yyyyMMdd-HHmmss>),同一次运行内不重复备份。
- 10 周视图下格子会偏小:面板越窄(尤其编辑框并排时)每格越窄,「格子里显示内容」只是提示,全文以悬停提示或点开编辑框为准。

许可

MIT
预览分享卡片长什么样 ↓liwangzimo/dsh-calendar-diary
分享 · DeepSeek Harness Hub
liwangzimo/dsh-calendar-diary

在侧栏月历上按天写日记,存进自己的 Excel 文件

这个插件是你维护的吗?
作者本人可认领并核对本条目;认领通过后,详情页会显示「作者已认领」标记。
认领条目 →
回到顶部