K8s Lab 把当前仓库文档整理成一个可阅读的网页站点

Repository Reading Site

技术架构方案 — 开源 AI SaaS 平台

**开源意味着:** --- | 层面 | 选型 | 理由 | |------|------|------| | **后端语言** | Go | 高并发原生支持、编译为单二进制、K8s 生态原生语言、性能好 | | **API 框架** | Go 标准库 net/http + chi router | 轻量、无魔法、社区大、开源项目不宜绑重框架 | | **

Markdownsaas-platform/docs/technical-architecture.md2026年4月9日 16:23

技术架构方案 — 开源 AI SaaS 平台

一、项目定位

开源的大模型训练与推理 SaaS 平台。
对标: 开源版的硅基流动 / 火山方舟。
目标: 任何人拿到代码 + 几台 GPU 机器,就能搭建自己的 AI 云平台。

开源意味着:

  • 代码质量要高,别人要读得懂、改得动
  • 部署要简单,不能依赖 50 个组件
  • 文档要完整,不光有用户文档还要有开发者文档
  • 扩展性要好,别人要能加自己的推理引擎/计费策略/认证方式

二、技术选型

2.1 总览

层面 选型 理由
后端语言 Go 高并发原生支持、编译为单二进制、K8s 生态原生语言、性能好
API 框架 Go 标准库 net/http + chi router 轻量、无魔法、社区大、开源项目不宜绑重框架
ORM sqlc SQL 优先,编译时类型安全,比 GORM 更透明
数据库 PostgreSQL 16 成熟稳定、JSON 支持好、pgvector 扩展做向量检索
缓存/限流 Redis 7 限流计数器、余额缓存、Session 缓存、消息队列
消息队列 Redis Stream 够用且少引入一个组件,重度场景再换 NATS
对象存储 MinIO (S3 兼容) 开源自建、API 兼容 AWS S3、可平替为真 S3
容器编排 Kubernetes 没有第二选择
推理引擎 vLLM (GPU) / llama.cpp (CPU) vLLM 是当前最强开源推理引擎
训练框架 Python + transformers + PEFT HuggingFace 生态,LoRA 微调标准方案
向量数据库 pgvector (PostgreSQL 扩展) 不多引入组件,PG 一个库搞定关系+向量
前端 React + TypeScript + Tailwind + Shadcn/ui 生态最大、组件库丰富、开源贡献者最多
API 协议 OpenAI 兼容 + gRPC 内部通信 对外兼容生态,对内高性能
CI/CD GitHub Actions + ArgoCD 开源项目标配
监控 Prometheus + Grafana + Loki 已部署,K8s 生态标准
镜像仓库 Harbor 已部署

2.2 为什么选 Go 而不是其他?

考虑过的方案:

Python (FastAPI):
  ✅ AI/ML 生态好,开发快
  ❌ 并发差(GIL),每秒 1000 QPS 需要多进程
  ❌ 内存占用高,一个 API 进程 200MB+
  ❌ 部署复杂(Python 环境/依赖/版本)
  结论: 适合做训练脚本,不适合做平台后端

Rust:
  ✅ 性能极致,内存安全
  ❌ 开发速度慢 3-5 倍
  ❌ K8s client 库不如 Go 成熟
  ❌ 招人难/开源贡献者少
  结论: 过度工程化,收益不匹配投入

Java (Spring Boot):
  ✅ 企业级生态完善
  ❌ 内存占用大(JVM 动辄 500MB)
  ❌ 容器化不够轻量
  ❌ K8s Operator 生态远不如 Go
  结论: 重型企业应用可以,云原生不合适

Go:
  ✅ K8s 本身用 Go 写的,Operator 生态完善
  ✅ 编译为单二进制,Docker 镜像 < 20MB
  ✅ goroutine 原生高并发,百万连接无压力
  ✅ 标准库就够用,依赖少
  ✅ 开源 Go 项目贡献者多
  结论: 云原生 SaaS 平台的最佳选择

2.3 为什么选 PostgreSQL 而不是 MySQL?

PostgreSQL:
  ✅ pgvector: 向量检索原生支持(省掉独立向量数据库)
  ✅ JSONB: 灵活存储配置/元数据,带索引
  ✅ 分区表: usage_logs 按时间分区,查询快
  ✅ CTE/窗口函数: 复杂账单统计 SQL 更好写
  ✅ 行级安全策略: 多租户隔离可以在 DB 层做
  ✅ 开源协议友好 (PostgreSQL License)

MySQL:
  ❌ 无向量检索(需额外部署 Milvus/Qdrant)
  ❌ JSON 支持弱于 PG
  ❌ 分区表功能受限

2.4 为什么选 sqlc 而不是 GORM?

GORM (ORM):
  user := User{Name: "张三"}
  db.Create(&user)
  db.Where("name = ?", "张三").First(&user)
  
  ❌ 隐藏了 SQL,性能问题难排查
  ❌ 复杂查询写起来比直接写 SQL 还痛苦
  ❌ 运行时反射,类型安全靠程序员自觉

sqlc (SQL 优先):
  -- queries.sql
  -- name: GetUser :one
  SELECT * FROM users WHERE id = $1;
  
  // 编译生成的 Go 代码
  func (q *Queries) GetUser(ctx context.Context, id uuid.UUID) (User, error)
  
  ✅ 写原生 SQL,完全掌控
  ✅ 编译时类型检查(SQL 语法错误编译就报)
  ✅ 自动生成 Go struct 和函数,不手写模板代码
  ✅ 没有运行时开销
  ✅ DBA 友好,SQL 可以直接审查

2.5 为什么用 Redis Stream 而不是 Kafka/RabbitMQ?

我们的消息场景:
  1. usage_log 异步写入(高频,但不需要复杂路由)
  2. 事件通知(训练完成、余额告警)
  3. 任务队列(数据处理、异步校验)

Redis Stream:
  ✅ 已经需要 Redis 做缓存/限流,不多引入组件
  ✅ 消费者组、ACK、持久化都支持
  ✅ 吞吐量满足(万级/秒够了)
  ✅ 部署运维简单

什么时候换 Kafka/NATS:
  - 消息量达到十万级/秒
  - 需要复杂的 topic 路由
  - 需要多消费者独立消费同一消息
  - 需要消息回溯重放

三、系统架构

3.1 单体优先,按需拆分

⚠️ 关键设计决策: 不要一开始就做微服务。

开源项目不同于大厂:
  大厂: 100 人团队,需要各写各的,微服务有道理
  开源: 1-3 人核心开发,微服务 = 运维负担 + 部署复杂 + 调试地狱

我们的方案: 模块化单体 (Modular Monolith)

一个 Go 二进制包含所有业务逻辑:

  ┌─────────────────────────────────────────────┐
  │              ai-gateway (单二进制)            │
  │                                             │
  │  ┌─────────┐ ┌─────────┐ ┌─────────┐      │
  │  │ auth    │ │ billing │ │ model   │      │
  │  │ 包      │ │ 包      │ │ 包      │      │
  │  └─────────┘ └─────────┘ └─────────┘      │
  │  ┌─────────┐ ┌─────────┐ ┌─────────┐      │
  │  │training │ │ dataset │ │ admin   │      │
  │  │ 包      │ │ 包      │ │ 包      │      │
  │  └─────────┘ └─────────┘ └─────────┘      │
  │                                             │
  │  共享: DB连接池 / Redis客户端 / 日志 / 配置   │
  └─────────────────────────────────────────────┘

  + 2 个独立二进制(必须独立运行的):

  ┌─────────────────────┐  ┌─────────────────────┐
  │ inference-operator  │  │ training-operator   │
  │ (K8s 控制器)         │  │ (K8s 控制器)        │
  └─────────────────────┘  └─────────────────────┘

为什么这样:
  - 部署只需要 3 个 Deployment,不是 10 个
  - 本地开发 go run ./cmd/gateway 一条命令启动
  - 函数调用替代 HTTP/gRPC 调用,延迟低、调试方便
  - 包之间通过 interface 解耦,日后要拆随时可拆
  - 开源用户 docker-compose up 就能跑

3.2 项目结构

ai-platform/
├── cmd/
│   ├── gateway/              # 主服务入口
│   │   └── main.go
│   ├── inference-operator/   # 推理 Operator 入口
│   │   └── main.go
│   └── training-operator/    # 训练 Operator 入口
│       └── main.go
│
├── internal/                 # 内部包(不对外暴露)
│   ├── auth/                 # 认证与授权
│   │   ├── jwt.go
│   │   ├── apikey.go
│   │   ├── middleware.go
│   │   └── oauth/
│   │       ├── github.go
│   │       └── google.go
│   │
│   ├── user/                 # 用户与租户
│   │   ├── handler.go        # HTTP handlers
│   │   ├── service.go        # 业务逻辑
│   │   └── repository.go     # 数据库操作 (sqlc 生成)
│   │
│   ├── billing/              # 计费
│   │   ├── handler.go
│   │   ├── service.go
│   │   ├── metering.go       # Token 计量
│   │   ├── balance.go        # Redis 余额管理
│   │   └── invoice.go        # 账单生成
│   │
│   ├── model/                # 模型管理
│   │   ├── handler.go
│   │   ├── service.go
│   │   ├── registry.go       # 模型注册表
│   │   └── router.go         # 推理请求路由
│   │
│   ├── inference/            # 推理代理
│   │   ├── proxy.go          # 反向代理到推理引擎
│   │   ├── stream.go         # SSE 流式转发
│   │   └── tokenizer.go      # Token 计数
│   │
│   ├── training/             # 训练管理
│   │   ├── handler.go
│   │   ├── service.go
│   │   └── queue.go          # 训练队列
│   │
│   ├── dataset/              # 数据集管理
│   │   ├── handler.go
│   │   ├── service.go
│   │   ├── validator.go      # 数据校验
│   │   └── processor.go      # 数据处理
│   │
│   ├── rag/                  # RAG 知识库
│   │   ├── handler.go
│   │   ├── chunker.go        # 文档分块
│   │   ├── embedder.go       # 向量化
│   │   └── retriever.go      # 检索
│   │
│   └── admin/                # 管理后台
│       ├── handler.go
│       ├── pricing.go        # 价格配置
│       └── gpu.go            # GPU 管理
│
├── pkg/                      # 可复用公共包
│   ├── config/               # 配置管理 (YAML + 环境变量)
│   ├── database/             # PostgreSQL 连接池
│   ├── redis/                # Redis 客户端封装
│   ├── storage/              # S3/MinIO 客户端
│   ├── openai/               # OpenAI 协议定义 (请求/响应结构)
│   ├── middleware/           # 通用中间件 (logging, recovery, cors)
│   ├── pagination/           # 分页工具
│   └── errors/               # 统一错误码
│
├── operator/                 # K8s Operator 代码
│   ├── api/
│   │   └── v1/
│   │       ├── inferenceservice_types.go
│   │       ├── trainingjob_types.go
│   │       └── deepcopy.go
│   ├── controller/
│   │   ├── inference_controller.go
│   │   └── training_controller.go
│   └── go.mod                # Operator 独立 go.mod
│
├── db/                       # 数据库相关
│   ├── migrations/           # 迁移文件
│   │   ├── 001_init.up.sql
│   │   ├── 001_init.down.sql
│   │   ├── 002_billing.up.sql
│   │   └── ...
│   ├── queries/              # sqlc SQL 文件
│   │   ├── users.sql
│   │   ├── organizations.sql
│   │   ├── api_keys.sql
│   │   ├── models.sql
│   │   ├── billing.sql
│   │   ├── datasets.sql
│   │   └── training.sql
│   ├── sqlc.yaml             # sqlc 配置
│   └── generated/            # sqlc 生成的 Go 代码
│
├── web/                      # 前端代码
│   ├── package.json
│   ├── src/
│   │   ├── app/              # Next.js App Router
│   │   ├── components/       # 通用组件
│   │   ├── features/         # 按功能模块组织
│   │   │   ├── auth/
│   │   │   ├── billing/
│   │   │   ├── models/
│   │   │   ├── training/
│   │   │   ├── datasets/
│   │   │   └── admin/
│   │   └── lib/              # 工具函数
│   └── Dockerfile
│
├── deploy/                   # 部署配置
│   ├── docker-compose.yaml   # 一键本地启动
│   ├── helm/                 # Helm Chart
│   │   └── ai-platform/
│   │       ├── Chart.yaml
│   │       ├── values.yaml
│   │       └── templates/
│   └── k8s/                  # 原始 K8s YAML
│       ├── namespace.yaml
│       ├── gateway.yaml
│       ├── operators.yaml
│       ├── postgresql.yaml
│       ├── redis.yaml
│       └── minio.yaml
│
├── docker/                   # Dockerfile
│   ├── gateway.Dockerfile
│   ├── operator.Dockerfile
│   ├── training.Dockerfile   # Python 训练镜像
│   └── web.Dockerfile
│
├── scripts/                  # 工具脚本
│   ├── setup.sh              # 一键初始化开发环境
│   ├── migrate.sh            # 数据库迁移
│   ├── seed.sh               # 填充测试数据
│   └── generate.sh           # sqlc generate + deepcopy
│
├── docs/                     # 文档
│   ├── getting-started.md    # 5 分钟快速开始
│   ├── deployment.md         # 生产部署指南
│   ├── api-reference.md      # API 文档
│   ├── development.md        # 开发者指南
│   └── architecture.md       # 架构说明
│
├── go.mod
├── go.sum
├── Makefile                  # 常用命令
├── LICENSE                   # Apache-2.0
└── README.md

3.3 关键设计原则

1. 一条命令启动:
   本地开发:    docker-compose up
   生产部署:    helm install ai-platform ./deploy/helm/ai-platform
   
2. 配置驱动:
   config.yaml:
     database:
       host: localhost
       port: 5432
     redis:
       host: localhost
     storage:
       type: minio        # 可切换为 s3 / local
       endpoint: localhost:9000
     inference:
       engine: llamacpp   # 可切换为 vllm / tgi
     auth:
       jwt_secret: xxx
       oauth:
         github:
           client_id: xxx

3. 接口隔离:
   // 计费不直接调数据库,通过 interface
   type BillingService interface {
       CheckBalance(ctx context.Context, orgID string) (decimal.Decimal, error)
       Deduct(ctx context.Context, orgID string, amount decimal.Decimal) error
       GetUsage(ctx context.Context, orgID string, from, to time.Time) ([]UsageLog, error)
   }
   
   // 存储不绑定 MinIO,通过 interface
   type ObjectStorage interface {
       Upload(ctx context.Context, bucket, key string, reader io.Reader) error
       Download(ctx context.Context, bucket, key string) (io.ReadCloser, error)
       Delete(ctx context.Context, bucket, key string) error
   }
   
   日后换实现只需要改注入,不改业务代码。

四、部署架构

4.1 docker-compose(开发/体验)

# docker-compose.yaml — 一条命令跑起整个平台
services:
  gateway:
    build: { context: ., dockerfile: docker/gateway.Dockerfile }
    ports: ["8080:8080"]
    depends_on: [postgres, redis, minio]
    
  web:
    build: { context: ./web, dockerfile: ../docker/web.Dockerfile }
    ports: ["3000:3000"]
    
  inference:
    image: ghcr.io/ggerganov/llama.cpp:server  # CPU 推理
    volumes: ["./models:/models"]
    ports: ["8081:8081"]
    command: ["-m", "/models/qwen2.5-1.5b.gguf", "--port", "8081"]
    
  postgres:
    image: pgvector/pgvector:pg16
    volumes: ["pgdata:/var/lib/postgresql/data"]
    environment:
      POSTGRES_DB: ai_platform
      POSTGRES_PASSWORD: postgres
      
  redis:
    image: redis:7-alpine
    
  minio:
    image: minio/minio
    command: server /data --console-address ":9001"
    ports: ["9000:9000", "9001:9001"]
    
volumes:
  pgdata:
# 用户体验:
git clone https://github.com/xxx/ai-platform
cd ai-platform
docker-compose up
# 打开 http://localhost:3000 → 注册 → 使用

4.2 Helm Chart(生产 K8s)

# values.yaml — 生产配置
gateway:
  replicas: 3
  resources:
    requests: { cpu: "500m", memory: "512Mi" }

inferenceOperator:
  replicas: 1

trainingOperator:
  replicas: 1

postgresql:
  enabled: true         # 或用外部 RDS
  persistence:
    size: 100Gi
    storageClass: nfs-dynamic

redis:
  enabled: true         # 或用外部 ElastiCache
  sentinel:
    enabled: true       # 生产开 Sentinel

minio:
  enabled: true         # 或用 AWS S3
  persistence:
    size: 500Gi

inference:
  engine: vllm
  models:
    - name: qwen2.5-7b
      gpu: nvidia-a10
      replicas: 2
      
web:
  replicas: 2
# 生产部署:
helm install ai-platform ./deploy/helm/ai-platform \
  -f values-production.yaml \
  --namespace ai-platform

4.3 GPU 节点架构

平台节点 (无 GPU):
  ┌─────────────────────────────────┐
  │ gateway × 3                     │
  │ web × 2                         │
  │ inference-operator × 1          │
  │ training-operator × 1           │
  │ postgresql × 1 (HA 集群可选)    │
  │ redis × 1 (Sentinel 可选)       │
  │ minio × 1                       │
  │ prometheus + grafana + loki      │
  └─────────────────────────────────┘

GPU 推理节点:
  taint: nvidia.com/gpu=true:NoSchedule
  ┌─────────────────────────────────┐
  │ vLLM Pod (qwen-7b) × N         │
  │ vLLM Pod (qwen-14b) × N        │
  │ llama.cpp Pod (小模型) × N      │
  │ dcgm-exporter (GPU 监控)        │
  └─────────────────────────────────┘

GPU 训练节点:
  taint: nvidia.com/gpu=true:NoSchedule
  label: node-type=training
  ┌─────────────────────────────────┐
  │ Training Job Pod × N (动态)     │
  │ dcgm-exporter                   │
  └─────────────────────────────────┘

五、核心技术方案

5.1 OpenAI 兼容层

// pkg/openai/types.go — 完全兼容 OpenAI 请求/响应格式

type ChatCompletionRequest struct {
    Model       string          `json:"model"`
    Messages    []Message       `json:"messages"`
    MaxTokens   int             `json:"max_tokens,omitempty"`
    Temperature float64         `json:"temperature,omitempty"`
    TopP        float64         `json:"top_p,omitempty"`
    Stream      bool            `json:"stream,omitempty"`
    Stop        []string        `json:"stop,omitempty"`
    // ... 完整兼容所有 OpenAI 参数
}

type ChatCompletionResponse struct {
    ID      string   `json:"id"`
    Object  string   `json:"object"`
    Created int64    `json:"created"`
    Model   string   `json:"model"`
    Choices []Choice `json:"choices"`
    Usage   Usage    `json:"usage"`
}

// 用户只需要改 base_url:
// client = OpenAI(base_url="https://你的平台/v1", api_key="sk-xxx")
// 现有代码零修改

5.2 推理代理层

// internal/inference/proxy.go
// 核心职责: 接收 OpenAI 格式请求 → 转发到后端推理引擎 → 返回 OpenAI 格式响应

func (p *Proxy) HandleChatCompletions(w http.ResponseWriter, r *http.Request) {
    // 1. 解析请求
    var req openai.ChatCompletionRequest
    json.NewDecoder(r.Body).Decode(&req)
    
    // 2. 从上下文获取认证信息(middleware 已处理)
    org := auth.OrgFromContext(r.Context())
    
    // 3. 查找模型路由
    backend, err := p.router.Route(req.Model, org.ID)
    // backend = "http://qwen-7b-shared.inference:8080/v1/chat/completions"
    
    // 4. 计算 input tokens
    promptTokens := p.tokenizer.Count(req.Messages, req.Model)
    
    // 5. 流式 vs 非流式
    if req.Stream {
        p.handleStream(w, r, backend, req, org, promptTokens)
    } else {
        p.handleBlocking(w, r, backend, req, org, promptTokens)
    }
}

func (p *Proxy) handleStream(w http.ResponseWriter, ...) {
    // SSE 流式转发
    // 同时统计 completion tokens
    // 流结束后异步扣费
    flusher := w.(http.Flusher)
    w.Header().Set("Content-Type", "text/event-stream")
    
    resp, _ := http.Post(backend, "application/json", bodyReader)
    scanner := bufio.NewScanner(resp.Body)
    completionTokens := 0
    
    for scanner.Scan() {
        line := scanner.Text()
        fmt.Fprintf(w, "%s\n", line)
        flusher.Flush()
        completionTokens += countTokensInChunk(line)
    }
    
    // 异步扣费
    go p.billing.Deduct(ctx, org.ID, promptTokens, completionTokens, model)
}

5.3 多引擎适配

// internal/inference/engine.go
// 不同推理引擎的 API 可能不同,统一适配为 OpenAI 格式

type InferenceEngine interface {
    ChatCompletions(ctx context.Context, req openai.ChatCompletionRequest) (*openai.ChatCompletionResponse, error)
    StreamChatCompletions(ctx context.Context, req openai.ChatCompletionRequest) (<-chan openai.StreamChunk, error)
    Health(ctx context.Context) error
}

// vLLM: 原生兼容 OpenAI API,直接透传
type VLLMEngine struct { baseURL string }

// llama.cpp: API 格式略有不同,需要转换
type LlamaCppEngine struct { baseURL string }

// Ollama: 又是另一种格式
type OllamaEngine struct { baseURL string }

// 工厂模式,配置文件决定用哪个引擎
func NewEngine(config EngineConfig) InferenceEngine {
    switch config.Type {
    case "vllm":     return &VLLMEngine{baseURL: config.URL}
    case "llamacpp": return &LlamaCppEngine{baseURL: config.URL}
    case "ollama":   return &OllamaEngine{baseURL: config.URL}
    }
}

5.4 训练任务调度

// internal/training/service.go

func (s *TrainingService) CreateJob(ctx context.Context, req CreateTrainingRequest) (*TrainingJob, error) {
    // 1. 验证数据集存在且格式兼容
    dataset, err := s.datasetRepo.Get(ctx, req.DatasetID)
    
    // 2. 验证基座模型可微调
    model, err := s.modelRepo.Get(ctx, req.BaseModel)
    
    // 3. 预估费用
    estimate := s.estimateCost(dataset, model, req.Config)
    
    // 4. 预扣费用
    err = s.billing.PreDeduct(ctx, org.ID, estimate)
    
    // 5. 创建 TrainingJob CRD
    cr := &v1.TrainingJob{
        Spec: v1.TrainingJobSpec{
            BaseModel:       req.BaseModel,
            Dataset:         dataset.Path,
            Method:          req.Method,
            Hyperparameters: req.Config,
            GPU:             selectGPU(model),
        },
    }
    err = s.k8sClient.Create(ctx, cr)
    
    // 6. 写入数据库
    job := &TrainingJob{
        OrgID:      org.ID,
        BaseModel:  req.BaseModel,
        Status:     "queued",
        PreDeducted: estimate,
    }
    return s.repo.Create(ctx, job)
}

六、开源策略

6.1 许可证

Apache-2.0

理由:
  - 允许商业使用(企业放心用)
  - 允许修改和分发
  - 要求保留版权声明
  - 不要求衍生作品开源(比 GPL 友好)
  - K8s / Docker / Prometheus 都用 Apache-2.0

6.2 开源 vs 商业

完全开源(Apache-2.0):
  ✅ 全部后端代码(Go)
  ✅ 全部前端代码(React)
  ✅ 全部 Operator 代码
  ✅ Helm Chart / docker-compose
  ✅ 文档
  ✅ CI/CD 配置

可选商业增值(如果做商业化):
  💰 托管云服务(你帮用户运维)
  💰 企业 SSO 集成(SAML/OIDC)
  💰 多集群管理
  💰 高级审计与合规
  💰 SLA 保障与技术支持
  💰 私有部署 + 定制开发

参考模式:
  GitLab: 核心开源,高级功能付费
  Supabase: 完全开源,托管服务收费
  MinIO: 完全开源,企业版加功能

6.3 项目命名建议

需要一个好记的名字:

考虑方向:
  - 和 AI/模型 相关
  - 简短,2-3 音节
  - .com 或 .dev 域名可注册
  - GitHub 名没被占

候选:
  AiForge    — AI 锻造厂
  ModelHub   — 模型中心(可能和 HuggingFace 混淆)
  InferX     — 推理平台
  OmniLLM    — 全能大模型
  NovAI      — 新 AI 平台
  AIGate     — AI 网关

你来定。

七、开发路线

不分 MVP/正式,按构建顺序排列。
每一步都是可运行的完整状态。

Week 1-2: 地基
  ├── 项目脚手架(目录结构、Makefile、CI)
  ├── PostgreSQL schema + sqlc 生成
  ├── 配置系统 (config.yaml)
  ├── docker-compose 开发环境
  └── 交付: docker-compose up 能启动

Week 3-4: 认证 + 推理
  ├── 用户注册/登录 (JWT)
  ├── API Key 生成/验证
  ├── OpenAI 兼容 /v1/chat/completions
  ├── llama.cpp 接入 (CPU 推理)
  ├── SSE 流式输出
  └── 交付: 注册→创建Key→调API→得到回答

Week 5-6: 计费
  ├── Token 计量 (tiktoken-go)
  ├── Redis 余额管理 + Lua 原子扣费
  ├── usage_logs 异步写入
  ├── 余额检查 middleware
  ├── 充值接口(先做手动加余额,支付后接)
  └── 交付: 调 API 会扣钱,余额不足被拒

Week 7-8: 模型管理 + Operator
  ├── 模型注册/列表/详情 API
  ├── InferenceService CRD + Operator
  ├── vLLM 推理引擎接入
  ├── 多模型路由
  ├── HPA 自动伸缩
  └── 交付: 在 K8s 上部署多个模型,通过 API 调用

Week 9-10: 数据 + 训练
  ├── 数据集上传/校验/统计
  ├── TrainingJob CRD + Operator
  ├── Python 训练镜像 (LoRA)
  ├── Checkpoint 管理
  ├── 训练监控 (loss 曲线)
  └── 交付: 上传数据→提交训练→产出模型→部署上线

Week 11-12: 前端
  ├── React 项目搭建
  ├── 登录/注册/Dashboard
  ├── Playground 对话界面
  ├── 模型列表/详情
  ├── 数据集管理界面
  ├── 训练任务界面
  ├── 计费/用量界面
  └── 交付: 全功能 Web 控制台

Week 13-14: 企业功能
  ├── 组织/成员管理
  ├── API Key 权限细化
  ├── 套餐/充值/账单
  ├── RAG 知识库
  ├── 批量推理
  └── 交付: 多租户、多模型、完整计费

Week 15-16: 生产化
  ├── Helm Chart 完善
  ├── Prometheus 监控集成
  ├── 告警规则
  ├── 文档(用户/开发者/部署)
  ├── GitHub Actions CI/CD
  ├── 性能测试 + 安全审计
  └── 交付: 可对外发布的 v1.0

八、技术选型一览表

类别 选型 版本 备选
后端语言 Go 1.22+
API 路由 chi v5 gin, echo
SQL 工具 sqlc 1.25+ GORM, ent
数据库迁移 golang-migrate v4 goose
关系数据库 PostgreSQL 16
向量检索 pgvector 0.7+ Milvus, Qdrant
缓存 Redis 7
消息队列 Redis Stream NATS, RabbitMQ
对象存储 MinIO AWS S3
K8s 客户端 client-go 0.30
Operator 框架 controller-runtime 0.18
推理引擎 vLLM / llama.cpp TGI, Ollama
训练框架 transformers + PEFT
Token 计算 tiktoken-go
前端框架 Next.js + React 14+ Vue
UI 组件 Shadcn/ui + Tailwind Ant Design
容器编排 Kubernetes 1.28+
包管理 Helm 3
CI/CD GitHub Actions + ArgoCD
监控 Prometheus + Grafana
日志 Loki + Promtail EFK
镜像仓库 Harbor Docker Hub
许可证 Apache-2.0