| name | lina-feedback |
| description | 用于处理用户对已有实现的反馈分诊与执行闭环:先判断是否需要纳入 OpenSpec 活跃变更或新建变更,再完成根因分析、实现、验证和必要测试。凡是用户针对已有实现反馈 Bug、缺陷、改进点、建议或实现遗漏,即使没有明确提到“反馈”或 OpenSpec,也必须使用本技能。 |
| compatibility | 依赖 openspec CLI、lina-e2e 技能、lina-review 技能。 |
Lina 反馈:结构化的修复、验证与测试覆盖循环
当用户在实现后发现 Bug、改进点或提出建议时,此技能先判断反馈是否值得沉淀为 OpenSpec 记录,再选择追加活跃变更、新建变更、直接修复或仅答复说明。进入 OpenSpec 路径的问题需要组织到tasks.md中的可追踪任务列表;未达到 OpenSpec 记录门槛的问题也必须完成清晰的根因分析、实现取舍、验证和结果说明。
核心原则:
- 先分诊再处理 — 不因存在活跃变更就自动写入 OpenSpec,先判断反馈价值、影响范围和可追踪性需求
- 规范是唯一事实来源 — 达到 OpenSpec 门槛且属于规范级别的变更需先更新规范再记录任务
- 验证方式匹配问题性质 — 功能行为修复需要单元测试或 E2E 测试覆盖;项目治理类反馈使用
openspec validate、静态扫描、文件检查、格式检查或审查结论等治理验证方式
交互语言:与用户交互的内容语言以用户上下文使用的语言为准,用户使用英文则使用英文,用户使用中文则使用中文。
工作流
1. 反馈分诊与 OpenSpec 门槛
关键规则:
- 先判断反馈是否需要 OpenSpec 记录,再决定目标变更;活跃变更只是候选上下文,不是自动追加条件。
- OpenSpec 记录门槛由 AI 自主判断。除非归属存在真实歧义或方案风险需要用户取舍,不要把门槛判断交还给用户。
- 活跃变更是指仍直接存在于
openspec/changes/下、且未被移入openspec/changes/archive/的变更目录。不要将status: complete、所有任务已勾选或其他完成信号视为"非活跃",除非实际已归档。
openspec list --json
当两个信号不一致时,优先遵循文件系统规则:
- 如果变更目录仍存在于
openspec/changes/下且不在archive/中,则为活跃变更。
openspec list --json可能仍将此类变更报告为status: complete;这仅表示实现任务已完成,不表示变更已归档。
- 只有位于
openspec/changes/archive/下的已归档变更才是非活跃的。
处理路径:
| 路径 | 判定标准 | 操作 |
|---|
openspec-existing | 反馈直接修正或补全某个活跃变更的目标、验收、实现缺口、回归问题或治理门禁 | 追加到该活跃变更的tasks.md,必要时更新specs/ |
openspec-new | 反馈形成新的可持续产品能力、模块/API/数据/权限契约、跨模块设计、架构决策或需要长期追踪的治理规则 | 新建变更,再写入最小必要 OpenSpec 文档 |
direct-fix | 反馈是局部实现问题、文案/技能说明微调、轻量治理修正、低风险测试补充,或不具备长期规范沉淀价值 | 不创建或追加 OpenSpec;直接做根因分析、修复和验证,并在结果中说明跳过 OpenSpec 的理由 |
no-change | 反馈只是讨论、已被现有实现覆盖、暂不采纳的建议,或需要先澄清而不能安全落地 | 不修改文件;输出判断依据、已检查证据和下一步条件 |
应进入 OpenSpec 的常见信号:
- 改变用户可观察的功能语义、接口契约、数据模型、权限边界、模块边界或插件宿主能力。
- 修复暴露出原规范缺失、验收标准不完整、任务拆分遗漏或活跃变更实现范围不完整。
- 影响多个模块、插件、端到端工作流、发布治理或后续归档审查。
- 需要在未来审查、归档、回归验证或团队协作中保留明确追踪记录。
通常不进入 OpenSpec 的信号:
- 不改变产品或框架契约的技能文档措辞、注释、格式、局部脚本提示或轻量治理说明。
- 单文件、低风险、无长期设计价值的实现修正,且通过测试或静态检查即可闭环。
- 探索性建议、偏好表达或暂不采纳的方向,尚未形成可执行需求。
分诊后必须先告知:
### 反馈分诊
- 处理路径:direct-fix / openspec-existing / openspec-new / no-change
- 判断依据:<反馈是否达到 OpenSpec 记录门槛的原因>
- 活跃变更:<无 / 已考虑的变更及相关性>
- 后续动作:<直接修复 / 写入目标变更 / 新建变更 / 仅说明>
存在多个活跃变更时:
只有在处理路径为openspec-existing且多个活跃变更都高度相关、无法可靠自主选择时,才向用户确认目标变更。
检测到多个活跃变更。此反馈应追加到哪个变更?
1. config-management — 系统配置 CRUD 管理
2. user-auth — 用户认证增强
请选择 1 或 2:
如果只有一个活跃变更与反馈强相关,则自动选择并告知;如果存在活跃变更但均不相关,不要强行追加。
需要新建变更时:
- 从反馈内容派生 kebab-case 名称(如 "fix-menu-circular-ref")
- 如果名称已存在,添加后缀 ("-2")
- 执行:
openspec new change "<name>"
- 生成最小化的
proposal.md(一段话概述上下文)
- 纯 Bug 修复可跳过
design.md,除非涉及架构变更
OpenSpec 路径告知:"将反馈修复应用到变更:<名称>"
2. 读取当前上下文
如果处理路径为openspec-existing或openspec-new,读取目标变更上下文:
| 文件 | 用途 |
|---|
tasks.md | 任务结构、命名规范、编号 |
design.md | 架构上下文 |
proposal.md | 功能范围和意图 |
specs/ | 增量规范定义 |
find hack/tests/e2e/<module> -maxdepth 1 -type f -name 'TC*.ts' | sort
find apps/lina-plugins/<plugin-id>/hack/tests/e2e/<module> -maxdepth 1 -type f -name 'TC*.ts' | sort
如果处理路径为direct-fix或no-change,只读取判断和验证所需的源码、文档、测试、规则文件或运行证据;不要为了形式化流程创建 OpenSpec 文档。
外部规则文件:
- 读取
AGENTS.md作为顶层规范入口。
- 必须按
AGENTS.md的强制规则加载矩阵识别反馈命中的规则域,并在分诊、记录任务、修改规范、修复代码或输出审查结论前读取所有对应的.agents/rules/*.md。
- 禁止仅凭记忆、历史上下文、摘要或此前读取记录替代本次读取。
- 若触发场景命中但对应规则文件不存在、无法读取或存在无法调和的规则冲突,不得继续反馈修复;必须先修复规则入口或向用户说明阻断原因。
- 每个反馈都必须评估并记录
i18n、缓存一致性、数据权限、开发工具跨平台和测试影响。若存在影响,必须读取对应规则文件并按其中的设计、实现、验证和审查要求执行;若确认无影响,也必须在该反馈的影响分析或审查结论中明确记录。
- 常见规则域包括但不限于:后端 Go 读取
.agents/rules/backend-go.md;API 契约读取.agents/rules/api-contract.md;SQL 和 DAO 读取.agents/rules/database.md;缓存读取.agents/rules/cache-consistency.md;数据权限读取.agents/rules/data-permission.md;源码插件、动态插件、插件同构开发目录和插件生命周期资源读取.agents/rules/plugin.md;前端 UI 读取.agents/rules/frontend-ui.md;测试读取.agents/rules/testing.md;开发工具读取.agents/rules/dev-tooling.md;文档治理读取.agents/rules/documentation.md;OpenSpec 流程读取.agents/rules/openspec.md;i18n读取.agents/rules/i18n.md。
3. 分析和组织问题
对每个报告的问题:
按类型分类:
- bug — 行为不正确,代码与规范不匹配
- missing — 功能不完整,实现存在缺口
- ux — 用户体验改进,无需修改规范
- test-gap — 仅缺少测试覆盖
按规范影响分类:
| 级别 | 定义 | 操作 |
|---|
| implementation | 规范正确,代码有误 | 仅修复代码 |
| spec-level | 需求缺失/不完整/已变更 | 先更新规范,再修复 |
| internal | 无用户可观察变更但涉及可执行行为 | 修复代码,优先单元测试 |
| governance | 文档命名、规范文本、OpenSpec 记录、审查规则说明等项目治理问题 | 修复文档/规范,使用治理验证 |
关联问题分组 — 同一根因 → 合并为单个任务,包含多个验证点。
同时记录 OpenSpec 门槛判断:
openspec-existing:说明关联的活跃变更、关联原因和需要更新的tasks.md/specs/范围。
openspec-new:说明为什么不能放入现有活跃变更,以及新变更的最小范围。
direct-fix:说明为什么不值得沉淀为 OpenSpec,以及采用的验证方式。
no-change:说明不修改的原因和未来触发条件。
4. 更新增量规范(仅限 OpenSpec 路径的规范级别问题)
对于规范级别的问题,在记录任务前先更新规范:
- 确定受影响的能力:
specs/<capability>/spec.md
- 执行增量操作:
<!-- ADDED: 新增需求 -->
### Requirement: 父级选择器循环引用防护
系统应在父级选择器中禁用当前菜单及其所有子菜单,
以防止循环引用。
#### Scenario: 编辑包含子菜单的菜单
WHEN 用户编辑一个包含子菜单的菜单
THEN 父级选择器应禁用当前菜单及所有子菜单
<!-- MODIFIED: 变更需求(包含完整原始块) -->
### Requirement: 导入错误处理
系统应在导入失败时显示错误信息。
**MODIFIED:** 错误信息应包含行号、字段名和校验失败原因。
<!-- REMOVED: 废弃需求 -->
### Requirement: 旧版导入格式
系统应支持旧版 CSV 格式。
**REMOVED:** 此格式不再支持。
**迁移方案:** 使用带表头行的新版 CSV 格式。
5. 将任务列表写入 tasks.md(仅限 OpenSpec 路径)
在tasks.md中追加反馈章节:
## Feedback
- [ ] **FB-1**: 父级选择器在菜单编辑中允许循环引用
- [ ] **FB-2**: 导入错误信息缺少行号和字段详情
- [ ] **FB-3**: 重置密码功能缺少测试覆盖
编号: 顺序使用FB-1、FB-2等。如果章节已存在,从最后编号继续。
每个任务一行 — 不使用子字段。分析在修复阶段进行。
写入前说明分诊结论和拟写入任务;只有在多个目标变更归属不清、任务范围存在高风险取舍或用户明确要求确认时,才暂停等待用户选择。
如果处理路径为direct-fix或no-change,跳过本步骤,并在最终结果中记录未更新tasks.md的原因。
验证覆盖规划(内部):
- 用户可观察的行为变更 → 需要 E2E 测试
- 源码插件专属的用户可观察行为变更 → E2E 放在
apps/lina-plugins/<plugin-id>/hack/tests/e2e/,专属 POM/helper 放在插件同级hack/tests/pages/、hack/tests/support/
- 后端逻辑、服务层、工具函数、缓存、权限、数据权限、插件桥接等内部可执行行为变更 → 需要单元测试或更低成本的自动化测试
- 纯项目治理类反馈 → 不为兜底新增单元测试或 E2E 测试,改用
openspec validate、静态扫描、文件存在性检查、格式检查或审查结论
- 场景合适时优先在现有 TC 或现有测试中添加子断言
6. 执行修复(循环)
对每个 OpenSpec 反馈任务或直接修复项:
a. 告知: ## 修复 FB-X: <问题标题>或## 直接修复: <问题标题>
b. 调查 — 读取源文件,确认根因
c. 实现 — 最小化、聚焦的修复,遵循现有模式
d. 编写/更新测试或治理验证 — 行为修复按AGENTS.md选择单元测试或lina-e2e测试;项目治理类反馈使用规范校验、静态扫描或文件检查
e. 评估影响范围(必须)
实现后,识别回归风险:
| 变更类型 | 关联验证 |
|---|
| 后端 API 端点 | 所有调用该端点的前端页面 |
| 共享组件/工具函数 | 所有使用该组件的页面 |
| 数据库 Schema/DAO | 所有读写受影响表的功能 |
| 认证/权限 | 所有认证测试 + 权限相关测试 |
| 页面特定 | 该模块目录下的所有测试 |
| 项目治理文档/规范 | openspec validate、静态扫描、文件存在性检查或格式检查 |
git grep -l "api/user" -- 'hack/tests/e2e/**/TC*.ts' 'apps/lina-plugins/**/TC*.ts'
告知:
### FB-X 影响分析
- 修改文件:apps/lina-core/internal/controller/menu.go
- 受影响模块:菜单管理
- 回归测试:hack/tests/e2e/iam/menu/TC001-menu-crud.ts, hack/tests/e2e/iam/menu/TC002-auth-menu.ts
同时必须记录:
i18n影响:涉及时列出资源归属、目标语言、验证命令;不涉及时写明无运行时行为、前端 UI、API 文档源文本、插件清单或语言包资源影响。
- 缓存一致性影响:涉及时说明权威数据源、失效机制和分布式策略;不涉及时写明无缓存影响。
- 数据权限影响:涉及时说明读写边界和验证;不涉及时写明无数据操作影响。
- 开发工具跨平台影响:涉及时说明验证;不涉及时写明无开发工具或脚本影响。
- 外部规则加载影响:列出已按
AGENTS.md命中的.agents/rules/*.md;若某规则域确认无影响,写明无影响判断。命中规则但未读取对应规则文件时,不得标记该反馈完成。
f. 验证(标记完成前必须执行)
- 运行此任务新增/更新的测试或治理验证 → 必须通过
- 运行所有已识别的回归测试或回归验证 → 必须通过
- OpenSpec 路径仅在以上都通过后,才能在
tasks.md中将任务标记为[x];直接修复路径不修改tasks.md
如果回归测试失败:
- 如果与当前变更相关,直接修复
- 如果是独立问题,重新执行反馈分诊;达到 OpenSpec 门槛才作为新的 FB 任务添加,否则按直接修复或后续风险报告处理
g. 运行审查 — 完成后调用lina-review技能
7. 综合验证
所有修复完成后:
- 汇总所有任务的回归测试
- 一次性运行全部测试
- 报告:
### 综合验证结果
- 总测试数:N
- 通过:N
- 失败:N(列出详情)
- 回归测试:全部通过 ✓ / X 个失败
如果存在失败 → 重新执行反馈分诊,必要时添加新的 FB 任务,回到步骤 6。
8. 报告完成
## 反馈完成
**处理路径:** direct-fix / openspec-existing / openspec-new / no-change
**变更:** <名称>
**OpenSpec 记录:** 已写入 <change>/tasks.md / 已新建 <change> / 未记录(原因:<原因>)
**报告问题数:** X
**已修复问题数:** Y/X
**新增测试:** Z 个测试用例 / 子断言
**回归测试:** 跨 N 个模块运行 R 个测试
**验证结果:** 全部通过 / 剩余 N 个问题
### 本次已修复
- [x] FB-1: <标题> ✓(测试:TC001a | 回归:iam/menu TC001, TC002 ✓)
- [x] FB-2: <标题> ✓(测试:已有覆盖 | 回归:auth TC003 ✓)
### 剩余(如有)
- [ ] FB-3: <标题> — 被 <原因> 阻塞
边界情况
| 场景 | 处理方式 |
|---|
| 单个问题 | 先分诊;达到 OpenSpec 门槛才写入变更 |
| 仅缺少测试用例 | 分类为 test-gap;若只是局部覆盖缺口可直接补测试,不强制写入 OpenSpec |
| 修复后发现更多问题 | 重新分诊;达到门槛才添加 FB 任务 |
| "Bug"实为功能请求 | 重新分类为 spec-level;达到 OpenSpec 门槛时先更新规范 |
| 存在活跃变更但反馈不相关 | 不强行追加;按direct-fix、openspec-new或no-change处理 |
| 轻量文档、技能或治理措辞改进 | 通常走direct-fix;若会改变 OpenSpec 工作流或团队治理门禁,必须同步规则文件并重新判断记录门槛 |
| 测试不可行(时序、基础设施) | 通过完整测试套件验证,在摘要中说明原因 |
| 多轮反馈 | 每轮先分诊;同一目标变更中的任务在单个 Feedback 章节中顺序编号 |
护栏规则
- 先判断 OpenSpec 门槛 — 不因存在活跃变更就自动追加,也不为低价值反馈新建变更
- 达到门槛才记录 —
openspec-existing和openspec-new路径需要先记录再修复,direct-fix路径需要先说明分诊和根因再修复
- 规范级别问题先更新规范 — OpenSpec 路径中先更新增量规范
- 减少不必要确认 — AI 自主决定记录门槛;仅在归属或方案取舍确实不清时询问用户
- 最小化修复 — 不进行问题范围之外的重构
- 用户可见的修复需要测试 — 除非技术上不可行,否则无例外
- 测试未通过不得标记完成 — 仅在测试通过后标记
[x]
- 必须进行影响分析 — 每个修复都需要识别回归测试
- 回归失败阻塞完成 — 必须在标记完成前解决
- 实时更新 tasks.md — 仅 OpenSpec 路径在验证后立即标记完成
- 匹配文件语言 — 使用目标文件中已有内容的相同语言