节点在线、应用在线、配置在线使用令牌查询
大石头 authored at 2021-12-16 19:49:30
7.30 KiB
Stardust
# DEPLOY-1 节点应用文件日志 > 版本:v1.0 | 日期:2026-11-03 > 关联:`Doc/NODE-9-指令下发.md`、`Doc/SVR-8-远程命令执行安全.md` > 状态:**P1 MVP 已实现**(2026-11-03) --- ## 1. 背景 运维需要在星尘控制台查看**部署在节点上的应用**写在本地的日志文件。现有能力无法替代: | 能力 | 局限 | |------|------| | 应用页签 **AppClientLog** | 需 SDK 上报,非文件 stdout | | 节点 **抓日志** | StarAgent 自身 XTrace,非业务应用 | | **bash/cmd** | 适合应急,不宜作为日常看日志入口 | ## 2. 目标 1. **AppDeploy** / **AppDeployNode** 配置日志目录(节点可覆盖部署集默认值)及文件匹配规则。 2. 控制台在「部署节点」行操作 **查看日志**:列文件、读尾部、手动刷新。 3. 经 **Node 指令通道**(WebSocket + 心跳备份)同步等待回包,**禁止**用 bash 拼 `tail`。 ## 3. 数据模型 ### AppDeploy(部署集默认) | 字段 | 类型 | 说明 | |------|------|------| | LogDirectory | String(500) | 日志目录;绝对路径,或相对 WorkingDirectory | | LogFilePattern | String(200) | 默认 `*.log` | ### AppDeployNode(部署节点,可覆盖) 同上两字段;合并规则与 `WorkingDirectory` 一致(节点为空 → 用部署集)。 解析(Agent 与平台一致): - `LogDirectory` 为空 → 不可查看,API 返回明确提示。 - 非根路径且非 `X:\` / `/` 开头 → 与 **EffectiveWorkingDirectory** 组合。 ## 4. Agent 指令 注册于 `ServiceManager.Attach`(StarAgent 进程): ### `deploy/log/list` 请求 JSON: ```json { "logDirectory": "D:/app/logs", "workingDirectory": "D:/app", "pattern": "*.log" } ``` 响应 JSON(写入 `CommandReplyModel.Data`): ```json { "files": [ { "name": "app.log", "size": 12345, "lastWriteUtc": "2026-11-03T02:00:00Z" } ] } ``` 限制:最多 100 个文件;路径必须在解析后的日志根目录内。 ### `deploy/log/tail` 请求 JSON: ```json { "logDirectory": "D:/app/logs", "workingDirectory": "D:/app", "file": "app.log", "offset": 0, "maxBytes": 262144 } ``` 响应 JSON: ```json { "content": "...", "offset": 0, "fileSize": 999999, "truncated": false } ``` 安全:`file` 仅允许文件名(无 `..`、无目录分隔符);读文件用 `FileShare.ReadWrite`;单次 maxBytes 上限 512KB(Agent 与 API 双端限制)。 ## 5. HTTP API(WebApi / Web) | 方法 | 路径 | 权限 | |------|------|------| | GET | `/Deployment/AppDeployNode/LogFiles?id={deployNodeId}` | Detail | | GET | `/Deployment/AppDeployNode/LogTail?id=&file=&offset=&maxBytes=` | Detail | 流程:加载 `AppDeployNode` → 合并日志配置 → `StarFactory.SendNodeCommandAsync(node.Code, command, args, timeout: 25)` → 解析回包 JSON。 ## 6. 前端(StardustLayout2 / Console) 完整交互、接口、验收见 **[DEPLOY-3-前端应用日志需求.md](/NewLife/Stardust/Blob/master/Doc/DEPLOY-3-前端应用日志需求.md)**。 - **NodeFormDrawer**:日志目录、文件匹配(部署节点 kind=deploy)。 - **DeployNodes**:「查看日志」→ **DeployLogDrawer**(文件选择、等宽展示、刷新 loading)。 - **ShipPanel**(应用工作台部署页):接线 `DeployLogDrawer`。 - 逻辑:**deployLog.logic.ts** + Vitest。 与 **AppClientLog** 页签区分:本能力为 **节点文件日志**。 ## 7. 分期 | 阶段 | 内容 | |------|------| | **P1 MVP** | 字段 + list/tail + API + 抽屉 + 手动刷新 | | **P2(2026-11-04 已交付)** | **MCP 查询工具** `stardust_deploy_log_files` / `stardust_deploy_log_tail`(L0/deploy,见 §11);抽屉**自动轮询开关 + 1~5 秒间隔**;**向上翻页**(加载更早,256KB/页,累计 2MB 上限,Agent offset=0 语义为读尾部故头部窗口用 offset=1);**下载当前窗口**(.log 文件);文件大小友好格式 | | **P3(2026-11-04 已交付)** | 准实时 tail:轮询增量追新(offset=上次 fileSize,内容封顶 1MB);SSE/WebSocket 留作后续可选增强 | | 遗留 | 更细离线/Agent 版本提示;P4 K8s:`kubectl logs`(待工作区在途 k8s 改动落库后再做) | ## 8. 本地联调 见 **[DEPLOY-2-本地应用日志联调环境.md](/NewLife/Stardust/Blob/master/Doc/DEPLOY-2-本地应用日志联调环境.md)**(`Doc/scripts/deploy-log/setup_local.py`、分层验证 L1/L2/L3)。 ## 9. 自动化测试(P1 关键路径) | 层级 | 工程 / 文件 | 覆盖 | |------|-------------|------| | Agent 指令 | `ClientTest/DeployLogCommandsTests.cs` | 路径解析、list/tail happy path、目录不存在、非法文件名 | | 配置合并 | `Stardust.WebApiTests/Areas/DeploymentDeployLogApiTests.cs` | `GetEffectiveLogDirectory` / Pattern 节点覆盖与回落 | | HTTP API | 同上 | 未配置目录、缺 file、无效 id;已配置时进入下发(无 Agent 则非「未配置」错误) | | 前端 logic | `deployLog.logic.test.ts` | parse / fetch 契约与失败透传;`applyTailSnapshot` 增量合并(追加/替换/回卷/1MB 封顶,14 用例) | | 部署节点表单 | `deploy.logic.test.ts` | logDirectory / logFilePattern 映射与 update body | | MCP 工具 | `Stardust.McpApiTests/DeployLogToolsTests.cs` | 未配置目录优雅空数据+note、节点不存在/缺 file/路径分隔符 -32602、非成员 -32003(6 用例) | | MCP 覆盖 | `Stardust.McpApiTests/McpToolCoverageTests.cs` | tools/list 计数 34;逐工具正路径(含两个新工具) | | 本机 E2E | `.temp/smoke_deploy_log.py` | 可选 L3,非 CI 门禁 | 全链路 **WebApi → StarServer → StarAgent → 磁盘** 仍依赖 DEPLOY-2 环境;未纳入 xUnit(成本高,用 L3 冒烟补)。 ## 10. 主要代码 | 层 | 路径 | |----|------| | 实体 | `Stardust.Data/Deployment/Model.xml`、`应用节点.Biz.cs` | | Agent | `Stardust/Managers/DeployLogCommands.cs`、`ServiceManager.cs` | | API | `AppDeployNodeController.cs`、`DeployService`(LogFiles/LogTail) | | MCP | `Stardust.Mcp/Tools/Deploy/DeployLogTools.cs`、`Stardust.Mcp/IMcpOperations.cs`(两宿主 `Services/McpOperations.cs`) | | 前端 | `deployLog.logic.ts`、`DeployLogDrawer.vue`、`ShipPanel.vue` | ## 11. MCP 工具(P2,2026-11-04) 供 MCP 客户端/Agent 助手查询节点文件日志,与 HTTP API 同底座(`DeployService.ListLogFilesAsync/TailLogFileAsync`): | 工具 | 风险/域 | 参数 | 返回 | |------|---------|------|------| | `stardust_deploy_log_files` | L0 / deploy | `deploy_node_id` | `data.files[]{name,size,last_write_utc}`;未配置目录 → 空列表 + `note` 说明(不下发节点指令) | | `stardust_deploy_log_tail` | L0 / deploy | `deploy_node_id`、`file`、`offset`(默认 0)、`max_bytes`(默认 256KB,上限 512KB) | `data.{content,offset,file_size,truncated}`;未配置 → 空 content + `note` | - 节点不存在 / 缺 `file` / 文件名含路径分隔符或 `..` → `-32602`;项目归属不符 → `-32003`。 - 增量轮询建议(工具返回的 `rollback_hint`):下一次调用把 `offset` 设为本次返回的 `file_size`。 - 宿主操作接口 `IMcpOperations.ReadDeployLogFilesAsync/ReadDeployLogTailAsync` 在 **Web 与 WebApi 两个宿主**各有实现,接口变更需同步两侧。