Composer 多文件编辑
如果说 Chat 更像“边问边改”的协作方式,那 Composer 就更像你把一个相对完整的任务交给 Cursor 去推进。
它最有价值的地方,不是单纯能改多个文件,而是它能把“一个功能通常会牵动多个位置”这件事放到同一个工作流里处理。
打开 Composer
| 操作 | macOS | Windows/Linux |
|---|---|---|
| 打开 Composer | Cmd + I | Ctrl + I |
| 全局 Composer | Cmd + Shift + I | Ctrl + Shift + I |
Composer vs Chat 的区别
| 特性 | Chat | Composer |
|---|---|---|
| 多文件编辑 | ❌ 单文件 | ✅ 多文件 |
| 实时预览 | ❌ | ✅ |
| 代码应用 | 需手动 | 一键应用 |
| 适用场景 | 问答、小修改 | 功能实现、重构 |
我自己的判断很简单:
- 你还在确认方向,用 Chat
- 你已经知道要改一串相关文件,用 Composer
如果一开始就上 Composer,但任务本身还没想清楚,它也会变得很吵。
基础用法
创建新功能
> 创建一个用户登录表单组件,包含:
> - 邮箱和密码输入框
> - 表单验证
> - 提交按钮和 loading 状态
> - 使用 React Hook Form
> - Tailwind CSS 样式
Composer 会自动:
- 创建新组件文件
- 添加必要的类型定义
- 实现表单逻辑
- 更新相关导入
这正是 Composer 最省时间的地方。很多开发任务不是难在某一段代码,而是烦在“改这边就得补那边、文件之间要一起对齐”。Composer 正好擅长这种成串的改动。
修改现有代码
> @src/components/UserList.tsx
> 修改这个组件:
> 1. 添加分页功能
> 2. 添加搜索过滤
> 3. 优化性能,使用 useMemo
重构代码
> @src/services/api.ts
> 重构这个文件:
> 1. 将 API 调用改为使用 axios
> 2. 添加统一的错误处理
> 3. 添加请求拦截器
> 4. 创建对应的 TypeScript 类型
高级功能
指定文件范围
使用 @ 符号指定要操作的文件:
> @src/hooks/ @src/components/
> 在这些文件中:
> 1. 将所有 useState 改为 useReducer
> 2. 统一错误处理方式
Agent 模式
Composer 支持 Agent 模式,可以自主探索和修改:
> [启用 Agent 模式]
> 实现一个完整的购物车功能,包括:
> - 添加/删除商品
> - 修改数量
> - 计算总价
> - 持久化到 localStorage
Agent 会自动:
- 分析项目结构
- 确定需要修改的文件
- 创建缺失的文件
- 更新依赖导入
这一模式很强,但也更需要你盯住范围。能力越强,越不能放着不看。尤其在真实项目里,我会默认先看计划,再看 diff,再决定是不是应用。
预览和确认
Composer 生成代码后会显示预览:
- 查看差异: 点击文件名查看具体更改
- 逐个确认: 可以选择应用哪些更改
- 编辑后应用: 可以在预览中手动修改
- 一键应用: 确认无误后全部应用
最佳实践
1. 详细描述需求
❌ 模糊描述
> 添加一个表单
✅ 详细描述
> 创建用户注册表单 (src/components/RegisterForm.tsx)
>
> 功能要求:
> - 字段:用户名、邮箱、密码、确认密码
> - 验证:必填、邮箱格式、密码至少 8 位、两次密码一致
> - 提交后调用 @src/services/auth.ts 中的 register API
>
> 技术要求:
> - 使用 react-hook-form + zod
> - Tailwind CSS 样式
> - 显示 loading 和错误状态
2. 提供上下文
> 参考 @src/components/LoginForm.tsx 的风格,创建注册表单
> 使用同样的表单验证模式和样式规范
3. 分阶段实现
对于大型功能,分阶段请求:
阶段 1:> 创建数据模型和类型定义
阶段 2:> 实现 API 服务层
阶段 3:> 创建 UI 组件
阶段 4:> 添加状态管理
阶段 5:> 编写测试
4. 利用现有代码
> 基于 @src/components/ProductCard.tsx 的模式,
> 创建 CategoryCard、BrandCard、CollectionCard 三个组件
> 保持相同的样式和交互模式
这一步很重要,因为 Cursor 在“顺着现有模式继续写”时通常会比“完全从零猜一个新模式”稳定得多。
常用场景
添加新页面
> 创建一个 Dashboard 页面:
> 1. 路由: /dashboard
> 2. 组件: src/pages/Dashboard/
> 3. 包含:统计卡片、图表、最近活动列表
> 4. 使用 @src/components/Layout 作为布局
数据库操作 (Prisma)
> 添加用户收藏功能:
> 1. 更新 schema.prisma,添加 Favorite 模型
> 2. 创建 @src/services/favorite.ts 服务
> 3. 添加 API 路由
> 4. 前端组件:收藏按钮
API 集成
> 集成 Stripe 支付:
> 1. 安装必要依赖
> 2. 创建 @src/services/stripe.ts
> 3. 添加结账流程组件
> 4. 处理 webhook 回调
如果你已经开始做这类跨层改动,就很适合用 Composer。因为这已经不是“写一段代码”,而是“让多个位置一起对齐”。
常见问题
生成的代码有错误?
- 提供更多上下文
- 指定使用的库版本
- 给出代码示例参考
修改范围过大?
- 使用
@限定文件范围 - 分批次进行修改
- 先预览再应用
没有预期的更改?
- 检查描述是否清晰
- 确认文件路径正确
- 尝试重新描述需求
还有一个很常见的问题是:Composer 改得太多,但不一定都错。这时候最怕的不是错误本身,而是你没有能力快速判断哪些改动值得保留。
所以我会非常建议在真实项目里养成一个习惯:
- 先看 diff
- 再看有没有引入不必要文件
- 最后才考虑一键应用
一个更实用的经验
Composer 最适合的,不是“让它接管一切”,而是“把一段本来就应该一起改的工作交给它”。
比如:
- 新增一个完整表单
- 把一个功能从单文件抽成模块
- 把多个同类组件统一改造
这种任务里,它的优势会很明显。
反过来,如果只是改一行逻辑或修一个局部 bug,很多时候 Chat 或 Inline Edit 反而更轻、更快。
下一步
- Tab 智能补全 - 学习代码补全功能
- .cursorrules 配置 - 自定义 AI 行为