You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

60 lines
4.7 KiB
Markdown

# Windows SSH 一键部署设计
## 目标
在开发机执行一个 PowerShell 命令完成前端和后端构建、上传、备份、发布、后端重启、Nginx 平滑重载以及基础可用性检查。目标服务器为 Windows使用已验证可连接的 OpenSSH 服务。
## 范围与约束
- 开发机工作区:`E:\workspace\dianshang`。
- 前端工程:`e-commerce-internet`,使用 `npm run build:prod`,产物为 `dist`
- 后端工程:`link_commerce`,使用 Maven 构建,目标 JAR 为 `link_commerce-2.7.12.jar`
- 服务器通过 SSH 以 `Administrator` 账号连接;主机地址不得硬编码在可提交的私密配置中以外。
- 前端发布目录:`D:\nginx-1.19.3.1\html\dist`。
- 后端发布目录:`D:\dianshang-test-http-deploy-20260629-093129`。
- Nginx 根目录:`D:\nginx-1.19.3.1`,发布时必须先执行 `nginx -t`,成功后才执行 `nginx -s reload`
- 后端监听端口:`7548`。
- 不在部署脚本、Git 跟踪文件、日志或命令行参数中保存数据库密码。
## 方案
采用「SSH + 服务器启动脚本 + Windows 计划任务」:
1. 本地部署入口读取未跟踪的 `deploy.local.psd1`其中只包含服务器地址、用户名、SSH 私钥路径等非代码环境信息。
2. 入口先验证 `ssh`、`scp`、Node.js 与 Maven 可用,再顺序构建前端和后端;任一构建失败即停止,绝不上传旧产物。
3. 入口为本次发布生成唯一临时目录,将前端 `dist` 和 JAR 打成 ZIP 后通过 SCP 上传至服务器临时目录。
4. 远程发布脚本先解压到同盘临时目录,校验前端入口文件和 JAR 存在后,再分别把当前前端目录与 JAR 复制到带时间戳的备份目录。
5. 远程脚本仅停止命令行中明确匹配目标 JAR 的 Java 进程,避免误杀其他 Java 程序;随后替换前端目录和 JAR。
6. 后端由服务器本地 `Start-CommerceBackend.ps1` 启动。该脚本从仅服务器可读的 `backend.private.ps1` 加载数据库连接参数,在后台启动 Java并将标准输出和错误输出写入后端目录的 `logs`。计划任务 `CommerceBackend` 负责机器启动时运行该启动脚本;发布脚本通过 `schtasks /Run` 重启它。
7. 远程脚本等待 `7548` 端口监听如未就绪则返回错误和日志路径。Nginx 配置语法检查成功后执行平滑重载,并以本机 HTTP 请求确认 Nginx 可响应。
8. 失败时不删除备份;远程脚本报告备份路径和失败阶段。自动回滚不纳入第一版,以避免在未知的业务启动失败场景下覆盖调查证据;提供一个显式 `rollback.ps1` 入口作为后续可选操作。
## 文件边界
- `deploy/deploy.ps1`:开发机的一键入口;只负责编译、打包、传输、调用远程脚本与汇总结果。
- `deploy/deploy.local.psd1.example`:可提交的配置模板,不含凭据;真实 `deploy.local.psd1` 被忽略。
- `deploy/server/Initialize-CommerceDeployment.ps1`:仅首次执行;创建服务器目录、私密配置模板、启动脚本和计划任务。
- `deploy/server/Publish-Commerce.ps1`:每次发布执行;解压、备份、切换文件、重启后端并重载 Nginx。
- `deploy/server/Start-CommerceBackend.ps1`:只在服务器上运行;从私密配置读取 Spring 启动参数并启动 JAR。
- `deploy/tests/DeployScript.Tests.ps1`Pester 测试,以模拟 SSH/SCP 与临时目录验证入口的命令构造、失败中止和不泄露私密配置。
## 配置与安全
- 使用专用 SSH 密钥;私钥保存在开发机用户目录并由 `deploy.local.psd1` 引用。脚本不读取或记录登录密码。
- `backend.private.ps1` 仅存在于服务器后端目录,包含数据源 URL、用户名与密码应只允许 `Administrator` 读取,且不通过 SCP 回传。
- 先前在聊天中暴露过的数据源密码需要由管理员尽快轮换,然后将新值仅写入服务器的私密配置。
- 远程命令的路径均采用固定、已给定的绝对路径,不接受来自发布包的可执行命令。
## 验证
- 本地Pester 验证部署脚本在构建失败时不触发 SCP在成功路径下构造正确的远程调用且日志文本不包含私密配置字段。
- 本地:执行前端构建与 Maven 打包,确认产物存在。
- 服务器初始化:确认计划任务存在且启动脚本可读取私密配置。
- 发布:确认新的前端 `index.html` 与后端 JAR 已到位,`7548` 监听,且 `nginx -t` 和 HTTP 检查成功。
## 非目标
- 不自动执行数据库 SQL 或结构迁移。
- 不修改 Nginx 反向代理规则;仅测试并平滑重载现有配置。
- 不在第一版接入 CI/CD、Git 标签或多服务器滚动发布。