Bundle
@dsh-external/dsh-night-greeting
一个在晚上随机向你问好的插件
- Source
- HokkaidoCOLA
- stars
- 1 stars
- License
- BSD-3-Clause
- Updated
- Updated 2 days ago
Readme
# dsh-night-greeting
> 这是一个在晚上随机向你问好的插件。
在深夜时分,它可能会突然出现,轻轻地向你道一声「晚上好」。
## 环境要求
| 项目 | 要求 |
|------|------|
| 运行时 | DeepSeek Harness (DSH) 0.1.x(0.1.0-rc.6 及以上均可) |
| Node.js | ≥ 20(实测 22.x 可用) |
| 平台 | Windows / macOS / Linux |
| 前置插件 | 无 |
> 插件运行在 DSH 宿主进程内,`cordis`、`@deepseek-ai/dsh-tools` 等依赖
> 由 DSH 宿主提供(plugin 以 `peerDependencies` 声明)。其中
> `@deepseek-ai/dsh-tools` **同时声明为普通 dependency**:这样即使宿主以
> `link:`/本地目录方式装配插件,插件也能在自身 `node_modules` 内解析到它,
> 不会因解析失败导致宿主启动崩溃。
## 安装
### 方式 A:git 装配(推荐)
```bash
dsh plugin --profile web add github:HokkaidoCOLA/dsh-night-greeting
```
> 本包在 `package.json` 中声明了 `dsh.bundle`,因此 `dsh plugin add` 安装后
> **自动并入 profile 的 bundle 层并激活**——设置页插件清单、工具与问候功能
> 全部就绪,**无需手动编辑任何 `cordis.patch.yml`**(重启 web 后生效)。
>
> `--profile web` 指装配到 web 配置;headless / tui 等其他 profile 同理替换。
### 方式 B:Release 包(免构建)
从 [Releases](https://github.com/HokkaidoCOLA/dsh-night-greeting/releases) 下载
`dsh-external-dsh-night-greeting-<版本>.tgz`,解压后:
```bash
dsh plugin --profile web add <解压目录>
```
### 方式 C:本地源码(开发调试)
```bash
# 先在仓库根目录安装依赖并构建(依赖锁定在 package-lock.json,推荐 npm ci)
npm ci
npm run build
# 再装入目标 profile(bundle 声明同样会自动激活)
dsh plugin --profile web add ./dsh-night-greeting
```
> ⚠️ **`node_modules` 不在仓库内**(见 `.gitignore`)。若把它删除或重新克隆后
> 未安装依赖就装配插件,DSH 将解析不到 `@deepseek-ai/dsh-tools` 而启动失败。
> 重新克隆后请先执行 `npm ci`(或 `npm install`)再装配。
## 使用
安装后无需任何操作——它会在晚上(北京时间 00:00–04:00)每小时以 1/100 的概率
随机向你问好。你也可以对 AI 说"帮我触发晚上好问候"
(`night_greeting_trigger` 工具)。
### 提供的工具
| 工具名 | 用途 |
|--------|------|
| `night_greeting_trigger` | 立即向你问好(演示/强制触发) |
| `night_greeting_status` | 查询插件状态与配置 |
### 配置项(可选)
安装即用,无需配置。如需调整,在 `~/.dsh/profiles/web/cordis.patch.yml`
按 id 覆盖该行配置(`name` 必须使用真实包名
`@dsh-external/dsh-night-greeting`):
```yaml
- id: dsh-night-greeting
config:
probability: 0.01 # 每小时问候概率(0..1)
startHour: 0 # 问候时段起点(北京时间,含)
endHour: 4 # 问候时段终点(北京时间,不含)
text: 晚上好 # 问候文本
color: '#ff2020' # 问候颜色
autoDismissMs: 0 # 自动关闭毫秒;0 = 等待手动关闭
pollIntervalMs: 10000 # 浏览器端轮询间隔(问候时段内)
idlePollIntervalMs: 60000 # 浏览器端轮询间隔(问候时段外)
checkIntervalMs: 60000 # host 端掷骰检查间隔
expireOutsideWindow: true # 自动命中的问候离开时段后作废(只在深夜炸)
pendingMaxAgeMs: 0 # 待显示问候的最长挂起时长;0 = 不按时长作废
```
> 配置经 schemastery `Config` schema 校验:非法值(如概率 > 1、时段越界)
> 会在加载时报错而不是静默带病运行;未填写的项自动使用默认值。
### 轮询节奏
问候只可能出现在 `[startHour, endHour)` 这段时间里,其余时段的轮询注定为空,
因此浏览器端的节奏由 host 在 `/state` 响应里用 `nextPollMs` 指定,分三档:
| 情形 | 间隔 | 说明 |
| --- | --- | --- |
| 正在显示问候 | 5s | 让多个标签页之间的关闭动作及时同步 |
| 在问候时段内 | `pollIntervalMs`(10s) | 命中后尽快显示 |
| 在问候时段外 | `idlePollIntervalMs`(60s) | 不可能命中,只需能感知手动触发 |
此外浏览器端**标签页不可见时完全挂起轮询**(不留定时器、不发请求),回到前台
时立即补一次。默认时段下,一天的请求量从约 8640 次降到约 2640 次,后台标签页
则降到 0。
这条不只是省流量,更是为了**让惊吓真正生效**:浏览器会拒绝后台标签页的
`requestFullscreen()`,并把 `AudioContext` 保持在 `suspended`。若在后台就把
overlay 搭好,黑屏 → 文字墙的时序会在没人看的时候演完、也没有声音,等用户切回
来只剩一具静止的残骸。改成「切回前台再当场炸」后,全屏、音墙、完整时序都在用户
眼皮底下发生。
### 过期:只在深夜炸
因为后台不轮询,命中的那一发会一直存在 host 上。若不清理,凌晨 2 点掷中、标签页
挂了一整夜,用户上午 9 点切回来会被补炸一发——深夜氛围荡然无存。
因此**自动命中的问候一旦离开问候时段就作废**(`expireOutsideWindow: true`,
宁可白丢一发);也可用 `pendingMaxAgeMs` 再加一道「最长挂起时长」。
> **手动触发不受此限。** `night_greeting_trigger` 工具与 `POST /trigger` 会把这
> 一发标记为 `forced`,白天演示照样弹得出来——否则过期逻辑会把演示当场清掉、
> 让工具看起来像坏了。`night_greeting_status` 会报出 `forced` 字段便于分辨。
把 `expireOutsideWindow` 设为 `false` 即可回到旧的「惊吓存盘」行为。
## 开发
本仓库按 DSH 官方插件规范编写:
- **Cordis 插件形态**:`name` / `inject` / `apply` 函数导出;
- **配置声明**:schemastery `Config`(loader 校验 + 填默认值);
- **工具注册**:`@deepseek-ai/dsh-tools` 的 `defineTool`(参数类型化 + 执行前校验);
- **生命周期**:所有注册挂在 `ctx.effect` 上,热重载/卸载自动清理;
- **双面打包**:`dsh.client` + `./client` 导出(浏览器端零依赖轮询渲染);
- **自动激活**:`dsh.bundle.patch` 声明(安装即并入 profile 层)。
```bash
npm install # 安装构建依赖(host 类型 + client 打包器)
npm run build # tsc 编译 host → lib/,tsdown 打包 client → lib/client.js
npm run typecheck
```
> 说明:官方 `adding-a-package` 规范中 `@deepseek-ai/cordis` 同时出现在
> peerDependencies 与 devDependencies(本仓库已遵循)。
## 常见问题
- **装完没生效?** 确认已重启 web;检查设置页插件清单中该插件为已启用状态。
- **报 peerDependency 错误?** 确认 DSH 版本满足 [环境要求](#环境要求)。
- **想改默认行为?** 按 [配置项](#配置项可选) 在 profile 层覆盖。
## License
MITInstall
dsh plugin --profile web add github:HokkaidoCOLA/dsh-night-greeting
Profile: web
With the hub plugin installed, ask your agent to install it by name — it resolves the same plan shown here.
dsh plugin --profile web add github:stvlynn/dsh.fish#path:packages/dsh-plugin-hub
install dsh-external-dsh-night-greeting from the hub
- This package builds from source on install. pnpm will ask you to allow its build script — that is permission to run the package’s code on your machine, outside the agent sandbox. Only allow sources you trust.
- This source has no pinned commit, so a later push upstream changes what installs. Prefer pinning a commit.