nilaway

nilaway

编译时捕获Go代码nil指针异常

NilAway是一款静态分析工具,专门用于在编译时检测Go代码中的nil指针异常。它无需额外注释,能够跨包分析nil流,并提供详细错误报告。NilAway以低开销和高精度著称,适合大型Go项目使用。该工具支持独立运行,也可与golangci-lint和Bazel/nogo集成,为开发者提供灵活的使用方式。

NilAwayGo语言静态分析空指针检测编译时检查Github开源项目

NilAway

GoDoc 构建状态 覆盖率状态

[!警告]
NilAway 目前正在积极开发中:可能会出现误报和破坏性更改。 我们非常感谢任何反馈和贡献!

NilAway 是一个静态分析工具,旨在通过在编译时而非运行时捕获空指针异常,帮助开发人员避免在生产环境中出现空指针崩溃。NilAway 类似于标准的nilness 分析器,但它采用了更复杂和强大的静态分析技术来跟踪包内以及跨包的空值流,并报告错误,为用户提供空值流以便更容易调试。

NilAway 具有三个关键特性,使其脱颖而出:

  • 它是全自动的:NilAway 配备了推理引擎,除了标准的 Go 代码外,不需要开发人员提供任何额外信息(如注释)。

  • 速度快:我们设计 NilAway 时考虑了速度和可扩展性,使其适用于大型代码库。在我们的测量中,启用 NilAway 时观察到的构建时间开销不到 5%。我们还在不断应用优化以进一步减少其占用。

  • 它是实用的:它不会阻止代码中所有可能的空指针异常,但它能捕获我们在生产中观察到的大多数潜在空指针异常,使 NilAway 能够在实用性和构建时间开销之间保持良好平衡。

:star2: 有关更详细的技术讨论,请查看我们的 Wiki工程博客 和论文(进行中)。

运行 NilAway

NilAway 使用标准的 go/analysis 实现,使其易于与现有的分析器驱动程序集成(即 golangci-lintnogo作为独立检查器运行)。

[!重要]
默认情况下,NilAway 分析所有 Go 代码,包括标准库和依赖项。这有助于 NilAway 更好地理解依赖项的代码并减少误报。然而,对于有大量依赖项的大型 Go 项目,这也会带来显著的性能成本(对于支持模块化的驱动程序来说只需一次),并增加依赖项中不可操作错误的数量。

我们强烈建议使用 include-pkgs 标志将分析范围缩小到仅限于您的项目代码。这指示 NilAway 跳过分析依赖项(例如第三方库),让您专注于 NilAway 在您的一方代码中报告的潜在空指针异常!

独立检查器

[!重要]
由于 NilAway 进行的分析较为复杂,NilAway 通过 go/analysis 框架的 Fact 机制 缓存其对特定包的发现。因此,强烈建议使用支持模块化分析的驱动程序(即 bazel/nogo 或 golangci-lint,但不是独立检查器,因为它将所有事实存储在内存中)以获得更好的大型项目性能。提供独立检查器更多是为了评估目的,因为它易于上手。

通过运行以下命令从源代码安装二进制文件:

go install go.uber.org/nilaway/cmd/nilaway@latest

然后,运行 linter:

nilaway -include-pkgs="<YOUR_PKG_PREFIX>,<YOUR_PKG_PREFIX_2>" ./...

golangci-lint (>= v1.57.0)

NilAway 在其当前形式下可能会报告误报。这不幸阻碍了它立即合并到 golangci-lint 并作为一个 linter 提供(参见 PR#4045)。因此,您需要将 NilAway 构建为 golangci-lint 的插件,以作为私有 linter 执行。golangci-lint 中有两个插件系统,使用 模块插件系统(自 v1.57.0 版本引入)要容易得多,这是在 golangci-lint 中运行 NilAway 的唯一支持方法。

(1) 如果您还没有在仓库根目录创建 .custom-gcl.yml 文件,请创建它并添加以下内容:

# 这必须是 >= v1.57.0 以支持模块插件系统。 version: v1.57.0 plugins: - module: "go.uber.org/nilaway" import: "go.uber.org/nilaway/cmd/gclplugin" version: latest # 或固定版本以实现可重现构建。

(2) 将 NilAway 添加到 linter 配置文件 .golangci.yaml 中:

linters-settings: custom: nilaway: type: "module" description: 检测 Go 代码中潜在空指针异常的静态分析工具。 settings: # 设置必须是"字符串到字符串的映射"以模拟命令行标志:键是标志名,值是特定标志的值。 include-pkgs: "<YOUR_PACKAGE_PREFIXES>" # NilAway 可以像其他 golangci-lint 分析器一样在配置文件的其他部分中被称为 `nilaway`。

(3) 构建包含 NilAway 的自定义 golangci-lint 二进制文件:

# 注意,用于引导自定义二进制文件的 `golangci-lint` 版本也必须 >= v1.57.0。 $ golangci-lint custom

默认情况下,自定义二进制文件将在 . 目录下构建,名称为 custom-gcl,这可以在 .custom-gcl.yml 文件中进一步自定义(参见 模块插件系统 的说明)。

[!提示]
缓存自定义二进制文件以避免重新构建,节省资源。如果您使用的是 NilAway 的固定版本,可以使用 .custom-gcl.yml 文件的哈希值作为缓存键。如果您使用 latest 作为 NilAway 版本,可以将构建日期附加到缓存键上,以强制在特定时间段后使缓存过期。

(4) 运行自定义二进制文件而不是 golangci-lint

# 参数与 `golangci-lint` 相同。 $ ./custom-gcl run ./...

Bazel/nogo

使用 bazel/nogo 运行需要稍多的努力。首先按照 rules_gogazellenogo 的说明设置您的 Go 项目,使其可以使用 bazel/nogo 构建,不配置或使用默认的 linter 集。然后,

(1) 在您的 tools.go 文件中添加 import _ "go.uber.org/nilaway"(或您用于配置工具依赖的其他文件,参见 Go 模块文档中的 如何跟踪模块的工具依赖?),以避免 go mod tidy 删除 NilAway 作为工具依赖。 (2) 运行以下命令将NilAway作为工具依赖添加到您的项目中:

# 将NilAway作为依赖项获取,并在go.mod文件中获取其传递依赖项。 $ go get go.uber.org/nilaway@latest # 这不应该从go.mod文件中删除NilAway作为依赖项。 $ go mod tidy # 运行gazelle以从go.mod同步依赖项到WORKSPACE文件。 $ bazel run //:gazelle -- update-repos -from_file=go.mod

(3) 将NilAway添加到nogo配置中(通常在顶级BUILD.bazel文件中):

nogo( name = "my_nogo", visibility = ["//visibility:public"], # 必须具有公共可见性 deps = [ +++ "@org_uber_go_nilaway//:go_default_library", ], config = "config.json", )

(4) 运行bazel build以查看NilAway的工作情况(任何nogo错误都会停止bazel构建,您可以使用--keep_going标志要求bazel尽可能多地构建):

$ bazel build --keep_going //...

(5) 查看nogo文档了解如何向nogo驱动程序传递配置JSON,并查看我们的wiki页面了解如何向NilAway传递配置。

代码示例

让我们看几个例子,了解NilAway如何帮助防止空指针引起的panic。

// 示例1: var p *P if someCondition { p = &P{} } print(p.f) // nilness在这里不报错,但NilAway会报错。

在这个例子中,局部变量p只在someCondition为真时被初始化。在访问字段p.f时,如果someCondition为假,可能会发生panic。NilAway能够捕获这个潜在的空指针流,并报告以下错误,显示这个空指针流:

go.uber.org/example.go:12:9: error: 检测到潜在的空指针panic。观察到从源到解引用点的空指针流:
    - go.uber.org/example.go:12:9: 未赋值的变量`p`访问了字段`f`

如果我们用空指针检查(if p != nil)来保护这个解引用,错误就会消失。

NilAway还能捕获跨函数的空指针流。例如,考虑以下代码片段:

// 示例2: func foo() *int { return nil } func bar() { print(*foo()) // nilness在这里不报错,但NilAway会报错。 }

在这个例子中,函数foo返回一个空指针,在bar中直接解引用,导致每次调用bar时都会panic。NilAway能够捕获这个潜在的空指针流,并报告以下错误,描述了跨函数边界的空指针流:

go.uber.org/example.go:23:13: error: 检测到潜在的空指针panic。观察到从源到解引用点的空指针流:
    - go.uber.org/example.go:20:14: 字面量`nil`从`foo()`在位置0返回
    - go.uber.org/example.go:23:13: `foo()`的结果0被解引用

请注意,在上面的例子中,foo不一定要与bar位于同一个包中。NilAway能够跟踪跨包的空指针流。此外,NilAway还处理Go特有的语言结构,如接收器、接口、类型断言、类型switch等。

配置

我们通过go/analysis中的标准标志传递机制公开了一组标志。请查看wiki/Configuration以了解可用的标志以及如何使用不同的linter驱动程序传递它们。

支持

我们遵循与Go项目相同的版本支持政策:我们支持并测试Go的最后两个主要版本。

如果您有任何问题、错误报告和功能请求,请随时在GitHub上提出问题

贡献

我们非常欢迎您为NilAway做出贡献!请注意,一旦您创建拉取请求,您将被要求签署我们的Uber贡献者许可协议

许可证

本项目版权归2023 Uber Technologies, Inc.所有,并根据Apache 2.0许可证授权。

编辑推荐精选

Vora

Vora

免费创建高清无水印Sora视频

Vora是一个免费创建高清无水印Sora视频的AI工具

Refly.AI

Refly.AI

最适合小白的AI自动化工作流平台

无需编码,轻松生成可复用、可变现的AI自动化工作流

酷表ChatExcel

酷表ChatExcel

大模型驱动的Excel数据处理工具

基于大模型交互的表格处理系统,允许用户通过对话方式完成数据整理和可视化分析。系统采用机器学习算法解析用户指令,自动执行排序、公式计算和数据透视等操作,支持多种文件格式导入导出。数据处理响应速度保持在0.8秒以内,支持超过100万行数据的即时分析。

AI工具酷表ChatExcelAI智能客服AI营销产品使用教程
TRAE编程

TRAE编程

AI辅助编程,代码自动修复

Trae是一种自适应的集成开发环境(IDE),通过自动化和多元协作改变开发流程。利用Trae,团队能够更快速、精确地编写和部署代码,从而提高编程效率和项目交付速度。Trae具备上下文感知和代码自动完成功能,是提升开发效率的理想工具。

AI工具TraeAI IDE协作生产力转型热门
AIWritePaper论文写作

AIWritePaper论文写作

AI论文写作指导平台

AIWritePaper论文写作是一站式AI论文写作辅助工具,简化了选题、文献检索至论文撰写的整个过程。通过简单设定,平台可快速生成高质量论文大纲和全文,配合图表、参考文献等一应俱全,同时提供开题报告和答辩PPT等增值服务,保障数据安全,有效提升写作效率和论文质量。

AI辅助写作AI工具AI论文工具论文写作智能生成大纲数据安全AI助手热门
博思AIPPT

博思AIPPT

AI一键生成PPT,就用博思AIPPT!

博思AIPPT,新一代的AI生成PPT平台,支持智能生成PPT、AI美化PPT、文本&链接生成PPT、导入Word/PDF/Markdown文档生成PPT等,内置海量精美PPT模板,涵盖商务、教育、科技等不同风格,同时针对每个页面提供多种版式,一键自适应切换,完美适配各种办公场景。

AI办公办公工具AI工具博思AIPPTAI生成PPT智能排版海量精品模板AI创作热门
潮际好麦

潮际好麦

AI赋能电商视觉革命,一站式智能商拍平台

潮际好麦深耕服装行业,是国内AI试衣效果最好的软件。使用先进AIGC能力为电商卖家批量提供优质的、低成本的商拍图。合作品牌有Shein、Lazada、安踏、百丽等65个国内外头部品牌,以及国内10万+淘宝、天猫、京东等主流平台的品牌商家,为卖家节省将近85%的出图成本,提升约3倍出图效率,让品牌能够快速上架。

iTerms

iTerms

企业专属的AI法律顾问

iTerms是法大大集团旗下法律子品牌,基于最先进的大语言模型(LLM)、专业的法律知识库和强大的智能体架构,帮助企业扫清合规障碍,筑牢风控防线,成为您企业专属的AI法律顾问。

SimilarWeb流量提升

SimilarWeb流量提升

稳定高效的流量提升解决方案,助力品牌曝光

稳定高效的流量提升解决方案,助力品牌曝光

Sora2视频免费生成

Sora2视频免费生成

最新版Sora2模型免费使用,一键生成无水印视频

最新版Sora2模型免费使用,一键生成无水印视频

下拉加载更多