AI 工具链反思:平台团队到底该自研哪些轮子

AI2周前发布 beixibaobao
9 0 0

AI 工具链反思:平台团队到底该自研哪些轮子

一、每个平台团队都趟过的坑

2025 年上半年,我们平台组做了一个决定:自研一套 Prompt 管理平台。三个月后,平台上线了,功能包括 Prompt 模板编辑、版本对比、在线评估。又过了两个月,团队发现 Langfuse 开源版完全覆盖了这些需求,而且社区迭代速度快三倍。

类似的踩坑还有:自研模型网关(Kong + 自定义插件完全够用)、自研模型性能监控面板(Grafana + Prometheus 现成的)、自研训练任务调度器(Argo Workflows 成熟且稳定)。

每次自研的理由都差不多:"开源的不好用""我们需要定制化""用别人的有 lock-in 风险"。但三个月后回头看,大多数自研项目都变成了团队无人维护的技术债。

基础设施不需要漂亮话。轮子质量的唯一衡量标准是它在生产环境跑了多久、多少人在维护。

二、自研 vs 复用决策框架

是否自研一个组件,可以通过以下四个维度做决策:

flowchart TD
    Q1{是否为<br/>核心差异化能力?}
    Q1 -->|否| B[直接采用开源方案]
    Q1 -->|是| Q2{开源方案<br/>功能差距大?}
    Q2 -->|否,差距<20%| C[采用开源<br/>提 PR 贡献功能]
    Q2 -->|是,差距>50%| Q3{团队能否<br/>长期维护?}
    Q3 -->|不能| D[采用开源+封装]
    Q3 -->|能| Q4{社区迭代速度<br/>比团队快?}
    Q4 -->|是| E[参与开源贡献<br/>避免重复造轮子]
    Q4 -->|否| F[自研<br/>明确维护计划]
    B --> G[聚焦核心业务]
    C --> G
    D --> H[控制自研范围]
    E --> G
    F --> I[需要文档、测试<br/>和 on-call 计划]

四维决策矩阵:

维度一:是否是核心差异化能力。Kubernetes 调度优化(如 GPU 拓扑感知调度)是平台团队的差异化能力,值得自研。但 API 网关、日志采集、监控面板等通用能力,开源方案成熟且社区活跃,不应该自研。

维度二:开源方案的功能差距。如果开源方案覆盖了你 80% 以上的需求,剩余 20% 通过配置或插件就能解决,不应自研。只有当核心场景完全不匹配时才考虑自研。

维度三:团队长期维护能力。一个自研组件的生命周期是 3-5 年。如果团队只有 3 个人,维护一个自研网关就会耗尽所有精力。自研决策不是敲代码那三个月,而是后续三年的 bug 修复、升级、安全补丁。

维度四:社区迭代速度。如果开源社区每周都在发版,你的自研组件很快就会落后。与其自研,不如贡献到上游——你的定制需求可能也是别人的痛点。

三、AI 平台组件的自研/开源决策实例

以下是一个 Go 语言编写的决策工具,用于量化评估自研可行性:

package buildvsbuy
import (
    "fmt"
    "time"
)
// Component 待评估的组件
type Component struct {
    Name             string
    Category         string  // "orchestration", "observability", "gateway", "storage"
    CoreDifferentiator bool   // 是否是平台核心差异化能力
    TeamSize         int     // 团队人数
    MaintenanceYears int     // 预期维护年限
    OpenSourceGap    float64 // 开源方案功能差距百分比 (0-100)
    CommunityVelocity int    // 社区月均发版次数
}
// Decision 自研决策结果
type Decision struct {
    Build          bool
    Reason         string
    Recommendation string
    RiskLevel      string // "low", "medium", "high"
    EffortEstimate string // 投入预估
}
// Evaluate 执行自研 vs 复用决策
func Evaluate(c Component) Decision {
    // 规则1:非差异化能力且开源差距小 — 直接复用
    if !c.CoreDifferentiator && c.OpenSourceGap < 20 {
        return Decision{
            Build:          false,
            Reason:         "非核心能力,开源方案覆盖度高",
            Recommendation: "直接采用开源方案,如需要可提 PR 贡献",
            RiskLevel:      "low",
            EffortEstimate: "0 人月,仅配置适配",
        }
    }
    // 规则2:团队太小,不要接长期维护的重组件
    if c.TeamSize < 5 && c.MaintenanceYears > 2 {
        return Decision{
            Build:          false,
            Reason:         fmt.Sprintf("团队仅 %d 人,无法长期维护 %d 年", c.TeamSize, c.MaintenanceYears),
            Recommendation: "选择托管服务或带有商业支持的开源方案",
            RiskLevel:      "high",
            EffortEstimate: "0 人月",
        }
    }
    // 规则3:社区迭代快 — 参与社区而非单干
    if c.CommunityVelocity > 4 {
        return Decision{
            Build:          false,
            Reason:         fmt.Sprintf("社区月均发版 %d 次,自研难以跟上", c.CommunityVelocity),
            Recommendation: "参与上游贡献,将定制需求推入主分支",
            RiskLevel:      "medium",
            EffortEstimate: "1-2 人月(贡献代码)",
        }
    }
    // 规则4:核心差异化能力 + 有维护能力 — 可以自研
    if c.CoreDifferentiator && c.TeamSize >= 5 {
        var effort string
        switch c.Category {
        case "orchestration":
            effort = "4-6 人月(含设计、实现、测试、文档)"
        case "gateway":
            effort = "2-3 人月(插件化架构即可)"
        case "observability":
            effort = "2-4 人月(基于 Prometheus 生态扩展)"
        default:
            effort = "3-5 人月"
        }
        return Decision{
            Build:          true,
            Reason:         "核心差异化能力,团队有维护条件",
            Recommendation: "自研但保持接口与开源兼容,降低未来迁移成本",
            RiskLevel:      "medium",
            EffortEstimate: effort,
        }
    }
    // 默认:不确定时选复用
    return Decision{
        Build:          false,
        Reason:         "不满足自研条件,建议保守选择复用",
        Recommendation: "先用开源方案跑 1-2 个季度,再评估是否需要自研",
        RiskLevel:      "low",
        EffortEstimate: "0 人月",
    }
}
// EvaluationMatrix 评估矩阵,对多个组件批量评估
type EvaluationMatrix struct {
    EvaluatedAt time.Time
    Results     map[string]Decision
}
// EvaluateAll 批量评估
func EvaluateAll(components []Component) EvaluationMatrix {
    matrix := EvaluationMatrix{
        EvaluatedAt: time.Now(),
        Results:     make(map[string]Decision),
    }
    for _, c := range components {
        matrix.Results[c.Name] = Evaluate(c)
    }
    return matrix
}

结合团队的实际情况,以下是 AI 平台各组件的决策示例:

组件 决策 理由
GPU 拓扑感知调度器 自研 K8s 默认调度器不理解 GPU 拓扑。这是平台的差异化能力
API 网关 复用 Kong 开源成熟、插件体系完善、社区活跃
模型版本管理 复用 MLflow 社区标准,不需要自己造
训练任务调度 复用 Argo Workflows 比 K8s Job 更适合 DAG 任务编排
Prompt 管理 复用 Langfuse 开源版功能完整,迭代速度快
内部 CLI 工具集 自研 封装内部 Workflow,提升开发效率
监控面板 复用 Grafana 生态最完整,自定义 Dashboard 即可

四、自研组件的生存法则

如果决定自研,需要遵守以下约束,否则组件很快变成无人维护的废墟:

设计时就定义退出策略。自研组件的 API 必须与社区标准对齐。比如自研的模型网关,它的路由配置格式应该兼容 OpenAI API Proxy 的规范。这样未来迁移到开源方案时,上游调用方不需要改代码。

文档要求。自研组件必须有设计文档、API 文档、运维手册。如果组件挂了,文档是 on-call 同事唯一的依赖。没有文档的自研组件就是一颗地雷。

代码覆盖率要求。自研组件的单元测试覆盖率不低于 70%,关键路径(如调度决策、权限校验)需要集成测试。

维护人力预算。自研组件的维护成本不会低于开发成本的 30%/年。如果一个组件需要 3 人月开发,每年至少需要 1 人月做 bug 修复、依赖升级和安全补丁。

定期复盘。每个季度复盘一次所有自研组件:是否还有维护价值?社区是否有新的替代方案?使用量是否在持续增长?发现没有用的组件要果断下线——"留着以防万一"的代码就是债务。

开源回馈。如果自研组件解决了通用问题,考虑将其开源。开源能带来社区贡献者和更广的测试覆盖,降低长期维护成本。

五、总结

平台团队的自研决策需要基于四维框架:是否核心差异化能力、开源方案功能差距、团队维护能力、社区迭代速度。

关键原则:非核心能力直接复用开源方案;小团队不自研需要长期维护的重组件;社区迭代快的组件参与上游贡献而非自研;自研组件必须设计退出策略和完善文档;每季度复盘所有自研组件去留。轮子的价值由生产环境运行时长和社区活跃度决定,不是由初始设计文档的页数决定。

© 版权声明

相关文章