- .gitignore 新增 .hermes/ 目录,git rm --cached 已追踪的 plan 文件 - 删除 docker-compose.embed.yml(embed 部署统一走 K8s 或独立二进制) - Makefile 移除 docker-embed 目标 - CLAUDE.md 全面重写:三种部署方式详解、技术栈修正(Go1.24+MySQL/Redis)、架构完善、新增工具懒加载/凭证v2/远程执行/流水线/PTY终端等章节 - README.md 重写:三种部署快速开始、项目结构对齐实际目录、核心功能更新
342 lines
13 KiB
Markdown
342 lines
13 KiB
Markdown
# CLAUDE.md — AIOps
|
||
|
||
本文档为 Claude Code / Hermes 等 AI 编程助手提供在代码库中工作的指导说明。
|
||
|
||
> 作者:Logan.Li
|
||
> 语言:中文(代码注释和文档主要使用中文,注释署名 `// Logan.Li`)
|
||
|
||
## 项目概述
|
||
|
||
**AIOps** 是一个企业级智能运维平台,聚焦三大核心能力:
|
||
|
||
1. **资产管理** — 服务器管理、云资源(云账号/域名/账单)、K8s 集群
|
||
2. **监控告警** — Agent 采集指标、告警引擎(资源阈值/离线检测)、告警中心、链路追踪、监控大屏
|
||
3. **自动化运维 / AIOps** — 流水线 CI/CD、定时任务/脚本库、远程执行(Go-native SSH)、资源申请审批、AI 智能运维(智能助手/告警分析/容量预测)
|
||
|
||
### 核心特性
|
||
|
||
- **Agent 双通道** — 指标采集通道(10s 上报 `/proc`)+ 远程任务通道(5s 轮询执行命令)
|
||
- **LDAP 集成** — 配置管理、用户导入、OU 管理、LDAP 用户 CRUD
|
||
- **资源申请审批** — 云服务器申请、应用部署申请,动态表单
|
||
- **5 套主题** — CSS 变量驱动,暗色/亮色/紫色/绿色/玫红一键切换
|
||
- **WebShell** — WebSocket 终端,在线 SSH 操作服务器
|
||
- **凭证系统 v2** — 7 种统一凭证类型(SSH/Docker/TLS/AKSK/DB/API/Generic),加密存储
|
||
- **CI/CD 流水线** — GitLab CI 风格可视化,阶段色块进度条,实时日志,文件浏览器
|
||
- **Kubectl 终端** — WebSocket + PTY 交互式 K8s 终端,懒加载 kubectl 二进制
|
||
|
||
## 技术栈
|
||
|
||
| 层 | 技术 | 端口 |
|
||
|---|---|---|
|
||
| 后端 | Go 1.24 + Gin + GORM + MySQL 8.0 + Redis 7 + JWT + Zap | 8080 |
|
||
| 前端 | React 19 + TypeScript + Vite + Tailwind + shadcn/ui + Zustand + TanStack Query | 5173 |
|
||
| Agent | Go 1.24 (CGO_ENABLED=0 静态二进制, amd64+arm64) | — |
|
||
|
||
## 三种部署方式
|
||
|
||
项目通过统一入口 `./run.sh` 支持三种部署方式,适配不同场景:
|
||
|
||
### 方式一:独立二进制(`./run.sh build` / `./run.sh binary`)
|
||
|
||
前端通过 `go:embed` 嵌入后端二进制,生成单一可执行文件。零外部依赖,直接运行。
|
||
|
||
```bash
|
||
./run.sh build # 编译独立二进制 → backend/aiops
|
||
./run.sh binary # 编译 + 直接启动
|
||
./run.sh build agent # 交叉编译 Agent (amd64+arm64)
|
||
```
|
||
|
||
**二进制用法:**
|
||
```bash
|
||
./backend/aiops # 默认启动 (SQLite, 端口 8080)
|
||
./backend/aiops --port 9090 # 自定义端口
|
||
./backend/aiops --db-driver mysql --db-host 10.10.10.75 ... # MySQL 模式(需 --redis-driver redis)
|
||
./backend/aiops --config config.yaml # 使用配置文件
|
||
```
|
||
|
||
> ⚠️ MySQL 模式必须显式传 `--redis-driver redis`,否则默认 redka(CGO 依赖)在 `CGO_ENABLED=0` 下静默失败。
|
||
|
||
### 方式二:Kubernetes(`./run.sh k8s deploy`)
|
||
|
||
在 K8s 集群 `devops` 命名空间部署,单容器 embed 模式,NodePort 30080 暴露。
|
||
|
||
```bash
|
||
./run.sh k8s deploy # 构建 Dockerfile.embed 镜像 + 全量部署 (MySQL+Redis+App)
|
||
./run.sh k8s upgrade # 重新构建 + 滚动更新(不停机)
|
||
./run.sh k8s status # 查看 pods/svc/pvc/ingress
|
||
./run.sh k8s logs # 应用日志 (follow)
|
||
./run.sh k8s exec # 进入容器 Shell
|
||
./run.sh k8s mysql # MySQL CLI
|
||
./run.sh k8s redis # Redis CLI
|
||
./run.sh k8s scale 3 # 扩缩容
|
||
./run.sh k8s port-forward # 端口转发 localhost:8080 → svc/aiops
|
||
./run.sh k8s delete # 清理资源(保留 PVC)
|
||
```
|
||
|
||
**K8s 部署文件** (`deploy/k8s/`): namespace.yaml / secret.yaml / configmap.yaml / mysql.yaml / redis.yaml / deployment.yaml / ingress.yaml
|
||
|
||
> ⚠️ 健康检查用 `/version`(无 DB 依赖),不用 `/health`(启动早期可能不响应)。
|
||
|
||
### 方式三:Docker Compose(`./run.sh docker up`)
|
||
|
||
传统 4 容器部署:`aiops-mysql` + `aiops-redis` + `aiops-backend` + `aiops-frontend` (nginx)。
|
||
|
||
```bash
|
||
./run.sh docker up # 构建 + 启动全部容器
|
||
./run.sh docker down # 停止 + 移除容器
|
||
./run.sh docker build # 仅构建镜像
|
||
./run.sh docker restart # 重启容器
|
||
./run.sh docker logs # 实时日志
|
||
./run.sh docker ps # 容器状态
|
||
./run.sh docker clean # 清理构建缓存
|
||
```
|
||
|
||
**容器清单:**
|
||
| 容器 | 镜像 | 端口 | 说明 |
|
||
|------|------|------|------|
|
||
| `aiops-mysql` | `mysql:8.0` | 3306 | 数据库 |
|
||
| `aiops-redis` | `redis:7-alpine` | 6379 | 缓存 |
|
||
| `aiops-backend` | `backend/Dockerfile` (3-stage) | 8080 | Go API |
|
||
| `aiops-frontend` | `frontend/Dockerfile` (nginx:alpine) | 80 | React SPA |
|
||
|
||
### 本地开发(`./run.sh dev`)
|
||
|
||
```bash
|
||
./run.sh dev # 前后端热重载 (5173 + 8080)
|
||
./run.sh stop # 停止
|
||
./run.sh restart # 重启
|
||
./run.sh status # 查看状态
|
||
./run.sh logs # 实时日志
|
||
```
|
||
|
||
## 常用命令
|
||
|
||
### 后端 (backend/)
|
||
|
||
```bash
|
||
cd backend
|
||
|
||
# 编译
|
||
unset http_proxy https_proxy && export GOPROXY=https://goproxy.cn,direct && GOTOOLCHAIN=local CGO_ENABLED=1 go build -o aiops-server ./cmd/
|
||
|
||
# 直接运行
|
||
go run ./cmd/
|
||
|
||
# 代码检查
|
||
go vet ./...
|
||
```
|
||
|
||
### 前端 (frontend/)
|
||
|
||
```bash
|
||
cd frontend
|
||
npm run dev # 开发服务器 (端口 5173)
|
||
npm run build # 生产构建
|
||
npx tsc --noEmit # 类型检查(提交前必须零错误)
|
||
```
|
||
|
||
### Agent (agent/)
|
||
|
||
```bash
|
||
cd agent
|
||
|
||
# 本地构建
|
||
CGO_ENABLED=0 go build -o aiops-agent .
|
||
|
||
# 交叉编译
|
||
GOOS=linux GOARCH=amd64 CGO_ENABLED=0 go build -o aiops-agent-linux-amd64 .
|
||
GOOS=linux GOARCH=arm64 CGO_ENABLED=0 go build -o aiops-agent-linux-arm64 .
|
||
|
||
# 运行
|
||
./aiops-agent --server http://localhost:8080 --token <JWT_TOKEN>
|
||
```
|
||
|
||
## 架构说明
|
||
|
||
### 项目结构
|
||
|
||
```
|
||
aiops/
|
||
├── backend/
|
||
│ ├── cmd/
|
||
│ │ ├── main.go # 应用入口
|
||
│ │ ├── embed.go # go:embed 前端静态资源
|
||
│ │ ├── seed.go # 种子数据
|
||
│ │ └── static/ # embed 目标目录 (必须存在)
|
||
│ ├── internal/
|
||
│ │ ├── config/config.go # Viper 配置
|
||
│ │ ├── models/ # GORM 模型
|
||
│ │ └── api/
|
||
│ │ ├── handlers/ # HTTP handler
|
||
│ │ ├── middleware/ # JWT + Admin + PipelineAccess
|
||
│ │ └── routes/ # 路由注册
|
||
│ ├── pkg/
|
||
│ │ ├── database/ # DB 连接 + AutoMigrate
|
||
│ │ ├── kubernetesclient/ # 轻量 K8s API 客户端
|
||
│ │ ├── remoteexec/ # Go-native SSH 远程执行
|
||
│ │ └── toolinstaller/ # 工具懒加载 + 镜像回退
|
||
│ └── Dockerfile # 3 阶段构建 (Backend+Agent→Alpine Runtime)
|
||
│
|
||
├── frontend/
|
||
│ ├── src/components/
|
||
│ │ ├── dashboard/ # 仪表盘
|
||
│ │ ├── server/ # 服务器管理
|
||
│ │ ├── cloud/ # 云资源
|
||
│ │ ├── k8s/ # K8s 集群管理
|
||
│ │ ├── deploy/ # 应用发布(流水线/发布配置/发布权限/工具配置)
|
||
│ │ ├── monitor/ # 监控告警
|
||
│ │ ├── automation/ # 定时任务/脚本库/远程执行
|
||
│ │ ├── approval/ # 资源申请审批
|
||
│ │ ├── aiops/ # AI 智能运维(助手/告警分析/容量预测)
|
||
│ │ ├── system/ # 系统管理
|
||
│ │ └── layout/ # Sidebar/Header
|
||
│ ├── src/services/
|
||
│ │ ├── api.ts # API 定义
|
||
│ │ └── http.ts # http 封装(自动解包 data + Token 注入)
|
||
│ └── Dockerfile # Node build → nginx:alpine
|
||
│
|
||
├── agent/ # 监控 Agent(独立 Go module)
|
||
│ ├── collector/ # /proc 采集器
|
||
│ ├── task/ # 远程任务执行器
|
||
│ └── reporter/ # HTTP 上报
|
||
│
|
||
├── deploy/k8s/ # K8s 部署清单 (devops 命名空间)
|
||
├── Dockerfile.embed # 4 阶段 Embed 镜像 (前端→后端→Agent→Runtime)
|
||
├── docker-compose.yml # 4 容器部署 (mysql+redis+backend+frontend)
|
||
├── run.sh # 统一入口脚本
|
||
└── Makefile # 快捷命令
|
||
```
|
||
|
||
### API 响应格式
|
||
|
||
```go
|
||
// 统一响应
|
||
type Response struct {
|
||
Code int `json:"code"`
|
||
Message string `json:"message"`
|
||
Data interface{} `json:"data"`
|
||
}
|
||
|
||
// 列表响应
|
||
type ListResponse struct {
|
||
List interface{} `json:"list"`
|
||
Total int64 `json:"total"`
|
||
}
|
||
```
|
||
|
||
**前端 http.ts 已自动提取 `.data`**,组件中拿到的就是 `Response.Data`。列表返回 `{list, total}`。
|
||
|
||
### 认证流程
|
||
|
||
```
|
||
Login(本地/LDAP fallback) → JWT Token → 前端 Zustand persist + localStorage 双写
|
||
→ http.ts 自动注入 Bearer → JWTAuth 中间件 → AdminAuth 中间件(管理类路由)
|
||
```
|
||
|
||
WebSocket 无法设自定义 header → 后端 JWTAuth 支持 `?token=` query param 回退。
|
||
|
||
### Agent 双通道架构
|
||
|
||
```
|
||
指标通道: ticker(10s) → collect(/proc) → POST /agent/report
|
||
任务通道: ticker(5s) → GET /agent/tasks/poll → execute → POST /agent/tasks/:id/result
|
||
```
|
||
|
||
## 开发规范
|
||
|
||
### ⛔ 文件大小红线
|
||
|
||
| 类型 | 上限 | 超出处理 |
|
||
|------|------|----------|
|
||
| Go handler | **400 行** | 按 sub-domain 拆分 |
|
||
| Go model | **300 行** | 按模块拆分 |
|
||
| React 组件 (.tsx) | **700 行** | 提取子组件 |
|
||
| 任何文件 | **700 行(硬上限)** | 必须拆分 |
|
||
|
||
### ⛔ Go 代码规范
|
||
|
||
1. **所有 handler 返回必须用 `models.Response{Code:200, Data:...}` 包裹**
|
||
2. **编译命令**: `unset proxy + GOPROXY=goproxy.cn + GOTOOLCHAIN=local + CGO_ENABLED=1`
|
||
3. **新增 handler 不绑 model** — 用独立 request struct
|
||
4. **GORM 指针字段必须解引用** — `*field` 后再用
|
||
5. **Update handler 禁止复用 CreateRequest** — 用 `map[string]interface{}` 接收
|
||
|
||
### ⛔ React 前端规范
|
||
|
||
1. **API 列表响应解包** — `http.ts` 自动取 `.data`,列表返回 `{list, total}`
|
||
2. **禁止 `window.confirm()`/`alert()`** — 用 `useConfirm()` + `toast`
|
||
3. **Radix Dialog 必须有 `<DialogDescription>`**
|
||
4. **Token 双保险**: `useUserStore.getState().token || localStorage.getItem('token')`
|
||
|
||
### ⛔ UI 设计原则
|
||
|
||
- **能去掉的都去掉** — 不要多余边框、装饰线
|
||
- **按钮文案 2-4 字** — "批量导入" 而非 "批量导入用户"
|
||
- **不留占位按钮** — 功能没做好就不放按钮
|
||
- **页面打开即用** — 不需要额外"新建"按钮跳转
|
||
- **主题感知** — 用 CSS 变量 `var(--dg-xxx)`,不硬编码颜色
|
||
|
||
### ⛔ 通用开发流程
|
||
|
||
```
|
||
分析需求 → 写代码 → go build + tsc --noEmit → ./run.sh docker up → curl 验证 → git commit + push
|
||
```
|
||
|
||
- **代码改完不算完成,端到端验证通过才算完成**
|
||
- **大变更前先 git commit** — 方便回滚
|
||
|
||
## 默认账号
|
||
|
||
| 用户名 | 密码 | 角色 |
|
||
|--------|------|------|
|
||
| admin | 123456 | 超级管理员 |
|
||
| ops01 | 123456 | 运维 |
|
||
| dev01 | 123456 | 开发 |
|
||
| logan | zxc987 | LDAP 用户 |
|
||
|
||
⚠️ **生产环境请修改默认密码**
|
||
|
||
## 访问地址
|
||
|
||
- 前端:`http://localhost:5173` (dev) / `http://localhost:80` (docker)
|
||
- 后端:`http://localhost:8080`
|
||
- 健康检查:`http://localhost:8080/health`
|
||
- K8s:`http://<NODE_IP>:30080`
|
||
|
||
## 常见陷阱速查
|
||
|
||
| # | 陷阱 | 解决 |
|
||
|---|------|------|
|
||
| Go1 | go build 超时 | `unset proxy + GOPROXY=goproxy.cn + GOTOOLCHAIN=local` |
|
||
| Go2 | handler 不包裹 Response | 必须 `models.Response{Code:200, Data:...}` |
|
||
| Go3 | GORM 指针字段 | `*field` 解引用后再用 |
|
||
| Go4 | Update 复用 CreateRequest | 用 `map[string]interface{}` |
|
||
| Go5 | CGO_ENABLED=0 + redka → 缓存静默失败 | `--redis-driver redis` |
|
||
| FE1 | 白屏无堆栈 | 90% 是列表 `{list,total}` 未解包 |
|
||
| FE2 | confirm() 冻结自动化 | 用 `useConfirm()` |
|
||
| FE3 | Token 获取 | `useUserStore.getState().token` + `localStorage` |
|
||
| FE4 | Radix Dialog 警告 | 必须有 `<DialogDescription>` |
|
||
| FE5 | Select.Item 空字符串 value | 用 sentinel 值 `__manual` |
|
||
| FE6 | API 字段名不匹配 | 检查前后端命名一致性 |
|
||
|
||
## 注释规范
|
||
|
||
新增或修改代码必须写中文注释,注释结尾署名 `// Logan.Li`。
|
||
|
||
## 远程仓库
|
||
|
||
```
|
||
https://gitee.com/attacker/aiops.git
|
||
Git 用户: attacker / attacker@gitee.com
|
||
分支: main
|
||
```
|
||
|
||
## 关键设计决策
|
||
|
||
- **凭证驱动管理** — 不在表单手动输入密码/密钥,用凭证下拉关联(7 种类型统一模型)
|
||
- **工具懒加载** — kubectl/maven/nodejs/helm 首次使用时自动下载,国内网络自动优先国内镜像
|
||
- **远程执行** — Ansible 已替换为 Go-native SSH(`pkg/remoteexec/`),零新增依赖
|
||
- **K8s 客户端** — 轻量自研(net/http + crypto/tls),不引入 50MB+ 的 client-go
|
||
- **BuildKit cache mount** — Docker 构建从 13min 降至 3sec(二次构建)
|
||
- **健康检查用 `/version`** — K8s 中 `/health` 可能依赖 DB,`/version` 始终 200
|