# Windows 设备部署文档 ## 1. 环境要求 - Windows 10/11 或 Windows Server - Python 3.11 及以上 - Node.js 20 及以上 - smartmontools,且 `smartctl.exe` 已加入 `PATH` - 可选:LibreHardwareMonitor 或 OpenHardwareMonitor,用于提供更完整的 CPU/GPU/主板温度传感器 - 可选:NVIDIA 驱动自带 `nvidia-smi`,用于 NVIDIA 显卡负载、温度、显存和功耗 ## 2. 获取项目 将项目目录复制到目标设备,例如: ```powershell C:\Apps\win_monitor ``` 以下命令默认在项目根目录执行: ```powershell cd C:\Apps\win_monitor ``` ## 3. 安装 Python 依赖 建议使用虚拟环境: ```powershell python -m venv .venv .\.venv\Scripts\Activate.ps1 python -m pip install --upgrade pip python -m pip install -r backend\requirements.txt ``` 如果 PowerShell 禁止执行激活脚本,可先执行: ```powershell Set-ExecutionPolicy -Scope CurrentUser RemoteSigned ``` ## 4. 安装前端依赖并构建 ```powershell cd frontend npm install npm run build cd .. ``` 开发调试时可运行: ```powershell cd frontend npm run dev -- --port 5173 ``` 生产部署建议使用前端构建产物 `frontend\dist`,可由 Nginx、IIS 或其他静态文件服务承载。 ## 5. 安装 smartmontools 下载安装 smartmontools for Windows,并确认命令可用: ```powershell smartctl --version smartctl --scan ``` 如果提示找不到命令,请将 smartmontools 安装目录加入系统 `PATH`,常见路径类似: ```text C:\Program Files\smartmontools\bin ``` 项目也会自动尝试以下常见路径: ```text C:\Program Files\smartmontools\bin\smartctl.exe C:\Program Files (x86)\smartmontools\bin\smartctl.exe ``` 如果安装在其他目录,可设置环境变量: ```powershell $env:SMARTCTL_PATH="D:\Tools\smartmontools\bin\smartctl.exe" ``` JMB39x USB 阵列硬盘柜中的硬盘可使用类似命令验证: ```powershell smartctl -a -d jmb39x,0 /dev/sdb smartctl -a -d jmb39x,1 /dev/sdb ``` 本项目的 SMART 页面会在启用“探测 JMB39x 阵列槽位”后自动按槽位读取。 ## 6. 可选:启用更完整的温度传感器 Windows 原生接口经常无法直接提供 CPU、GPU 和主板真实温度。建议在目标设备上运行 LibreHardwareMonitor 或 OpenHardwareMonitor,并开启 WMI 暴露能力。 后端会尝试读取以下 WMI 命名空间: ```text root\LibreHardwareMonitor root\OpenHardwareMonitor ``` 如果没有这些组件,页面仍会展示 CPU/内存负载、NVIDIA 显卡信息、Windows GPU 性能计数器和可用的 ACPI 温度。 ## 7. 启动后端 开发或本机使用: ```powershell cd C:\Apps\win_monitor\backend ..\.venv\Scripts\python.exe -m uvicorn app.main:app --host 127.0.0.1 --port 8000 ``` 如果上一条命令因路径复制产生问题,请使用绝对路径: ```powershell C:\Apps\win_monitor\.venv\Scripts\python.exe -m uvicorn app.main:app --host 127.0.0.1 --port 8000 ``` 局域网访问: ```powershell C:\Apps\win_monitor\.venv\Scripts\python.exe -m uvicorn app.main:app --host 0.0.0.0 --port 8000 ``` 如需局域网访问,请在 Windows 防火墙中放行 TCP 8000 端口,并按实际安全要求限制访问来源。 ## 8. 启动前端 开发模式: ```powershell cd C:\Apps\win_monitor\frontend npm run dev -- --host 0.0.0.0 --port 5173 ``` 访问: ```text http://目标设备IP:5173 ``` 如果前端和后端不在同一台机器,或后端不是 `127.0.0.1:8000`,请在启动或构建前设置: ```powershell $env:VITE_API_BASE="http://目标设备IP:8000" npm run build ``` ## 9. 作为 Windows 服务运行后端 可使用 NSSM: ```powershell nssm install WinMonitorApi ``` 推荐配置: - Application path:`C:\Apps\win_monitor\.venv\Scripts\python.exe` - Startup directory:`C:\Apps\win_monitor\backend` - Arguments:`-m uvicorn app.main:app --host 127.0.0.1 --port 8000` 保存后启动: ```powershell nssm start WinMonitorApi ``` ## 10. 数据和日志 - SQLite 数据库位置:`backend\data\win_monitor.db` - 服务、进程和扫描记录会写入数据库。 - 传感器信息和 SMART 信息是实时读取,不写入数据库。 - 如果需要备份,只需停止后端后复制 `backend\data\win_monitor.db`。 ## 11. 项目自身会增加的进程 项目启动后,进程列表中会出现一些属于本项目自身或由本项目临时调用的进程。做服务/进程扫描结果确认时,可以将这些进程按实际部署方式标记为可信。 ### 后端常驻进程 使用以下命令启动后端时: ```powershell C:\Apps\win_monitor\.venv\Scripts\python.exe -m uvicorn app.main:app --host 127.0.0.1 --port 8000 ``` 通常会看到: | 进程名 | 说明 | | --- | --- | | `python.exe` | FastAPI 后端主进程,运行 `uvicorn app.main:app`,负责 API、扫描、传感器和 SMART 查询 | 如果使用 NSSM 注册为 Windows 服务,还会看到: | 进程名 | 说明 | | --- | --- | | `nssm.exe` | NSSM 服务包装器,用于托管后端 Python 进程 | | `python.exe` | 被 NSSM 启动的 FastAPI 后端主进程 | ### 前端开发模式进程 如果使用开发模式启动前端: ```powershell npm run dev -- --host 0.0.0.0 --port 5173 ``` 通常会看到: | 进程名 | 说明 | | --- | --- | | `node.exe` | Vite 前端开发服务器 | | `npm.cmd` / `cmd.exe` | 启动脚本外壳,某些启动方式下会短暂或持续存在 | 实际部署时,如果前端使用 `frontend\dist` 静态文件,并由 IIS、Nginx 或其他 Web 服务承载,则不会再有 Vite 的 `node.exe` 进程。此时前端相关进程取决于你选择的静态文件服务,例如 `nginx.exe` 或 IIS 的 `w3wp.exe`。 ### 实时查询产生的临时进程 访问传感器或 SMART 页面时,后端可能临时启动以下进程,执行完会退出: | 进程名 | 触发场景 | 说明 | | --- | --- | --- | | `smartctl.exe` | 打开或刷新硬盘 SMART 页面 | 读取硬盘 SMART 信息,包括 JMB39x 阵列槽位探测 | | `powershell.exe` / `pwsh.exe` | 打开或刷新传感器页面 | 读取 WMI 传感器、ACPI 温度或 Windows GPU 性能计数器 | | `nvidia-smi.exe` | 存在 NVIDIA 显卡并刷新传感器页面 | 读取 NVIDIA 显卡负载、温度、显存和功耗 | 这些临时进程一般只在接口请求期间出现,不属于常驻服务。如果扫描进程列表时刚好捕获到它们,可以结合命令行和父进程判断是否由本项目后端触发。 ### 最小常驻进程总结 推荐生产部署方式下,项目自身最少只需要: | 进程名 | 是否常驻 | 用途 | | --- | --- | --- | | `python.exe` | 是 | 后端 API 服务 | | `nssm.exe` | 是,可选 | 仅当使用 NSSM 托管后端服务时出现 | | `nginx.exe` / `w3wp.exe` / 其他静态服务进程 | 是,可选 | 仅当前端由独立静态 Web 服务承载时出现 | 不建议在生产环境长期使用 `npm run dev`,因为它会额外保留 `node.exe` 开发服务器进程,适合调试,不适合作为正式前端服务。 ## 12. 结束程序 结束程序时,先确认你当前采用的是哪种启动方式。推荐优先使用启动方式对应的正常停止命令,避免直接结束无关的 `python.exe`、`node.exe` 或 Web 服务进程。 ### 命令行窗口中启动的后端 如果后端是在 PowerShell 或 CMD 窗口中用以下方式启动的: ```powershell python -m uvicorn app.main:app --host 127.0.0.1 --port 8000 ``` 在该窗口按: ```text Ctrl + C ``` 即可停止后端。 如果窗口已经关闭但进程仍在,可按端口查找并停止: ```powershell $pid = (Get-NetTCPConnection -LocalPort 8000 -State Listen).OwningProcess Stop-Process -Id $pid ``` ### NSSM 服务方式启动的后端 如果后端注册成了 NSSM 服务,例如服务名是 `WinMonitorApi`: ```powershell nssm stop WinMonitorApi ``` 或使用 Windows 服务命令: ```powershell Stop-Service WinMonitorApi ``` 如需禁止开机自启: ```powershell Set-Service WinMonitorApi -StartupType Manual ``` 如需彻底删除该服务: ```powershell nssm remove WinMonitorApi confirm ``` ### 前端开发服务器 如果前端是开发模式启动的: ```powershell npm run dev -- --host 0.0.0.0 --port 5173 ``` 在该窗口按: ```text Ctrl + C ``` 即可停止前端开发服务器。 如果窗口已经关闭但 `node.exe` 仍在监听 5173 端口,可执行: ```powershell $pid = (Get-NetTCPConnection -LocalPort 5173 -State Listen).OwningProcess Stop-Process -Id $pid ``` ### 静态 Web 服务方式部署的前端 如果前端由 Nginx 承载: ```powershell nginx -s stop ``` 如果前端由 IIS 承载,可停止对应站点,或停止 IIS: ```powershell Stop-Website -Name "WinMonitor" ``` 如果需要停止整个 IIS 服务: ```powershell iisreset /stop ``` 注意:`iisreset /stop` 会影响该设备上的所有 IIS 站点,使用前请确认没有其他业务依赖 IIS。 ### 临时查询进程 `smartctl.exe`、`powershell.exe` / `pwsh.exe`、`nvidia-smi.exe` 是由后端在刷新传感器或 SMART 页面时临时启动的查询进程,正常情况下会自动退出,不需要手动停止。 传感器接口已对外部命令设置超时,并会在超时后清理对应进程树。也就是说,由本项目后端启动的 PowerShell 查询进程不应该长期残留。 如果看到长期存在的 `powershell.exe` 或 `pwsh.exe`,请先查看它的父进程和命令行,确认是否属于本项目: ```powershell Get-CimInstance Win32_Process -Filter "name = 'powershell.exe' or name = 'pwsh.exe'" | Select-Object ProcessId, ParentProcessId, CreationDate, CommandLine | Format-List ``` 再查看后端进程 PID: ```powershell Get-CimInstance Win32_Process -Filter "name = 'python.exe'" | Where-Object { $_.CommandLine -like '*uvicorn app.main:app*' } | Select-Object ProcessId, ParentProcessId, CommandLine | Format-List ``` 如果 PowerShell 的 `ParentProcessId` 等于后端 `python.exe` 的 `ProcessId`,才说明它是本项目后端临时启动的查询进程。 如果某次硬盘或 WMI 查询卡住,可先停止后端;后端停止后仍残留且确认属于本项目的临时查询进程,再按需结束: ```powershell Get-Process smartctl,powershell,pwsh,nvidia-smi -ErrorAction SilentlyContinue ``` 确认是本项目触发且不再需要后,可结束指定 PID: ```powershell Stop-Process -Id 进程ID ``` ### 一次性检查项目是否仍在运行 检查后端端口: ```powershell Get-NetTCPConnection -LocalPort 8000 -State Listen -ErrorAction SilentlyContinue ``` 检查前端开发端口: ```powershell Get-NetTCPConnection -LocalPort 5173 -State Listen -ErrorAction SilentlyContinue ``` 如果没有输出,表示对应端口没有进程监听。 ## 13. 常见问题 ### 页面没有温度 优先确认 LibreHardwareMonitor/OpenHardwareMonitor 是否运行并开启 WMI。部分硬件或驱动不向 Windows 暴露温度,这是正常限制。 ### SMART 页面提示 smartctl 不存在 确认 smartmontools 已安装,并且 `smartctl.exe` 所在目录已加入系统 `PATH`。重新打开 PowerShell 后执行 `smartctl --scan` 验证。 ### JMB39x 槽位没有显示硬盘 先手动执行: ```powershell smartctl -a -d jmb39x,0 /dev/sdb ``` 将 `/dev/sdb` 替换为 `smartctl --scan` 中对应的阵列设备。如果手动命令能输出硬盘信息,页面刷新后也应能展示。