这三个功能与Go的标准包有什么不同:

Wrapf返回一个错误,在调用Wrapf的点和格式说明符处用堆栈跟踪来注释err.如果err为nil,Wrapf返回nil.

Errorf根据格式说明符进行格式化,并将字符串作为满足Error的值返回.Errorf还记录调用时的堆栈跟踪.

Errorf根据格式说明符格式化,并将字符串作为满足错误的值返回.

如果格式说明符包含带有错误操作数的%w谓词,则返回的错误将实现一个返回操作数的展开方法.包含多个%w谓词或为其提供未实现错误接口的操作数是无效的.%w动词是%v的同义词.

什么时候应该用一种而不是其他的?

推荐答案

首先,更正一下:

github.com/pkg/errors是标准库的not部分!标准errors包的API要小得多.

这就是说,github.com/pkg/errors非常受欢迎,并由一些著名的地鼠维护.然而,到了Go 1.13's extended error support年,它基本上(尽管不是完全)被淘汰了.

理解这三个函数之间的区别需要上一点历史课.

在Go 1.13之前,没有官方认可的"包装"错误的方法.github.com/pkg/errorsWrapWrapf方法填补了这一空白.这允许使用附加上下文(包括堆栈跟踪)包装错误,同时以原始形式保留原始错误.

在Go 1.13开发时,github.com/pkg/errors被用来影响新的API,但最终版本略有不同.他们决定用一个新的%w动词来扩展fmt.Errorf方法,而不是WrapWrapf方法,这将为您执行错误包装.

这意味着以下代码位大致*等价:

    import "github.com/pkg/errors"

    /* snip */

    return errors.Wrapf(err, "bad things")
    // +build go1.13

    import "fmt"

    /* snip */
    return fmt.Errorf("bad things: %w", err)

当Go 1.13问世时,fmt.Errorf增加了%w个动词,github.com/pkg/errors也跟着增加了同样的支持,所以现在Wrapf实际上已经过时了.

因此,这就把我们带到了今天的建议:

  1. 如果希望在错误中进行堆栈跟踪,请使用github.com/pkg/errors.Errorf来包装错误.
  2. 如果您不关心堆栈跟踪,可以使用标准库中的fmt.Errorf.
  3. 永远不要再用errors.Wrapf了.这是为了向后兼容.

*标准库的error包仍未包含堆栈痕迹,因此github.com/pkg/errors仍受欢迎

Go相关问答推荐

Go PQ驱动程序无法使用默认架构进行查询

GORM Find方法中缺少字段

使用ciph.AEAD.Seal()查看内存使用情况

理解Golang中的IOTA和常量

如何使用 html/template 在 golang 中运行一个范围内的范围

Go - 永远停止带有上下文的循环

使用goroutines在Golang中验证 struct

使用golang sqlc中的引用参数

Golang校验器包:重命名字段错误处理

如何将已知类型转换为指向switch 中类型参数的指针?

git ls-remote 成功而 go get 失败

当填充通道的函数调用未嵌入 goroutine 时,为什么我会遇到死锁?

有没有办法将 yaml node 添加到 golang 中现有的 yaml 文档中?

如何将多个切片打印为一个切片?

函数超时和 goroutine 泄漏

如何使用 Status 字段创建 Kubernetes 对象?

为什么时间很短.睡眠时间比基准测试中要求的(约 300 ns)长?

如何在没有内存分配的情况下压缩和发布文件

每 N 秒运行一次函数,上下文超时

Golang - 使用正则表达式提取链接