mcpField
G
go-nolint-audit

go-nolint-audit

github.com/rshade测试与质量388 次安装2 周前更新
代码仓库

关于 go-nolint-audit

Go Nolint Audit 是用于审查 Go 代码库中 `//nolint` 指令的技能,供维护者检查过期或理由不足的抑制项。它结合 golangci-lint 验证和多方辩论,输出处理建议与具体修改。

主要功能

  1. 01扫描 Go 文件中的 nolint
  2. 02验证指定规则是否仍触发
  3. 03评估修复可行性与理由质量
  4. 04辩论并给出处理结论
  5. 05输出具体差异和汇总

适用场景

  1. 01清理已不再需要的 lint 抑制
  2. 02检查缺少充分理由的 nolint
  3. 03为争议抑制项生成修订建议

安装

复制下面的命令,在终端中运行。

$npx skills add https://github.com/rshade/agent-skills --skill go-nolint-audit

安装后在 Claude Code 中输入/go-nolint-audit确认已加载。

包含的文件

除 SKILL.md 外,安装时一起下载的参考资料和脚本。

evals/
evals.json
evals/fixture/
go.mod
main.go
references/
go-nolint-patterns.md

详细介绍

Go Nolint 审计

审计 Go 代码库中的 //nolint: 指令。查找过时的抑制(代码已变更,不再触发 lint 规则)或理由牵强的抑制(底层代码本可以修复,而不是被抑制)。通过对抗式辩论逐一质疑每条理由,而不是直接相信注释。

前置条件检查

go version 2>/dev/null && golangci-lint --version 2>/dev/null

如果未安装 go,则停止并报告。如果缺少 golangci-lint:

除非两种工具都可用,否则不要继续。

查找 nolint 指令

grep -rn '//nolint' --include='*.go' . | grep -v vendor/

匹配所有形式://nolint(裸指令)、//nolint:rule、//nolint:rule1,rule2。对于每条指令,记录:

  • 文件和行号
  • 被抑制的规则,或未指定规则时记为“裸指令”
  • 理由注释(如果存在,则记录 //nolint:rule // 后的文本)
  • 周边代码上下文(约 5 行)

裸 //nolint(未指定规则)会抑制所有规则——在第 2 阶段自动标记。如果未找到任何指令,则报告代码库干净并停止。

第 1 阶段:机械验证

对于每条指定了规则的指令,测试该抑制是否仍有必要。将 nolintlint 与目标规则一起启用:

# v2 syntax (preferred):
golangci-lint run --enable-only=<rule>,nolintlint \
  --allow-parallel-runners <file>

# v1 syntax (if v2 unavailable):
golangci-lint run --disable-all --enable=<rule>,nolintlint \
  --allow-parallel-runners <file>

如果 nolintlint 报告该指令未被使用,则它已过时。这种方法无需修改源文件。对于多规则指令(//nolint:rule1,rule2),分别测试每条规则。最多运行 3 条并行 shell 命令。务必使用 --allow-parallel-runners。

如果 golangci-lint 因目标规则之外的原因失败(构建错误、缺少依赖),则跳过该指令,并报告为“无法验证”。

对每条指令进行分类:

  • 过时 — 规则不再触发。可以安全移除。
  • 仍有效 — 规则仍会触发。进入第 2 阶段。

立即报告过时指令。如果所有指令都已过时,则跳过第 2 阶段。裸 //nolint 指令跳过第 1 阶段——无法针对特定规则进行验证。

第 2 阶段:对抗式辩论

从两个维度(1-5 分)为所有已发现的指令评分(不只是第 1 阶段抽样的指令)。对于大型代码库(50 条以上指令),第 1 阶段按不同规则抽取 5-10 条进行测试,但此处要为完整列表评分,以找出最有问题的指令:

  • 可修复性 — 修复代码而不是抑制规则有多容易?
    • 5 = 很简单(提取函数、重命名、添加常量)
    • 3 = 中等(重构逻辑、拆分函数)
    • 1 = 需要架构变更
  • 理由质量 — 注释有多充分?
    • 5 = 没有注释,或理由含糊(“复杂度不可避免”“有必要”)
    • 3 = 解释了情况,但没说明为什么修复反而更糟
    • 1 = 理由具体且令人信服

得分 = 可修复性 x 理由质量。评分指南请参阅 references/go-nolint-patterns.md。

按得分对排名前 3 的指令进行辩论:

  • 红方(移除):主张移除 nolint 并修复代码。必须提出具体 diff。对理由提出质疑。
  • 蓝方(保留):主张 nolint 是合理的。必须补充现有注释之外的理由,并指出所提修复方案的风险。
  • 白方(裁决):依据证据进行评估,并作出决定:移除、保留或重写理由。
辩论规则
  • 红方和蓝方必须引用具体代码,不得泛泛而谈
  • 红方必须提供具体 diff,不能只说“可以更简单”
  • 蓝方不能只是重复现有理由
  • 白方的决定为最终决定

输出格式

第 1 阶段
Stale (safe to remove):
  file.go:42  //nolint:errcheck — rule no longer triggers
  file.go:87  //nolint:mnd — rule no longer triggers

Unable to verify:
  file.go:99  //nolint:gosec — golangci-lint build error
第 2 阶段

对于每条参与辩论的指令:

#N: file.go:line — //nolint:rule

当前代码(含 nolint): [周边代码 5-10 行]

理由:“原始注释” 移除后的 lint 警告:[golangci-lint 的确切输出]

红方(移除):[论点 + 具体 diff] 蓝方(保留):[包含具体理由的论点] 白方(裁决):移除 | 保留 | 重写理由 [理由]

[如果选择移除:重复 diff,方便应用] [如果选择重写:提供完整的替换行及改进后的理由]

摘要
#文件:行规则判定工作量
1locationruleverdicteffort
2locationruleverdicteffort
3locationruleverdicteffort

过时:N(立即移除) | 无法验证:N

评论

支持 Markdown