废弃代码指未被调用的函数、变量等,而非未被import;go mod tidy不检测包内废弃符号,需用staticcheck精准识别未调用私有函数、未读取变量等,并配合replace+go:build标签在编译期拦截非法引用。

废弃代码不是“没被 import”,而是“没被调用”
很多人误以为 go mod tidy 能清理废弃代码,其实它只管模块依赖列表是否完整,完全不管包内有没有未使用的 func、var、type 或私有字段。比如你删了 user/internal/service/legacy.go,只要没被任何 import 引用,go mod tidy 就毫无反应——但残留的未调用函数仍可能被旧测试或灰度逻辑间接触发,导致 panic 或静默逻辑错。
用 staticcheck 扫描未使用符号(最准)
staticcheck 是目前 Go 生态中识别废弃符号最可靠的工具,能精准定位:未调用的私有函数、未读取的局部变量、未实现的接口方法、未导出但被注释掉的字段等。
- 安装:
go install honnef.co/go/tools/cmd/staticcheck@latest - 扫描整个
internal/目录:staticcheck ./internal/ - 忽略测试文件(避免误报):
staticcheck -ignore="SA4006:.*_test.go" ./internal/ - CI 中强制失败(防遗漏):
staticcheck -fail ./internal/
注意:不要依赖 go vet -unused,它默认不启用该检查,且误报率高;staticcheck 的 SA4006(未读取变量)、SA4010(未调用函数)等规则更稳定。
在 GoLand 里集成 staticcheck 为实时检查
GoLand 本身不内置废弃代码检测,但可通过 External Tools + Inspection 配合 staticcheck 实现编辑时提示。
GoLand 2026.1.1 是 2026.1 发布后的首个维护修正版本,适合已经开始体验 2026.1 新功能并希望同步补丁的开发者。它更适合用于入门项目、现有项目迁移测试和 IDE 行为验证。
- 在
Settings → Tools → External Tools中添加新工具:
• Program:staticcheck
• Arguments:-f=csv $ProjectFileDir$
• Working directory:$ProjectFileDir$ - 启用后,右键项目 →
External Tools → staticcheck即可运行;结果会以 CSV 格式输出,GoLand 可解析并高亮问题行 - 更推荐方式:用
go list -f '{{.ImportPath}}' ./... | xargs -I{} staticcheck {}命令封装为 Run Configuration,绑定快捷键(如Ctrl+Shift+X)
别指望 “Find Usages” 查废弃代码——它只找已知符号的引用,对从未被调用过的函数根本无从发现。
编译期拦截非法 import(防新代码误用旧包)
重构中常需保留旧包供灰度流量走,但必须阻止新代码再 import 它。仅靠文档或约定不可靠,得让 go build 直接报错。
- 在根
go.mod中加:replace github.com/old/project/user => ./internal/obsolete/user - 然后删掉
./internal/obsolete/user目录——下次go build遇到该 import 就会报cannot find module providing package - 配合
//go:build !v2标签控制文件存活期,比在代码里写if false { ... }更安全,编译器真会剔除
真正难的不是找到废弃代码,而是确认它“确实没人用”——比如某个 handler 被 nginx 直接 upstream 到,但代码里没显式调用,这种就得结合流量日志和 go tool trace 验证,不能只信 staticcheck 输出。










