# ldesign-cli-telemetry-server **Repository Path**: ldesign/ldesign-cli-telemetry-server ## Basic Information - **Project Name**: ldesign-cli-telemetry-server - **Description**: LDesign CLI telemetry package - **Primary Language**: Unknown - **License**: Not specified - **Default Branch**: dev - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2026-08-13 - **Last Updated**: 2026-08-23 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # @ldesign/cli-telemetry-server NestJS 遥测接收端(ingestion)与管理员后台(admin API)服务,用于接收 `@ldesign/cli-telemetry` 客户端上报的命令运行遥测。 > 版本:`0.1.1-alpha.10` · 要求:`Node >= 20.19.0` ## 概述 本服务接收客户端的设备注册、会话开始、日志追加、结构化 CLI/浏览器错误与会话结束事件,并提供带登录鉴权的管理员查询 API 与 SSE 实时刷新。内置 Prisma schema 与 migration(面向 PostgreSQL 部署);当没有配置数据库时,运行时自动回退到内存存储,便于本机调试。 ## 安装与启动 ```bash Copy-Item .env.example .env pnpm install pnpm run start:dev ``` 默认监听 `0.0.0.0:4320`(可用 `PORT` 覆盖)。未设置 `TELEMETRY_PERSISTENCE=prisma` 时使用内存存储。 ## 特性 - 接收端 API:设备注册、会话开始、日志追加、结构化事件、会话结束;除首次注册外,所有写入均要求设备 ingest token,并绑定到对应 run/device。 - 两种存储:内存 `TelemetryStore` 与 PostgreSQL `PrismaTelemetryStore`,由 `createTelemetryStore` 择机启用。 - 管理员后台:账号登录 + session token,登录前不显示管理菜单;提供总览、运行、设备、错误管理、使用分析和用户管理路由。 - SSE 实时刷新:`/v1/admin/runs/stream` 每 1 秒推送一次运行列表。 - 后台页面:`/admin/` 提供 Vue 运维面板;所有 `/admin/*` history 路由支持直接访问和刷新,资产仍由 `/admin/assets/*` 提供。 - 内置安全:helmet、CORS、ValidationPipe 白名单校验、超级管理员角色权限控制。 - 首启自动建管理员:`ensureDefaultAdmin()` 创建配置的超级管理员(开发默认 `admin / admin123`)。 ## 接口 | 方法 | 路径 | 说明 | | --- | --- | --- | | POST | /v1/ingest/devices/register | 设备注册,返回 ingestToken | | POST | /v1/ingest/runs/start | 开启遥测会话 | | POST | /v1/ingest/runs/:runId/logs | 追加日志批次 | | POST | /v1/ingest/runs/:runId/finish | 结束会话并设置状态 | | POST | /v1/ingest/events | 写入 CLI/浏览器结构化事件(eventId 幂等) | | GET | /health | 健康检查 | | GET | /v1/admin/runs | 运行列表(支持 status 筛选) | | GET | /v1/admin/runs/:runId | 运行详情 | | GET | /v1/admin/summary | 统计汇总 | | GET | /v1/admin/analytics | 每日用时、命令频率、CLI 版本和错误分类 | | GET | /v1/admin/devices | 设备 ID、画像、最后版本、最后命令、累计用时 | | GET | /v1/admin/events | 事件分页与 category/type/deviceId 筛选 | | GET | /v1/admin/runs/stream | SSE 实时刷新 | | POST | /v1/admin/auth/login | 后台登录 | | POST | /v1/admin/auth/logout | 后台登出 | | GET | /v1/admin/auth/me | 当前登录用户 | | GET | /v1/admin/users | 用户列表(超级管理员) | | GET | /v1/admin/users/:id | 用户详情(超级管理员) | | POST | /v1/admin/users | 创建用户(超级管理员) | | POST | /v1/admin/users/:id | 编辑用户(超级管理员) | | POST | /v1/admin/users/:id/delete | 删除用户(超级管理员) | | GET | /admin/ | 管理后台页面 | 后台用户与角色管理(增删改、admin/super_admin)仅超级管理员可操作,需 `Authorization: Bearer `。设备和错误页面为只读分析,不包含远程设备控制。 ## 源码结构 ``` src/ main.ts # 启动入口:helmet、CORS、ValidationPipe、建默认管理员 app.module.ts # NestJS 模块装配 telemetry.controller.ts # ingest 与 admin 控制器、后台页面服务 telemetry.store.ts # 存储契约与内存/Prisma 实现 admin-auth.ts # 后台管理员登录、令牌与会话 ``` ## 存储模式 `createTelemetryStore()` 根据环境决定: - 未设置 `TELEMETRY_PERSISTENCE=prisma` 或没有 `DATABASE_URL`:内存存储(进程内 Map)。 - 两者都设置:`PrismaTelemetryStore`,使用 `@prisma/client` 落 PostgreSQL,做 token 哈希、日志批量落库与去重。容器启动命令会先执行 `prisma migrate deploy`,再启动 API。 ### 数据安全边界 - ingestion token 只以哈希落库;运行、日志、事件写入都会校验 token 与设备/run 绑定。 - 客户端负责对 argv、options、环境、日志、URL、错误堆栈做凭据脱敏;服务端不把 token 返回到管理 API。 - 生产 `NODE_ENV=production` 时,数据库密码、管理员初始密码和密码盐值不得使用默认/占位值;生产 Compose 还会在解析阶段要求显式提供这些变量。 ## Docker 本机部署 ```bash pnpm container:plan pnpm container:build pnpm container:deploy ``` `container:build` 只构建带版本 tag 的本机镜像;`container:deploy` 使用生产 Compose 构建并启动 PostgreSQL 和 API。部署后访问 `http://localhost:4320/health` 与 `/admin/`。后台用 `ADMIN_INITIAL_USERNAME` / `ADMIN_INITIAL_PASSWORD` 登录。 ```bash docker compose -p ldesign-cli-telemetry logs -f telemetry-server ``` ## PostgreSQL 部署 ```bash Copy-Item .env.example .env pnpm install pnpm run prisma:migrate:deploy pnpm run start ``` 首启创建配置的超级管理员(生产前必须改默认口令)。ingestion 无需终端用户登录;`ADMIN_TOKEN` 为临时兼容的服务令牌。 ## Docker Registry / NAS Harbor 发布 默认使用本机 Docker Desktop,镜像 `docker.io/swimly/ldesign-cli-telemetry-server`,平台 `linux/amd64,linux/arm64`。发布到自有 NAS Harbor 时,只需改 registry 和完整镜像 repository: ```bash export DOCKER_REGISTRY=nas.example.local:5443 export DOCKER_IMAGE=nas.example.local:5443/ldesign/ldesign-cli-telemetry-server export DOCKER_REGISTRY_USERNAME='robot$ldesign+release' export DOCKER_REGISTRY_TOKEN='从 Harbor 复制的 robot token' ``` ```bash pnpm container:release:dry pnpm container:release ``` 可用 `DOCKERHUB_USERNAME`、`DOCKER_IMAGE`、`DOCKER_TAG`、`DOCKER_PLATFORMS` 覆盖默认值。目标机只需发布目录与 `.env`: ```bash docker compose pull docker compose up -d ``` 发布流程先通过 Buildx 构建并加载多架构镜像,再由 Docker Desktop daemon 推送。这样能复用 Docker Desktop 已配置的网络代理,避免 Buildx registry exporter 在部分 Windows 网络环境中绕过代理。发布机需要先执行对应 Harbor 的 `docker login`,或设置 `DOCKER_REGISTRY_USERNAME` 和 `DOCKER_REGISTRY_TOKEN`;token 只通过 stdin 传给 Docker,不会写入日志。`release/docker-compose.yml` 只有在镜像推送成功后才会写入,镜像 tag 与发布镜像保持一致。`DOCKERHUB_USERNAME` / `DOCKERHUB_TOKEN` 仍可用于 Docker Hub 兼容流程。 若目标 NAS 不出网,请把 PostgreSQL 也导入 Harbor,并在目标 `.env` 设置 `POSTGRES_IMAGE` 为 Harbor 中的 PostgreSQL 镜像;仅将应用镜像推到 Harbor 不能使数据库启动完全离线。若数据库密码包含 URL 保留字符,请同时提供使用 URL 编码密码的完整 `DATABASE_URL`。 ## 相关包 | 包名 | 说明 | | --- | --- | | @ldesign/cli-telemetry | 本地遥测客户端,与 /v1/ingest 对接 | ## 许可证 ISC © LDesign。