Smail/docs/管理员重置命令限制验收.md
smail 97c815deb0
Some checks are pending
Security Checks / security (push) Waiting to run
限制管理员重置为显式启动并隔离终端输入
2026-09-19 23:43:25 +08:00

51 lines
3.7 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# 管理员重置命令限制验收
日期:2026-09-19。
## 需求与任务状态
- [✓] 仅显式 `systemctl start smail-admin` 进入重置流程,`systemctl stop smail-admin` 终止流程。
- [✓] `restart`、`reload` 及相关变体不能开启新的重置交互。
- [✓] 交互绑定启动终端,取消后无系统共享密码请求残留。
- [✓] 保留邮箱、动态码、安全码验证及受保护本机 IPC,不调整账户密码或生产数据库。
- [✓] Windows 定向测试、Linux 测试、服务器实际命令验证和部署完成。
## 原因与修改
systemd 会将 `restart` 的启动阶段转换成 `start` Job,因此只检查 `list-jobs` 无法识别原始动作。`Restart=no` 只禁止自动重启,不限制管理员手工重启。`reload` 本身已被拒绝,但 systemctl 创建的密码代理会显示已有的系统共享输入请求。
管理程序现在要求唯一、本机 root、前台终端的显式 `systemctl start smail-admin` 进程,同时校验可执行文件、参数、进程启动时间及终端设备,继续保留 systemd 上下文及本机 IPC 校验。非交互启动、多服务、通配符、并发启动及重启命令均不授权。
输入直接绑定启动终端,验证内容可见,新密码不回显。保留终端行编辑、信号和换行设置,避免停止过程中与 shell 的终端恢复竞争。监测原启动进程退出或 PID 复用,取消输入并关闭连接。服务使用 `KillMode=mixed`,主进程先处理取消,再由 systemd 兜底清理。
## 实机验证
环境:部署服务器的 systemd 259,使用两个独立 SSH 终端;只进入菜单或输入无效选项,没有发送邮件或执行真实改密。
| 场景 | 实际结果 |
| --- | --- |
| `start` | 显示安全验证方式列表,仅启动终端可见 |
| `stop` | 流程终止,`inactive`、`Result=success`,终端模式正常 |
| Ctrl+C | systemctl 退出,管理程序随后结束,无遗留输入请求 |
| 未运行时 `restart` | 拒绝启动,退出码 1,无验证菜单 |
| 正在输入时 `restart` | systemd 先终止现有流程;新启动被拒绝,不重新显示菜单 |
| `reload` | systemd 报不支持;另一终端现有输入不被接管,原流程可继续 |
| `reload-or-restart` | 拒绝启动,退出码 1,无验证菜单 |
| 未运行时 `try-restart`、`try-reload-or-restart` | systemd 返回成功但不执行动作,管理进程 PID 为 0 |
| 无效选项及结果提示 | 显示失败原因,按回车结束 |
| 系统密码请求目录 | 验证期间及结束后均无本次重置产生的 `ask.*` |
## 自动化验证
- 本机:`go test ./services/adminreset ./cmd/smail-admin` 通过。
- Linux:交叉编译后的 `adminreset` 完整测试在服务器隔离目录运行通过。
- 覆盖显式命令、危险参数变体、进程启动时间/PID 重用、root 身份、真实伪终端输入、密码无回显、输入取消和终端恢复。
- `go vet ./services/adminreset ./cmd/smail-admin`、`git diff --check` 通过。
- unit 校验通过;systemd 对现有其他服务的 `CPUAccounting` 弃用提示与本次修改无关。
## systemd 行为边界
systemd 没有独立禁止手工 `restart`、同时允许 `start`/`stop` 的 unit 指令。因此不能删除 systemctl 自身的命令,也不能阻止它先执行重启的停止阶段。本次保证这些命令无法启动或重新进入重置流程。只读的 `status`、`show` 和日志查询继续可用。
原始命令检查约束正常部署操作,不构成对主机 root 的隔离;安全凭据验证和受保护本机 IPC 必须独立保留。验证二进制保存在 `/run/smail-command-validation-20260919/`,部署前备份保存在 `/var/backups/smail-admin-command-20260919/`。