Skip to content

Instantly share code, notes, and snippets.

@mrsndmn
Created July 22, 2020 09:25
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save mrsndmn/cf456af952381a15394915cef2bdb274 to your computer and use it in GitHub Desktop.
Save mrsndmn/cf456af952381a15394915cef2bdb274 to your computer and use it in GitHub Desktop.
errors pkg/errors merry
package main
import (
errors "errors"
"fmt"
"testing"
pkgerrors "github.com/pkg/errors"
"github.com/ansel1/merry"
)
var DEPTH = 10
/*
22.07.20
var DEPTH = 10
error 3553 ns/op
pkg/error 15971 ns/op
merry 4672 ns/op
===========
var DEPTH = 50
error 22958 ns/op
pkg/error 110584 ns/op
merry 26800 ns/op
===========
ЗЫ больше, чем 50 глубину не стоит брать, в merry это максимальная глубина стек трейса, которая захватывается
# Почему так происходит?
Каждый pkgerrors.Wrap захватывает стек-трейс
В случае, если ошибку не получается быстро орбаботать и она прокидывается
на много уровней вверх, на каждом уровне будет захватываться почти один и тот же
стек-трейс (каждый последующий будет просто на один уровень меньше, чем предыдущий)
https://github.com/pkg/errors/blob/614d223910a179a466c1767a985424175c39b465/errors.go#L184
merry.Wrap захватывает трейс только если ошибка не содержала стек-трейс раньше
https://github.com/ansel1/merry/blob/8b7f40ead698ed36b27275d583da9549b4b98b40/errors.go#L117
* errors -- для гуру гошки, которые без стек трейса могут разобраться, как именно возникла ошибка
* pkg/error -- когда нужно больше стек трейсов
* merry -- баланс
*/
var ErrErrorsDeep = errors.New("deep err")
var ErrPkgErrorsDeep = pkgerrors.New("deep err")
var ErrMerryDeep = merry.New("deep err")
func main() {
var errHolderErrors, errHolderPkgErrors, errHolderMerry error
benchErrorsStacktrace := testing.Benchmark(func(b *testing.B) {
var err error
for i := 0; i < b.N; i++ {
err = deepErrorFunc(0)
}
errHolderErrors = err
})
benchPkgErrorsStacktrace := testing.Benchmark(func(b *testing.B) {
var err error
for i := 0; i < b.N; i++ {
err = deepPkgErrorFunc(0)
}
errHolderPkgErrors = err
})
benchMerryErrorsStacktrace := testing.Benchmark(func(b *testing.B) {
var err error
for i := 0; i < b.N; i++ {
err = deepMerryErrorFunc(0)
}
errHolderMerry = err
})
// можно раскомметить, посмотреть, как выглядят трейсы для каждого варианта
// fmt.Printf("error: %+v\n", errHolderErrors)
// fmt.Printf("pkg/error: %+v\n", errHolderPkgErrors)
// fmt.Printf("merry: %+v\n", errHolderMerry)
fmt.Printf("error %d ns/op\n", benchErrorsStacktrace.NsPerOp())
fmt.Printf("pkg/error %d ns/op\n", benchPkgErrorsStacktrace.NsPerOp())
fmt.Printf("merry %d ns/op\n", benchMerryErrorsStacktrace.NsPerOp())
}
func deepErrorFunc(depth int) error {
if DEPTH > depth {
err := deepErrorFunc(depth + 1)
return fmt.Errorf("deep err: %w", err)
}
return ErrErrorsDeep
}
func deepPkgErrorFunc(depth int) error {
if DEPTH > depth {
err := deepPkgErrorFunc(depth + 1)
return pkgerrors.Wrap(err, "deep err")
}
return ErrPkgErrorsDeep
}
func deepMerryErrorFunc(depth int) error {
if DEPTH > depth {
err := deepMerryErrorFunc(depth + 1)
return merry.Wrap(err).Prepend("deep err")
}
return ErrMerryDeep
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment