添加代码注释:行级评论、建议和关注点
学完你能做什么
- ✅ 在代码 diff 中添加行级注释(comment/suggestion/concern)
- ✅ 为代码修改提供建议代码(suggestedCode)
- ✅ 标记需要关注的代码段(concern)
- ✅ 查看和管理所有注释(侧边栏)
- ✅ 理解三种注释类型的使用场景
- ✅ 导出反馈为 Markdown 格式
你现在的困境
问题 1:评审代码变更时,只能在终端看 diff,然后写"第 3 行有问题"、"建议改成 XXX",位置不精确。
问题 2:有些代码只是想评论一下(comment),有些想提修改建议(suggestion),有些是严重问题需要关注(concern),但没有工具帮你区分。
问题 3:想给某个函数修改建议,但不知道怎么把代码片段传给 AI。
问题 4:添加了多个注释后,忘记都评审了哪些地方,没有概览。
Plannotator 能帮你:
- 点击行号即可选中代码范围,精确到行
- 三种注释类型(comment/suggestion/concern)分别对应不同场景
- 可以附加建议代码,AI 直接看到修改方案
- 侧边栏列出所有注释,一键跳转
什么时候用这一招
使用场景:
- 执行
/plannotator-review命令后查看代码变更 - 需要对具体代码行给出反馈
- 想提供代码修改建议给 AI
- 需要标记潜在问题或风险点
不适用场景:
- 评审 AI 生成的实施计划(使用计划评审功能)
- 只需要快速浏览 diff(使用代码评审基础功能)
🎒 开始前的准备
前置条件:
触发方式:
- 在 OpenCode 或 Claude Code 中执行
/plannotator-review命令
核心思路
代码注释是什么
代码注释是 Plannotator 代码评审的核心功能,用于在 Git diff 中添加行级反馈。通过点击行号选中代码范围,你可以精确地针对具体代码行添加评论、建议或关注点,注释会显示在 diff 下方,便于 AI 准确理解你的反馈意图。
为什么需要代码注释?
在代码评审中,你需要对具体的代码行给出反馈。如果只是用文字描述"第 5 行有问题"、"建议改成 XXX",AI 需要自己去定位代码,容易出错。Plannotator 让你点击行号选中代码范围,直接在该位置添加注释,注释会显示在 diff 下方(GitHub 风格),AI 能准确看到你针对哪段代码提出的建议。
工作流程
┌─────────────────┐
│ /plannotator- │ 触发命令
│ review 命令 │
└────────┬────────┘
│
│ 运行 git diff
▼
┌─────────────────┐
│ Diff Viewer │ ← 显示代码 diff
│ (split/unified) │
└────────┬────────┘
│
│ 点击行号 / Hover +
▼
┌─────────────────┐
│ 选中代码范围 │
│ (lineStart- │
│ lineEnd) │
└────────┬────────┘
│
▼
┌─────────────────┐
│ 添加注释 │ ← 工具栏弹出
│ - Comment │ 填写评论内容
│ - Suggestion │ 可选:提供建议代码
│ - Concern │
└────────┬────────┘
│
▼
┌─────────────────┐
│ 注释显示 │ 在 diff 下方
│ (GitHub 风格) │ 侧边栏列出所有注释
└────────┬────────┘
│
▼
┌─────────────────┐
│ 导出反馈 │ Send Feedback
│ (Markdown) │ AI 收到结构化反馈
└─────────────────┘注释类型
Plannotator 支持三种代码注释类型,每种都有不同的用途:
| 注释类型 | 用途 | 典型场景 | 建议代码 |
|---|---|---|---|
| Comment | 评论某段代码,提供一般性反馈 | "这段逻辑可以简化"、"变量命名不太清晰" | 可选 |
| Suggestion | 提供具体的代码修改建议 | "建议用 map 替代 for 循环"、"用 await 替代 Promise.then" | 推荐 |
| Concern | 标记潜在问题或风险点 | "这个 SQL 查询可能有性能问题"、"缺少错误处理" | 可选 |
注释类型的选择建议
- Comment:用于"提建议但不强制",比如代码风格、优化方向
- Suggestion:用于"强烈建议修改",并且你有明确的修改方案
- Concern:用于"必须注意的问题",比如 bug、性能风险、安全隐患
Comment vs Suggestion vs Concern
| 场景 | 选择类型 | 示例文本 |
|---|---|---|
| 代码可以工作,但有优化空间 | Comment | "这段可以用 async/await 简化" |
| 代码有明确的改进方案 | Suggestion | "建议用 Array.from() 替代展开运算符"(附代码) |
| 发现 bug 或严重问题 | Concern | "这里缺少 null 检查,可能导致运行时错误" |
跟我做
第 1 步:触发代码评审
在终端中执行:
/plannotator-review你应该看到:
- 浏览器自动打开代码评审界面
- 显示 git diff 内容(默认是
git diff HEAD) - 左侧是文件树,中间是 diff viewer,右侧是注释侧边栏
第 2 步:浏览 diff 内容
在浏览器中查看代码变更:
- 默认使用 split 视图(左右对比)
- 可以切换到 unified 视图(上下对比)
- 点击文件树中的文件名切换查看的文件
第 3 步:选中代码行,添加注释
方式一:Hover 点击 "+" 按钮
- 将鼠标悬停在要添加注释的代码行上
- 右侧会出现一个 + 按钮(仅在 diff 行上显示)
- 点击 + 按钮
- 弹出注释工具栏
方式二:直接点击行号
- 点击某个行号(例如
L10),选中单行 - 点击另一个行号(例如
L15),选中多行范围 - 选中范围后,工具栏自动弹出
你应该看到:
- 工具栏显示选中行号(例如
Line 10或Lines 10-15) - 工具栏包含文本输入框(
Leave feedback...) - 可选的"Add suggested code"按钮
第 4 步:添加 Comment 注释
场景:对代码提供建议,但不要求必须修改
- 在工具栏的文本框中输入评论内容
- 可选:点击 Add suggested code,输入建议代码
- 点击 Add Comment 按钮
示例:
评论内容:这个函数的参数命名不太清晰,建议改名为 fetchUserData你应该看到:
- 工具栏消失
- 注释显示在 diff 下方(蓝色框)
- 侧边栏中新增一条注释记录
- 如果提供了建议代码,会显示在注释下方(代码块格式)
第 5 步:添加 Suggestion 注释
场景:提供明确的代码修改方案,希望 AI 直接采用
- 在工具栏的文本框中输入建议说明(可选)
- 点击 Add suggested code
- 在出现的代码输入框中输入建议的代码
- 点击 Add Comment 按钮
示例:
建议说明:使用 async/await 简化 Promise 链
建议代码:
async function fetchData() {
const response = await fetch(url);
const data = await response.json();
return data;
}你应该看到:
- 注释显示在 diff 下方(蓝色框)
- 建议代码以代码块形式显示,带"Suggested:"标签
- 侧边栏中显示建议代码的第一行(带省略号)
第 6 步:添加 Concern 注释
场景:标记潜在问题或风险点,提醒 AI 注意
注意:当前版本的 Plannotator UI 中,注释类型默认为 Comment。如果需要标记 Concern,可以在注释文本中明确说明。
- 在工具栏的文本框中输入关注点说明
- 可以使用
Concern:或⚠️等标记明确这是关注点 - 点击 Add Comment 按钮
示例:
Concern: 这里缺少 null 检查,如果 user 为 null 会导致运行时错误
建议添加:
if (!user) return null;你应该看到:
- 注释显示在 diff 下方
- 侧边栏中显示注释内容
第 7 步:查看和管理注释
在侧边栏中查看所有注释:
- 右侧边栏显示所有注释列表
- 每条注释显示:
- 文件名(截取最后一个路径组件)
- 行号范围(例如
L10或L10-L15) - 作者(如果是协作评审)
- 时间戳(例如
5m、2h、1d) - 注释内容(最多显示 2 行)
- 建议代码预览(第一行)
点击注释跳转:
- 在侧边栏中点击某条注释
- Diff viewer 自动滚动到对应位置
- 该注释被高亮显示
删除注释:
- 鼠标悬停在侧边栏中的某条注释上
- 点击右上角的 × 按钮
- 注释被删除,diff 中的高亮消失
你应该看到:
- 侧边栏显示注释数量(例如
Annotations: 3) - 点击注释后,diff viewer 平滑滚动到对应行
- 删除注释后,数量更新
第 8 步:导出反馈
完成所有注释后,点击页面底部的 Send Feedback 按钮。
你应该看到:
- 浏览器自动关闭
- 终端中显示 Markdown 格式的反馈内容
- AI 收到结构化反馈,可以自动响应
导出的 Markdown 格式:
# Code Review Feedback
## src/app/api/users.ts
### Line 10 (new)
这段逻辑可以简化,建议用 async/await
### Lines 15-20 (new)
**Suggested code:**
```typescript
async function fetchUserData() {
const response = await fetch(url);
return await response.json();
}Line 25 (old)
Concern: 这里缺少 null 检查,如果 user 为 null 会导致运行时错误
::: tip 复制反馈
如果需要手动复制反馈内容,可以在侧边栏底部点击 **Copy Feedback** 按钮,将 Markdown 格式的反馈复制到剪贴板。
:::
## 检查点 ✅
完成以上步骤后,你应该能够:
- [ ] 在代码 diff 中点击行号或 Hover "+" 按钮选中代码行
- [ ] 添加 Comment 注释(一般性评论)
- [ ] 添加 Suggestion 注释(附建议代码)
- [ ] 添加 Concern 注释(标记潜在问题)
- [ ] 在侧边栏查看所有注释,点击跳转到对应位置
- [ ] 删除不需要的注释
- [ ] 导出反馈为 Markdown 格式
- [ ] 复制反馈内容到剪贴板
**如果某一步失败**,详见:
- [常见问题](../../faq/common-problems/)
- [代码评审基础](../code-review-basics/)
- [故障排查](../../faq/troubleshooting/)
## 踩坑提醒
**常见错误 1**:点击行号后,工具栏没有弹出
**原因**:可能点击的是文件名或行号不在 diff 范围内。
**解决**:
- 确保点击的是 diff 行的行号(绿色或红色行)
- 对于删除行(红色),点击左侧的行号
- 对于新增行(绿色),点击右侧的行号
**常见错误 2**:选中多行后,注释显示在错误的位置
**原因**:side(old/new)不正确。
**解决**:
- 检查你选中的是旧代码(deletions)还是新代码(additions)
- 注释会显示在范围最后一行的下方
- 如果位置不对,删除注释重新添加
**常见错误 3**:添加建议代码后,代码格式错乱
**原因**:建议代码可能包含特殊字符或缩进问题。
**解决**:
- 在建议代码输入框中,确保缩进正确
- 使用等宽字体编辑建议代码
- 如果有换行,使用 `Shift + Enter` 而不是直接回车
**常见错误 4**:侧边栏中看不到新增的注释
**原因**:侧边栏可能没有刷新,或者注释添加到了其他文件。
**解决**:
- 切换文件后再切换回来
- 检查注释是否添加到了当前查看的文件
- 刷新浏览器页面(可能丢失未提交的注释)
**常见错误 5**:导出反馈后,AI 没有按建议修改
**原因**:AI 可能没有正确理解注释的意图,或者建议不可行。
**解决**:
- 使用更明确的注释(Suggestion 比 Comment 更明确)
- 在建议代码中添加注释说明原因
- 如果问题持续,可以再次发送反馈,调整注释内容
## 本课小结
代码注释是 Plannotator 代码评审的核心功能,让你可以精确地反馈代码问题:
**核心操作**:
1. **触发**:执行 `/plannotator-review`,浏览器自动打开 diff viewer
2. **浏览**:查看代码变更(split/unified 视图切换)
3. **选中**:点击行号或 Hover "+" 按钮选中代码范围
4. **注释**:添加 Comment/Suggestion/Concern 注释
5. **管理**:在侧边栏查看、跳转、删除注释
6. **导出**:Send Feedback,AI 收到结构化反馈
**注释类型**:
- **Comment**:一般性评论,提供建议但不强制
- **Suggestion**:明确建议修改,附建议代码
- **Concern**:标记潜在问题或风险点
**最佳实践**:
- 使用 Suggestion 时,尽量提供完整的可运行代码
- 对于性能或安全问题,使用 Concern 标记
- 注释内容要具体,避免模糊描述(如"这个不好")
- 可以附加图片辅助说明(使用图像标注功能)
## 下一课预告
> 下一课我们学习 **[切换 Diff 视图](../code-review-diff-types/)**。
>
> 你会学到:
> - 如何切换不同的 diff 类型(uncommitted/staged/last commit/branch)
> - 不同 diff 类型的使用场景
> - 如何在多种 diff 类型间快速切换
---
## 附录:源码参考
<details>
<summary><strong>点击展开查看源码位置</strong></summary>
> 更新时间:2026-01-24
| 功能 | 文件路径 | 行号 |
|--- | --- | ---|
| CodeAnnotation 类型定义 | [`packages/ui/types.ts`](https://github.com/backnotprop/plannotator/blob/main/packages/ui/types.ts#L53-L56) | 53-56 |
| CodeAnnotation 接口 | [`packages/ui/types.ts`](https://github.com/backnotprop/plannotator/blob/main/packages/ui/types.ts#L55-L66) | 55-66 |
| DiffViewer 组件 | [`packages/review-editor/components/DiffViewer.tsx`](https://github.com/backnotprop/plannotator/blob/main/packages/review-editor/components/DiffViewer.tsx#L1-L349) | 1-349 |
| ReviewPanel 组件 | [`packages/review-editor/components/ReviewPanel.tsx`](https://github.com/backnotprop/plannotator/blob/main/packages/review-editor/components/ReviewPanel.tsx#L1-L211) | 1-211 |
| 导出反馈 Markdown | [`packages/review-editor/App.tsx`](https://github.com/backnotprop/plannotator/blob/main/packages/review-editor/App.tsx#L86-L126) | 86-126 |
| Hover "+" 按钮 | [`packages/review-editor/components/DiffViewer.tsx`](https://github.com/backnotprop/plannotator/blob/main/packages/review-editor/components/DiffViewer.tsx#L180-L199) | 180-199 |
| 注释工具栏 | [`packages/review-editor/components/DiffViewer.tsx`](https://github.com/backnotprop/plannotator/blob/main/packages/review-editor/components/DiffViewer.tsx#L267-L344) | 267-344 |
| 注释渲染 | [`packages/review-editor/components/DiffViewer.tsx`](https://github.com/backnotprop/plannotator/blob/main/packages/review-editor/components/DiffViewer.tsx#L140-L177) | 140-177 |
**关键类型**:
- `CodeAnnotationType`:代码注释类型('comment' | 'suggestion' | 'concern')(`packages/ui/types.ts:53`)
- `CodeAnnotation`:代码注释接口(`packages/ui/types.ts:55-66`)
- `SelectedLineRange`:选中的代码范围(`packages/ui/types.ts:77-82`)
**关键函数**:
- `exportReviewFeedback()`:将注释转换为 Markdown 格式(`packages/review-editor/App.tsx:86`)
- `renderAnnotation()`:在 diff 中渲染注释(`packages/review-editor/components/DiffViewer.tsx:140`)
- `renderHoverUtility()`:渲染 Hover "+" 按钮(`packages/review-editor/components/DiffViewer.tsx:180`)
**API 路由**:
- `POST /api/feedback`:提交评审反馈(`packages/server/review.ts`)
- `GET /api/diff`:获取 git diff(`packages/server/review.ts:111`)
- `POST /api/diff/switch`:切换 diff 类型(`packages/server/review.ts`)
**业务规则**:
- 默认查看未提交的 diff(`git diff HEAD`)(`packages/server/review.ts:111`)
- 注释显示在范围最后一行的下方(GitHub 风格)(`packages/review-editor/components/DiffViewer.tsx:81`)
- 支持在注释中附加建议代码(`suggestedCode` 字段)(`packages/ui/types.ts:63`)
</details>