docs: 确认全部默认项并补充发布、许可证和最低版本要求

This commit is contained in:
Nixevol
2026-09-30 05:22:15 +08:00
parent 2ab09507ff
commit 6daaa95f1f
5 changed files with 74 additions and 38 deletions
+28 -18
View File
@@ -1,6 +1,6 @@
# NixMsg 开发说明
读者是实现本期功能的开发组。产品行为以 [PRD.md](./PRD.md) 为准,本文对应 PRD 0.4,规定怎么实现。两者冲突时改代码以 PRD 为准,并把差异写进 `docs/DEVIATIONS.md`(日期、原条款、实际做法、原因),交给后续审核。
读者是实现本期功能的开发组。产品行为以 [PRD.md](./PRD.md) 为准,本文对应 PRD 0.5,规定怎么实现。两者冲突时改代码以 PRD 为准,并把差异写进 `docs/DEVIATIONS.md`(日期、原条款、实际做法、原因),交给后续审核。
文中「必须」是验收项,「不要」是已知会做错的实现。本文对 mochi-mqtt、coder/websocket、autopaho、modernc sqlite 内部行为的说明,已在 2026-09-30 对照它们主分支的源码核对过;升级这些依赖的大版本时要重新核对。
@@ -56,6 +56,10 @@ flowchart LR
| 部署 | 单文件二进制为主,同时提供 Docker 镜像(`linux/amd64`、`linux/arm64`)和 docker-compose 示例 | 第 11 节 |
| 监控 | Prometheus 格式的 `/metrics` | 访问限制见第 4.3 节 |
| 证书 | 程序读取证书文件,文件变了自动重载 | 生产环境由 1Panel 申请和自动续签,推送到本地目录给程序读(第 11.3 节) |
| SDK 发布 | 发布到 Gitea 包仓库(git.asio.asia,所有者 nixevol):npm `@nixevol/nixmsg`、PyPI `nixmsg`、Maven `asia.asio.nixmsg:nixmsg-sdk`;Go SDK 直接从代码仓库获取,模块 `git.asio.asia/nixevol/NixMsg/sdk/go` | 第 9 节 |
| Docker 镜像 | 推到 Gitea 容器仓库 `git.asio.asia/nixevol/nixmsg` | 第 11.4 节 |
| CI | 本期不做;总控合并前在本机跑全量验证 | TASKS.md 第 4.3 节 |
| 许可证和可见性 | 专有许可证,见仓库根目录 `LICENSE`;源码仓库、SDK 包、镜像都公开可读,公开不代表授权使用 | 各 SDK 的包信息写同样的许可证 |
### 2.2 按推荐定下的其余部分
@@ -82,12 +86,12 @@ flowchart LR
这里只列各语言 SDK 依赖的 MQTT 客户端库,SDK 的行为见第 9 节。
| SDK | 依赖 | 说明 |
|---|---|---|
| Go | `github.com/eclipse/paho.golang/autopaho` | MQTT 5、自动重连、支持 WebSocket |
| JS/TS | MQTT.js 5.x | 浏览器和 Node 都能用 |
| Python | paho-mqtt 2.x,`CallbackAPIVersion.VERSION2` | 同步接口为主,另给 asyncio 包装 |
| Java/Android | HiveMQ MQTT Client,加上 websocket 模块 | Java 8+,Android API 24+ |
| SDK | 依赖 | 说明 | 最低支持 |
|---|---|---|---|
| Go | `github.com/eclipse/paho.golang/autopaho` | MQTT 5、自动重连、支持 WebSocket | 和服务端相同的 Go 版本 |
| JS/TS | MQTT.js 5.x | 浏览器和 Node 都能用 | Node.js 20;近两年发布的 Chrome、Edge、Firefox、Safari |
| Python | paho-mqtt 2.x,`CallbackAPIVersion.VERSION2` | 同步接口为主,另给 asyncio 包装 | Python 3.10 |
| Java/Android | HiveMQ MQTT Client,加上 websocket 模块 | 同一套 jar 给 Java 和 Android 用 | Java 8;Android API 24 |
### 2.4 后台界面
@@ -108,6 +112,7 @@ flowchart LR
- 帮助图标用 `n-tooltip`;错误和关键状态用 `n-alert` 或表单校验信息直接显示。
- 弹窗用 `n-modal`(`preset="card"`),按钮放在 `footer` 插槽,正文放进 `n-scrollbar` 单独滚动。
- 表格用 `n-data-table`:`remote` 做服务端分页,设 `max-height` 让表格内部滚动,长列表开 `virtual-scroll`。
- 所有时间按浏览器本地时区显示,格式 `YYYY-MM-DD HH:mm:ss`;接口里一律用 Unix 毫秒。
- 只用 Naive UI 一套组件库,不要混用 Element Plus 等其他库。
## 3. 仓库
@@ -248,7 +253,7 @@ Capabilities:
| 钩子 | 行为 |
|---|---|
| `OnConnect` | 分配连接代号,校正心跳,然后查编号、停用,按下文「登录与会话令牌」校验会话令牌或登录密码(含锁定),把结论记在这个连接上。数据库出错等内部故障时返回 error:mochi 不回 CONNACK 直接断开,客户端按网络故障重连 |
| `OnConnectAuthenticate` | 只返回 `OnConnect` 记下的结论。返回 false 时 mochi 回「用户名或密码错误」,SDK 会停止重连,所以只有编号不存在、已停用、密码错误、已锁定这几种情况能返回 false |
| `OnConnectAuthenticate` | 只返回 `OnConnect` 记下的结论。返回 false 时 mochi 回「用户名或密码错误」,SDK 会停止重连,所以只有编号不存在、已停用、密码错误、会话令牌无效或过期、已锁定这几种情况能返回 false |
| `OnACLCheck` | 只允许上面这一对主题。发布检查 `write=true`;订阅和服务器下发检查 `write=false` |
| `OnPublish` | 拷贝 topic 和 payload 后交给该端的串行队列。返回 `packets.CodeSuccessIgnore`,让客户端拿到 PUBACK,同时不把这条转发给任何订阅者 |
| `OnPublishDropped` | 下行没写进连接的发送队列。把对应投递或回执的「已推送」标记清掉,1 秒后重推,别对慢客户端空转 |
@@ -919,7 +924,7 @@ API 令牌,给接入方后台用程序调用管理接口:
所有 JSON 响应在序列化前去掉正文。测试里对管理接口的响应做一次「不含 body 字段」的检查。
`nixmsg serve` 发现库里没有管理员密码时拒绝启动,提示先运行 `nixmsg admin init`。不要自动生成密码再打到日志里。`admin init` 生成 20 位密码,只在终端打印一次,库里存哈希;已经初始化过的库拒绝执行,改用 `admin set-password`。
`nixmsg serve` 发现库里没有管理员密码时拒绝启动,提示先运行 `nixmsg admin init`。不要自动生成密码再打到日志里。`admin init` 生成 20 位密码,只在终端打印一次,库里存哈希;已经初始化过的库拒绝执行,改用 `admin set-password`。管理员密码至少 12 位,`admin set-password` 和 `/api/admin/password` 都要校验。
## 9. SDK
@@ -962,7 +967,7 @@ close()
- 发送队列在内存,默认最多 1000 条,包括已发出但没收到 `resp` 的。连不上时 `send` 入队;重连后按原消息号、原请求内容再交。
- `sendAt` 在调用 `send` 时就换算成 `send_at_ms`,重交时不重算,否则请求指纹变了会被当成冲突。
- 同时在途(已发出、没收到 `resp`)的请求不超过 100 个。发送收到 `rate_limited` 时按退避自动重交,不算失败;其他请求收到 `rate_limited` 直接返回给应用。
- 进程退出则队列丢失。SDK 停止重连(被踢、认证失败、`close`)时,队列里的发送全部以对应错误结束。
- 进程退出则队列丢失。SDK 停止重连(被踢、认证失败、`logout`、`close`)时,队列里的发送全部以对应错误结束。
- 其他调用在未握手时返回未连接。
接收:
@@ -984,14 +989,17 @@ close()
各语言包装:
| 语言 | 包 | 接口形态 |
|---|---|---|
| Go | `github.com/nixmsg/nixmsg-sdk-go` | context,方法返回 error |
| JS/TS | `@nixmsg/sdk` | Promise,ESM 和 CJS 都发 |
| Python | `nixmsg` | 同步为主;`asyncio` 包装放在同一包 |
| Java | `com.nixmsg:nixmsg-sdk` | `CompletableFuture`。Android 最低 API 24,长连接由应用自己放到前台服务 |
| 语言 | 包名 | 获取方式 | 接口形态 |
|---|---|---|---|
| Go | 模块 `git.asio.asia/nixevol/NixMsg/sdk/go`,包名 `nixmsg` | `go get git.asio.asia/nixevol/NixMsg/sdk/go@v0.1.0`(仓库打 `sdk/go/v0.1.0` 标签) | context,方法返回 error |
| JS/TS | `@nixevol/nixmsg` | Gitea npm 仓库 `https://git.asio.asia/api/packages/nixevol/npm/` | Promise,ESM 和 CJS 都发 |
| Python | `nixmsg`(导入名也是 `nixmsg`) | Gitea PyPI 仓库 `https://git.asio.asia/api/packages/nixevol/pypi/simple/` | 同步为主;`asyncio` 包装放在同一包 |
| Java | `asia.asio.nixmsg:nixmsg-sdk`(Java 包 `asia.asio.nixmsg`) | Gitea Maven 仓库 `https://git.asio.asia/api/packages/nixevol/maven` | `CompletableFuture`。长连接由 Android 应用自己放到前台服务 |
包名是占位。正式名称和发布渠道(GitHub 组织、npm scope、PyPI 名、Maven groupId)由负责人确认拥有权后再定。Go 模块路径必须和实际仓库地址一致,放在本仓库 `sdk/go` 下时就是「仓库路径/sdk/go」。
- Go SDK 放在 `sdk/go`,但 `go` 是关键字,包名用 `nixmsg`。它是仓库里单独的 Go 模块,版本标签带目录前缀(`sdk/go/v0.1.0`)。仓库公开,接入方直接 `go get`;公共代理访问不到 git.asio.asia 时,设 `GOPRIVATE=git.asio.asia` 直连。
- 接入方的配置:npm 在 `.npmrc` 里写 `@nixevol:registry=https://git.asio.asia/api/packages/nixevol/npm/`;pip 用 `--index-url` 指向上面的 PyPI 地址;Gradle 或 Maven 加上面的仓库地址。包是公开的,下载不用登录。
- 包信息里的许可证:npm 写 `"license": "SEE LICENSE IN LICENSE"`;PyPI 用 `license = { file = "LICENSE" }` 并加分类 `License :: Other/Proprietary License`;Maven 的 `<licenses>` 写 `Proprietary`。每个包都带上仓库根目录的 `LICENSE`。
- 发布只在阶段 3 由总控执行(TASKS.md Z3)。用 Gitea 个人访问令牌,只给 `package` 读写权限;令牌存进 MemRelay 密码库,只写在本机用户级配置里(用户目录下的 `.npmrc`、`.pypirc`、`.gradle/gradle.properties`),不进仓库。
接入清单(每种语言一份集成测试,对真实服务器二进制):
@@ -1082,6 +1090,7 @@ data/nixmsg.db
data/backup/
```
- 程序本身不做定时备份。用 1Panel 计划任务或 cron 定时执行 `nixmsg backup --out <路径>`;Docker 部署时执行 `docker compose exec nixmsg /nixmsg backup --out /data/backup/<文件名>.db`。旧备份按需要自己清理。
- 备份文件包含备份当时还没送完的正文,要按敏感数据保管。
- systemd 示例只需要 `ExecStart`、`WorkingDirectory`、`Restart=on-failure`。Windows 上用 WinSW、NSSM 之类的工具托管成服务,本期不在程序里内置服务安装。
- 服务器开启 NTP 对时。
@@ -1104,6 +1113,7 @@ data/backup/
### 11.4 Docker
- 镜像多阶段构建:Node 构建前端 → Go 编译(嵌入前端)→ `gcr.io/distroless/static` 的 `nonroot` 变体。入口是 `/nixmsg`。发布 `linux/amd64`、`linux/arm64` 两个架构。
- 镜像名 `git.asio.asia/nixevol/nixmsg`。每次发布打版本号标签(如 `0.1.0`)和 `latest`,用 `docker buildx` 一次推送两个架构。推送前 `docker login git.asio.asia`,用和 SDK 发布同一个 Gitea 令牌。镜像是公开的,部署服务器拉取不用登录。
- 容器里的路径:配置 `/etc/nixmsg/config.yaml`(`NIXMSG_CONFIG` 指向它),数据目录 `/data`(配置里写 `data_dir: /data`),证书目录 `/certs` 只读挂载。
- 首次使用先执行 `docker compose run --rm nixmsg admin init`,记下只打印一次的管理员密码,再 `docker compose up -d`。
- 容器以 uid 65532 运行:挂载的数据目录要可写,证书私钥要可读。
@@ -1112,7 +1122,7 @@ data/backup/
```yaml
services:
nixmsg:
image: nixmsg:0.1.0
image: git.asio.asia/nixevol/nixmsg:0.1.0
restart: unless-stopped
command: ["serve"]
environment: