Go語言中實現(xiàn)打印堆棧的errors包的用法詳解
Go語言打印堆棧errors包
因為Go語言提供的錯誤太簡單了,以至于簡單的我們無法更好的處理問題,甚至不能為我們處理錯誤,提供更有用的信息,所以誕生了很多對錯誤處理的庫,github.com/pkg/errors是比較簡潔的一樣,并且功能非常強(qiáng)大,受到了大量開發(fā)者的歡迎,使用者很多。
1、安裝
go get github.com/pkg/errors
2、使用
跟蹤堆棧信息的函數(shù)使用:
// 新生成一個錯誤, 帶堆棧信息 func New(message string) error //只附加新的信息 func WithMessage(err error, message string) error //只附加調(diào)用堆棧信息 func WithStack(err error) error //同時附加堆棧和信息 func Wrap(err error, message string) error
打印出堆棧信息:
// 功能一樣,輸出錯誤信息,不包含堆棧
%s,%v
// 輸出的錯誤信息帶引號,不包含堆棧
%q
// 輸出錯誤信息和堆棧
%+v
//如:
fmt.Println(fmt.Sprintf("%s", err))
fmt.Println(fmt.Sprintf("%q", err))
fmt.Println(fmt.Sprintf("%+v", err))2.1 New()函數(shù)
它的使用非常簡單,如果我們要新生成一個錯誤,可以使用 New 函數(shù)生成錯誤,自帶調(diào)用堆棧信息。
// 例子
package main
import (
"fmt"
"github.com/pkg/errors"
)
func main() {
result, err := Divide(10, 0)
if err != nil {
fmt.Println(fmt.Sprintf("error1: %v", err))
fmt.Println(fmt.Sprintf("error2: %s", err))
fmt.Println(fmt.Sprintf("error3: %q", err))
fmt.Println(fmt.Sprintf("error4: %+v", err))
} else {
fmt.Println("result:", result)
}
}
func Divide(a, b int) (int, error) {
if b == 0 {
return 0, errors.New("division can not 0")
} else {
return a / b, nil
}
}程序輸出
error1: division can not 0
error2: division can not 0
error3: "division can not 0"
error4: division can not 0
main.Divide
C:/Users/admin/Desktop/gg/new/go-errors/001.go:23
main.main
C:/Users/admin/Desktop/gg/new/go-errors/001.go:10
runtime.main
D:/install/go1.18.4/src/runtime/proc.go:250
runtime.goexit
D:/install/go1.18.4/src/runtime/asm_amd64.s:1571
如果有一個現(xiàn)成的 error,我們需要對他進(jìn)行再次包裝處理,這時候有三個函數(shù)可以選擇。
//只附加新的信息 func WithMessage(err error, message string) error //只附加調(diào)用堆棧信息 func WithStack(err error) error //同時附加堆棧和信息 func Wrap(err error, message string) error
2.2 WithMessage()函數(shù)
// 例子
package main
import (
"fmt"
"github.com/pkg/errors"
)
func main() {
result, err := Divide(10, 0)
if err != nil {
fmt.Println(fmt.Sprintf("error1: %v", err))
fmt.Println(fmt.Sprintf("error2: %s", err))
fmt.Println(fmt.Sprintf("error3: %q", err))
fmt.Println(fmt.Sprintf("error4: %+v", err))
} else {
fmt.Println("result:", result)
}
}
func Divide(a, b int) (int, error) {
if b == 0 {
return 0, errors.WithMessage(errors.New("division can not 0"),"func Divide(a, b int) (int, error) {}")
} else {
return a / b, nil
}
}程序輸出
error1: func Divide(a, b int) (int, error) {}: division can not 0
error2: func Divide(a, b int) (int, error) {}: division can not 0
error3: func Divide(a, b int) (int, error) {}: division can not 0
error4: division can not 0
main.Divide
C:/Users/admin/Desktop/gg/new/go-errors/002.go:23
main.main
C:/Users/admin/Desktop/gg/new/go-errors/002.go:10
runtime.main
D:/install/go1.18.4/src/runtime/proc.go:250
runtime.goexit
D:/install/go1.18.4/src/runtime/asm_amd64.s:1571
func Divide(a, b int) (int, error) {}
2.3 WithStack()
// 例子
package main
import (
"fmt"
"github.com/pkg/errors"
)
func main() {
result, err := Divide(10, 0)
if err != nil {
fmt.Println(fmt.Sprintf("error1: %v", err))
fmt.Println(fmt.Sprintf("error2: %s", err))
fmt.Println(fmt.Sprintf("error3: %q", err))
fmt.Println(fmt.Sprintf("error4: %+v", err))
} else {
fmt.Println("result:", result)
}
}
func Divide(a, b int) (int, error) {
if b == 0 {
return 0, errors.WithStack(errors.New("division can not 0"))
} else {
return a / b, nil
}
}程序輸出
error1: division can not 0
error2: division can not 0
error3: "division can not 0"
error4: division can not 0
main.Divide
C:/Users/admin/Desktop/gg/new/go-errors/003.go:23
main.main
C:/Users/admin/Desktop/gg/new/go-errors/003.go:10
runtime.main
D:/install/go1.18.4/src/runtime/proc.go:250
runtime.goexit
D:/install/go1.18.4/src/runtime/asm_amd64.s:1571
main.Divide
C:/Users/admin/Desktop/gg/new/go-errors/003.go:23
main.main
C:/Users/admin/Desktop/gg/new/go-errors/003.go:10
runtime.main
D:/install/go1.18.4/src/runtime/proc.go:250
runtime.goexit
D:/install/go1.18.4/src/runtime/asm_amd64.s:1571
2.4 Wrap()函數(shù)
// 例子
package main
import (
"fmt"
"github.com/pkg/errors"
)
func main() {
result, err := Divide(10, 0)
if err != nil {
fmt.Println(fmt.Sprintf("error1: %v", err))
fmt.Println(fmt.Sprintf("error2: %s", err))
fmt.Println(fmt.Sprintf("error3: %q", err))
fmt.Println(fmt.Sprintf("error4: %+v", err))
} else {
fmt.Println("result:", result)
}
}
func Divide(a, b int) (int, error) {
if b == 0 {
return 0, errors.Wrap(errors.New("division can not 0"),"func Divide(a, b int) (int, error){}")
} else {
return a / b, nil
}
}程序輸出
error1: func Divide(a, b int) (int, error){}: division can not 0
error2: func Divide(a, b int) (int, error){}: division can not 0
error3: "func Divide(a, b int) (int, error){}: division can not 0"
error4: division can not 0
main.Divide
C:/Users/admin/Desktop/gg/new/go-errors/004.go:23
main.main
C:/Users/admin/Desktop/gg/new/go-errors/004.go:10
runtime.main
D:/install/go1.18.4/src/runtime/proc.go:250
runtime.goexit
D:/install/go1.18.4/src/runtime/asm_amd64.s:1571
func Divide(a, b int) (int, error){}
main.Divide
C:/Users/admin/Desktop/gg/new/go-errors/004.go:23
main.main
C:/Users/admin/Desktop/gg/new/go-errors/004.go:10
runtime.main
D:/install/go1.18.4/src/runtime/proc.go:250
runtime.goexit
D:/install/go1.18.4/src/runtime/asm_amd64.s:1571
這里只是簡單介紹相關(guān)函數(shù)的使用,我們可以自己對這些函數(shù)進(jìn)行封裝,然后在相應(yīng)的地方進(jìn)行調(diào)用。
3、總結(jié)
通過使用這個 github.com/pkg/errors 錯誤庫,我們可以收集更多的信息,可以讓我們更容易的定位問題。
我們收集的這些信息不止可以輸出到控制臺,也可以當(dāng)做日志,使用輸出到相應(yīng)的 Log 日志里,便于分析問題。
以上就是Go語言中實現(xiàn)打印堆棧的errors包的用法詳解的詳細(xì)內(nèi)容,更多關(guān)于Go語言打印堆棧errors包的資料請關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
Golang使用Channel組建高并發(fā)HTTP服務(wù)器
Golang 作為一門高效的語言,在網(wǎng)絡(luò)編程方面表現(xiàn)也非常出色,這篇文章主要介紹了如何使用 Golang 和 Channel 組建高并發(fā) HTTP 服務(wù)器,感興趣的可以了解一下2023-06-06
成功安裝vscode中g(shù)o的相關(guān)插件(詳細(xì)教程)
這篇文章主要介紹了成功安裝vscode中g(shù)o的相關(guān)插件的詳細(xì)教程,本文給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友可以參考下2020-05-05
Prometheus Go client library使用方式詳解
這篇文章主要為大家介紹了Prometheus Go client library使用方式詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-11-11
go程序測試CPU占用率統(tǒng)計ps?vs?top兩種不同方式對比
這篇文章主要為大家介紹了go程序測試CPU占用率統(tǒng)計ps?vs?top兩種不同方式對比,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-05-05
golang 實現(xiàn)時間戳和時間的轉(zhuǎn)化
這篇文章主要介紹了golang 實現(xiàn)時間戳和時間的轉(zhuǎn)化操作,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧2021-05-05

