Spotify 首席架构师在 Code with Claude 大会上抛出一个判断:写代码本身已经不再是约束了。真正卡住交付速度的,是团队协作摩擦、重复的基建搭建、以及工具链对 AI Agent 的不友好。他们的应对方式是——用平台工程把开发者体验(DevEx)从"个人写代码"的维度,拉升到"团队+Agent 高效运转"的维度。
这个判断值得认真对待。下面拆开看。
瓶颈已经转移
单个开发者写代码的速度,在 LLM 辅助下已经大幅提升。Copilot、Claude Code、Cursor 这类工具让函数实现、测试编写、重构这些"手活"变快了。但 Spotify 的观察是:代码产出速度提升之后,下一个瓶颈立刻暴露——团队级别的协调和基础设施的一致性。
具体表现:
- 新服务上线仍要手动拼装:CI pipeline、监控、日志、权限模板,每个团队各写一遍,格式不同、质量参差。
- 跨团队依赖靠口口相传:谁负责哪个 API、哪个数据 schema 最近改了什么,全靠 Slack 消息和 wiki 页面,没有结构化入口。
- Agent 无法自助操作:AI Agent 想部署一个服务、查一个依赖关系,必须走人类审批流程或翻文档,无法直接调用平台 API。
Spotify 的核心思路:把这些重复的、协调性的工作收进内部平台,让人和 Agent 都能自助完成。
Backstage:从开发者门户到团队操作系统
Spotify 开源了 Backstage——一个开发者门户框架,很多人把它当"文档站"用,但 Spotify 内部的定位远不止于此。Backstage 在他们内部是团队级别的操作系统:每个团队在 Backstage 里有一个"home page",上面聚合了该团队所有服务的 CI 状态、监控面板、API 文档、依赖拓扑、所有权信息。
关键设计原则:
- 软件模板(Software Templates):一键生成符合公司标准的新服务,自带 CI、监控、日志、安全扫描配置,而不是让每个团队从零拼。
- 插件架构:每个内部工具(部署系统、数据平台、权限管理)以插件形式接入 Backstage,开发者不需要记住十几个不同系统的 URL。
- 服务目录(Service Catalog):所有服务、API、数据集的结构化注册,所有权和依赖关系一目了然。
下面是一个 Backstage 软件模板的 YAML 示例——你可以用它一键创建一个标准化微服务骨架:
# backstage-templates/microservice-template.yaml
# 在 Backstage 中注册此模板后,开发者点击即可生成标准化微服务项目
apiVersion: scaffolder.backstage.io/v1
kind: Template
metadata:
name: microservice-standard
title: Standard Microservice
description: 生成一个符合平台标准的微服务,自带 CI、监控、健康检查
spec:
owner: platform-team
type: service
parameters:
- title: 基本信息填写
required:
- name
- owner
properties:
name:
title: 服务名
type: string
pattern: '^[a-z][a-z0-9-]{4,30}$'
description: 小写字母开头,5-31 字符,仅允许小写字母、数字和连字符
owner:
title: 所属团队
type: string
ui:field: OwnerPicker
ui:options:
allowedKinds:
- Group
description:
title: 服务描述
type: string
steps:
- id: fetch-base
name: 拉取基础骨架
action: fetch:template
input:
url: ./skeleton
values:
name: '{{ parameters.name }}'
owner: '{{ parameters.owner }}'
description: '{{ parameters.description }}'
- id: publish
name: 推送到 Git 仓库
action: publish:github
input:
repoUrl: 'https://github.com/{{ parameters.owner }}/{{ parameters.name }}'
description: '{{ parameters.description }}'
- id: register
name: 注册到服务目录
action: catalog:register
input:
catalogInfoUrl: 'https://github.com/{{ parameters.owner }}/{{ parameters.name }}/blob/main/catalog-info.yaml'
output:
links:
- title: 仓库地址
url: 'https://github.com/{{ parameters.owner }}/{{ parameters.name }}'
- title: 打开服务详情
icon: catalog
entityRef: 'service:default/{{ parameters.name }}'
运行前提:你需要一个运行中的 Backstage 实例,并在
app-config.yaml中注册此模板路径。详见 Backstage 官方文档。
这个模板的价值不在于"生成了代码",而在于生成了一个符合平台标准的完整服务配置包——CI pipeline、监控探针、服务目录注册一步到位,省掉了每个团队重复踩坑的环节。
为 Agent 设计平台接口
Spotify 架构师特别强调了"扩展到 Agent"这一层。当 AI Agent 能写代码之后,如果它只能写代码而不能操作平台(部署、查依赖、改配置),那 Agent 的生产力就被卡在"写完代码等人类审批"这一步。
实践方向是:让平台的关键操作暴露为 Agent 可调用的 API 或 CLI。
下面是一个概念性示例——假设你有一个内部部署平台,为 Agent 开放 CLI 和 API 两种调用方式:
# deploy_agent_client.py
# Agent 通过此客户端自助部署服务,无需人类手动操作 UI
# 前提:部署平台已开放 REST API,Agent 拥有 scoped token
import os
import requests
DEPLOY_API = os.environ.get("DEPLOY_API_URL", "https://deploy.internal.spotify.net/api/v1")
TEAM_TOKEN = os.environ.get("DEPLOY_TEAM_TOKEN") # scoped token,仅允许部署指定团队的服务
def deploy_service(service_name: str, version: str, env: str = "staging") -> dict:
"""Agent 调用部署 API,将指定版本推到目标环境"""
resp = requests.post(
f"{DEPLOY_API}/deployments",
headers={"Authorization": f"Bearer {TEAM_TOKEN}"},
json={
"service": service_name,
"version": version,
"environment": env,
"auto_monitor": True, # 自动挂载监控面板
},
timeout=30,
)
resp.raise_for_status()
return resp.json()
def get_deployment_status(deployment_id: str) -> dict:
"""查询部署进度,Agent 可据此决定下一步动作"""
resp = requests.get(
f"{DEPLOY_API}/deployments/{deployment_id}",
headers={"Authorization": f"Bearer {TEAM_TOKEN}"},
timeout=10,
)
resp.raise_for_status()
return resp.json()
# ---- Agent 使用示例 ----
if __name__ == "__main__":
# Agent 写完代码、推完 Git 后,直接调用部署
result = deploy_service("playlist-recommender", "v2.3.1", env="staging")
print(f"部署已触发,ID: {result['deployment_id']}")
# Agent 轮询状态,确认部署成功后再继续下一步
status = get_deployment_status(result["deployment_id"])
print(f"当前状态: {status['status']}")
注意:这是基于"平台为 Agent 开放 API"这一思路的实践示例,具体接口设计需根据你内部平台的实际情况调整。核心原则是——Agent 应该能用 scoped token 自助完成部署、查询、配置变更,而不是每一步都等人类审批。
关键设计要点:
- Scoped Token:Agent 的 token 权限要窄——只允许操作指定团队的服务、只允许部署到 staging,生产环境仍需人类确认。
- 结构化返回:API 返回 deployment_id 和状态,Agent 可以据此编排后续步骤(跑测试、通知团队、升级到生产)。
- 幂等性:同一个部署请求重复调用不会产生副作用,Agent 重试时不会出错。
从个人效率到系统效率
Spotify 这套做法的核心转变是:DevEx 的优化对象从"单个开发者写代码的体验"变成了"整个团队+Agent 协作运转的体验"。
这意味着几件事:
| 维度 | 旧焦点 | 新焦点 |
|---|---|---|
| 瓶颈 | 写代码慢 | 协调摩擦大、基建不一致 |
| 优化对象 | 个人 IDE 体验 | 团队自助平台 + Agent API |
| 标准化手段 | 代码规范 lint | 软件模板一键生成标准项目 |
| 知识管理 | wiki + Slack | 结构化服务目录 + 插件聚合 |
| Agent 角色 | 辅助写代码 | 自助操作平台全流程 |
落地检查清单
如果你的团队也在思考"写代码不再是瓶颈之后该做什么",可以逐项检查:
- 有没有软件模板? 新服务上线是否需要手动拼 CI、监控、权限?如果是,先做模板。
- 服务目录是否结构化? 团队成员和 Agent 能否一条查询知道"谁负责这个 API、它依赖什么、当前状态如何"?
- 平台关键操作是否对 Agent 开放? 部署、配置变更、依赖查询——这些操作 Agent 能否用 scoped token 自助完成?
- Agent 的权限边界是否明确? staging 自助、生产需人类确认——这条线划清楚了吗?
- 插件是否覆盖核心工具链? CI、监控、部署、数据平台、权限——开发者(和 Agent)是否在一个入口内完成所有操作,还是仍要跳转十几个系统?
写代码变快了,但交付速度没跟上——这个落差,大概率不在代码本身,而在代码之外的摩擦。Spotify 的回答是:用平台工程把摩擦系统性地消掉,让团队和 Agent 都能跑起来。