forked from TrueCloudLab/rclone
Switch to using the dep tool and update all the dependencies
This commit is contained in:
parent
5135ff73cb
commit
98c2d2c41b
5321 changed files with 4483201 additions and 5922 deletions
9
vendor/github.com/pkg/errors/.travis.yml
generated
vendored
9
vendor/github.com/pkg/errors/.travis.yml
generated
vendored
|
@ -1,10 +1,11 @@
|
|||
language: go
|
||||
go_import_path: github.com/pkg/errors
|
||||
go:
|
||||
- 1.4.3
|
||||
- 1.5.4
|
||||
- 1.6.3
|
||||
- 1.7.3
|
||||
- 1.4.x
|
||||
- 1.5.x
|
||||
- 1.6.x
|
||||
- 1.7.x
|
||||
- 1.8.x
|
||||
- tip
|
||||
|
||||
script:
|
||||
|
|
63
vendor/github.com/pkg/errors/bench_test.go
generated
vendored
Normal file
63
vendor/github.com/pkg/errors/bench_test.go
generated
vendored
Normal file
|
@ -0,0 +1,63 @@
|
|||
// +build go1.7
|
||||
|
||||
package errors
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"testing"
|
||||
|
||||
stderrors "errors"
|
||||
)
|
||||
|
||||
func noErrors(at, depth int) error {
|
||||
if at >= depth {
|
||||
return stderrors.New("no error")
|
||||
}
|
||||
return noErrors(at+1, depth)
|
||||
}
|
||||
|
||||
func yesErrors(at, depth int) error {
|
||||
if at >= depth {
|
||||
return New("ye error")
|
||||
}
|
||||
return yesErrors(at+1, depth)
|
||||
}
|
||||
|
||||
// GlobalE is an exported global to store the result of benchmark results,
|
||||
// preventing the compiler from optimising the benchmark functions away.
|
||||
var GlobalE error
|
||||
|
||||
func BenchmarkErrors(b *testing.B) {
|
||||
type run struct {
|
||||
stack int
|
||||
std bool
|
||||
}
|
||||
runs := []run{
|
||||
{10, false},
|
||||
{10, true},
|
||||
{100, false},
|
||||
{100, true},
|
||||
{1000, false},
|
||||
{1000, true},
|
||||
}
|
||||
for _, r := range runs {
|
||||
part := "pkg/errors"
|
||||
if r.std {
|
||||
part = "errors"
|
||||
}
|
||||
name := fmt.Sprintf("%s-stack-%d", part, r.stack)
|
||||
b.Run(name, func(b *testing.B) {
|
||||
var err error
|
||||
f := yesErrors
|
||||
if r.std {
|
||||
f = noErrors
|
||||
}
|
||||
b.ReportAllocs()
|
||||
for i := 0; i < b.N; i++ {
|
||||
err = f(0, r.stack)
|
||||
}
|
||||
b.StopTimer()
|
||||
GlobalE = err
|
||||
})
|
||||
}
|
||||
}
|
225
vendor/github.com/pkg/errors/errors_test.go
generated
vendored
Normal file
225
vendor/github.com/pkg/errors/errors_test.go
generated
vendored
Normal file
|
@ -0,0 +1,225 @@
|
|||
package errors
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"io"
|
||||
"reflect"
|
||||
"testing"
|
||||
)
|
||||
|
||||
func TestNew(t *testing.T) {
|
||||
tests := []struct {
|
||||
err string
|
||||
want error
|
||||
}{
|
||||
{"", fmt.Errorf("")},
|
||||
{"foo", fmt.Errorf("foo")},
|
||||
{"foo", New("foo")},
|
||||
{"string with format specifiers: %v", errors.New("string with format specifiers: %v")},
|
||||
}
|
||||
|
||||
for _, tt := range tests {
|
||||
got := New(tt.err)
|
||||
if got.Error() != tt.want.Error() {
|
||||
t.Errorf("New.Error(): got: %q, want %q", got, tt.want)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestWrapNil(t *testing.T) {
|
||||
got := Wrap(nil, "no error")
|
||||
if got != nil {
|
||||
t.Errorf("Wrap(nil, \"no error\"): got %#v, expected nil", got)
|
||||
}
|
||||
}
|
||||
|
||||
func TestWrap(t *testing.T) {
|
||||
tests := []struct {
|
||||
err error
|
||||
message string
|
||||
want string
|
||||
}{
|
||||
{io.EOF, "read error", "read error: EOF"},
|
||||
{Wrap(io.EOF, "read error"), "client error", "client error: read error: EOF"},
|
||||
}
|
||||
|
||||
for _, tt := range tests {
|
||||
got := Wrap(tt.err, tt.message).Error()
|
||||
if got != tt.want {
|
||||
t.Errorf("Wrap(%v, %q): got: %v, want %v", tt.err, tt.message, got, tt.want)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
type nilError struct{}
|
||||
|
||||
func (nilError) Error() string { return "nil error" }
|
||||
|
||||
func TestCause(t *testing.T) {
|
||||
x := New("error")
|
||||
tests := []struct {
|
||||
err error
|
||||
want error
|
||||
}{{
|
||||
// nil error is nil
|
||||
err: nil,
|
||||
want: nil,
|
||||
}, {
|
||||
// explicit nil error is nil
|
||||
err: (error)(nil),
|
||||
want: nil,
|
||||
}, {
|
||||
// typed nil is nil
|
||||
err: (*nilError)(nil),
|
||||
want: (*nilError)(nil),
|
||||
}, {
|
||||
// uncaused error is unaffected
|
||||
err: io.EOF,
|
||||
want: io.EOF,
|
||||
}, {
|
||||
// caused error returns cause
|
||||
err: Wrap(io.EOF, "ignored"),
|
||||
want: io.EOF,
|
||||
}, {
|
||||
err: x, // return from errors.New
|
||||
want: x,
|
||||
}, {
|
||||
WithMessage(nil, "whoops"),
|
||||
nil,
|
||||
}, {
|
||||
WithMessage(io.EOF, "whoops"),
|
||||
io.EOF,
|
||||
}, {
|
||||
WithStack(nil),
|
||||
nil,
|
||||
}, {
|
||||
WithStack(io.EOF),
|
||||
io.EOF,
|
||||
}}
|
||||
|
||||
for i, tt := range tests {
|
||||
got := Cause(tt.err)
|
||||
if !reflect.DeepEqual(got, tt.want) {
|
||||
t.Errorf("test %d: got %#v, want %#v", i+1, got, tt.want)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestWrapfNil(t *testing.T) {
|
||||
got := Wrapf(nil, "no error")
|
||||
if got != nil {
|
||||
t.Errorf("Wrapf(nil, \"no error\"): got %#v, expected nil", got)
|
||||
}
|
||||
}
|
||||
|
||||
func TestWrapf(t *testing.T) {
|
||||
tests := []struct {
|
||||
err error
|
||||
message string
|
||||
want string
|
||||
}{
|
||||
{io.EOF, "read error", "read error: EOF"},
|
||||
{Wrapf(io.EOF, "read error without format specifiers"), "client error", "client error: read error without format specifiers: EOF"},
|
||||
{Wrapf(io.EOF, "read error with %d format specifier", 1), "client error", "client error: read error with 1 format specifier: EOF"},
|
||||
}
|
||||
|
||||
for _, tt := range tests {
|
||||
got := Wrapf(tt.err, tt.message).Error()
|
||||
if got != tt.want {
|
||||
t.Errorf("Wrapf(%v, %q): got: %v, want %v", tt.err, tt.message, got, tt.want)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestErrorf(t *testing.T) {
|
||||
tests := []struct {
|
||||
err error
|
||||
want string
|
||||
}{
|
||||
{Errorf("read error without format specifiers"), "read error without format specifiers"},
|
||||
{Errorf("read error with %d format specifier", 1), "read error with 1 format specifier"},
|
||||
}
|
||||
|
||||
for _, tt := range tests {
|
||||
got := tt.err.Error()
|
||||
if got != tt.want {
|
||||
t.Errorf("Errorf(%v): got: %q, want %q", tt.err, got, tt.want)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestWithStackNil(t *testing.T) {
|
||||
got := WithStack(nil)
|
||||
if got != nil {
|
||||
t.Errorf("WithStack(nil): got %#v, expected nil", got)
|
||||
}
|
||||
}
|
||||
|
||||
func TestWithStack(t *testing.T) {
|
||||
tests := []struct {
|
||||
err error
|
||||
want string
|
||||
}{
|
||||
{io.EOF, "EOF"},
|
||||
{WithStack(io.EOF), "EOF"},
|
||||
}
|
||||
|
||||
for _, tt := range tests {
|
||||
got := WithStack(tt.err).Error()
|
||||
if got != tt.want {
|
||||
t.Errorf("WithStack(%v): got: %v, want %v", tt.err, got, tt.want)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestWithMessageNil(t *testing.T) {
|
||||
got := WithMessage(nil, "no error")
|
||||
if got != nil {
|
||||
t.Errorf("WithMessage(nil, \"no error\"): got %#v, expected nil", got)
|
||||
}
|
||||
}
|
||||
|
||||
func TestWithMessage(t *testing.T) {
|
||||
tests := []struct {
|
||||
err error
|
||||
message string
|
||||
want string
|
||||
}{
|
||||
{io.EOF, "read error", "read error: EOF"},
|
||||
{WithMessage(io.EOF, "read error"), "client error", "client error: read error: EOF"},
|
||||
}
|
||||
|
||||
for _, tt := range tests {
|
||||
got := WithMessage(tt.err, tt.message).Error()
|
||||
if got != tt.want {
|
||||
t.Errorf("WithMessage(%v, %q): got: %q, want %q", tt.err, tt.message, got, tt.want)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// errors.New, etc values are not expected to be compared by value
|
||||
// but the change in errors#27 made them incomparable. Assert that
|
||||
// various kinds of errors have a functional equality operator, even
|
||||
// if the result of that equality is always false.
|
||||
func TestErrorEquality(t *testing.T) {
|
||||
vals := []error{
|
||||
nil,
|
||||
io.EOF,
|
||||
errors.New("EOF"),
|
||||
New("EOF"),
|
||||
Errorf("EOF"),
|
||||
Wrap(io.EOF, "EOF"),
|
||||
Wrapf(io.EOF, "EOF%d", 2),
|
||||
WithMessage(nil, "whoops"),
|
||||
WithMessage(io.EOF, "whoops"),
|
||||
WithStack(io.EOF),
|
||||
WithStack(nil),
|
||||
}
|
||||
|
||||
for i := range vals {
|
||||
for j := range vals {
|
||||
_ = vals[i] == vals[j] // mustn't panic
|
||||
}
|
||||
}
|
||||
}
|
205
vendor/github.com/pkg/errors/example_test.go
generated
vendored
Normal file
205
vendor/github.com/pkg/errors/example_test.go
generated
vendored
Normal file
|
@ -0,0 +1,205 @@
|
|||
package errors_test
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"github.com/pkg/errors"
|
||||
)
|
||||
|
||||
func ExampleNew() {
|
||||
err := errors.New("whoops")
|
||||
fmt.Println(err)
|
||||
|
||||
// Output: whoops
|
||||
}
|
||||
|
||||
func ExampleNew_printf() {
|
||||
err := errors.New("whoops")
|
||||
fmt.Printf("%+v", err)
|
||||
|
||||
// Example output:
|
||||
// whoops
|
||||
// github.com/pkg/errors_test.ExampleNew_printf
|
||||
// /home/dfc/src/github.com/pkg/errors/example_test.go:17
|
||||
// testing.runExample
|
||||
// /home/dfc/go/src/testing/example.go:114
|
||||
// testing.RunExamples
|
||||
// /home/dfc/go/src/testing/example.go:38
|
||||
// testing.(*M).Run
|
||||
// /home/dfc/go/src/testing/testing.go:744
|
||||
// main.main
|
||||
// /github.com/pkg/errors/_test/_testmain.go:106
|
||||
// runtime.main
|
||||
// /home/dfc/go/src/runtime/proc.go:183
|
||||
// runtime.goexit
|
||||
// /home/dfc/go/src/runtime/asm_amd64.s:2059
|
||||
}
|
||||
|
||||
func ExampleWithMessage() {
|
||||
cause := errors.New("whoops")
|
||||
err := errors.WithMessage(cause, "oh noes")
|
||||
fmt.Println(err)
|
||||
|
||||
// Output: oh noes: whoops
|
||||
}
|
||||
|
||||
func ExampleWithStack() {
|
||||
cause := errors.New("whoops")
|
||||
err := errors.WithStack(cause)
|
||||
fmt.Println(err)
|
||||
|
||||
// Output: whoops
|
||||
}
|
||||
|
||||
func ExampleWithStack_printf() {
|
||||
cause := errors.New("whoops")
|
||||
err := errors.WithStack(cause)
|
||||
fmt.Printf("%+v", err)
|
||||
|
||||
// Example Output:
|
||||
// whoops
|
||||
// github.com/pkg/errors_test.ExampleWithStack_printf
|
||||
// /home/fabstu/go/src/github.com/pkg/errors/example_test.go:55
|
||||
// testing.runExample
|
||||
// /usr/lib/go/src/testing/example.go:114
|
||||
// testing.RunExamples
|
||||
// /usr/lib/go/src/testing/example.go:38
|
||||
// testing.(*M).Run
|
||||
// /usr/lib/go/src/testing/testing.go:744
|
||||
// main.main
|
||||
// github.com/pkg/errors/_test/_testmain.go:106
|
||||
// runtime.main
|
||||
// /usr/lib/go/src/runtime/proc.go:183
|
||||
// runtime.goexit
|
||||
// /usr/lib/go/src/runtime/asm_amd64.s:2086
|
||||
// github.com/pkg/errors_test.ExampleWithStack_printf
|
||||
// /home/fabstu/go/src/github.com/pkg/errors/example_test.go:56
|
||||
// testing.runExample
|
||||
// /usr/lib/go/src/testing/example.go:114
|
||||
// testing.RunExamples
|
||||
// /usr/lib/go/src/testing/example.go:38
|
||||
// testing.(*M).Run
|
||||
// /usr/lib/go/src/testing/testing.go:744
|
||||
// main.main
|
||||
// github.com/pkg/errors/_test/_testmain.go:106
|
||||
// runtime.main
|
||||
// /usr/lib/go/src/runtime/proc.go:183
|
||||
// runtime.goexit
|
||||
// /usr/lib/go/src/runtime/asm_amd64.s:2086
|
||||
}
|
||||
|
||||
func ExampleWrap() {
|
||||
cause := errors.New("whoops")
|
||||
err := errors.Wrap(cause, "oh noes")
|
||||
fmt.Println(err)
|
||||
|
||||
// Output: oh noes: whoops
|
||||
}
|
||||
|
||||
func fn() error {
|
||||
e1 := errors.New("error")
|
||||
e2 := errors.Wrap(e1, "inner")
|
||||
e3 := errors.Wrap(e2, "middle")
|
||||
return errors.Wrap(e3, "outer")
|
||||
}
|
||||
|
||||
func ExampleCause() {
|
||||
err := fn()
|
||||
fmt.Println(err)
|
||||
fmt.Println(errors.Cause(err))
|
||||
|
||||
// Output: outer: middle: inner: error
|
||||
// error
|
||||
}
|
||||
|
||||
func ExampleWrap_extended() {
|
||||
err := fn()
|
||||
fmt.Printf("%+v\n", err)
|
||||
|
||||
// Example output:
|
||||
// error
|
||||
// github.com/pkg/errors_test.fn
|
||||
// /home/dfc/src/github.com/pkg/errors/example_test.go:47
|
||||
// github.com/pkg/errors_test.ExampleCause_printf
|
||||
// /home/dfc/src/github.com/pkg/errors/example_test.go:63
|
||||
// testing.runExample
|
||||
// /home/dfc/go/src/testing/example.go:114
|
||||
// testing.RunExamples
|
||||
// /home/dfc/go/src/testing/example.go:38
|
||||
// testing.(*M).Run
|
||||
// /home/dfc/go/src/testing/testing.go:744
|
||||
// main.main
|
||||
// /github.com/pkg/errors/_test/_testmain.go:104
|
||||
// runtime.main
|
||||
// /home/dfc/go/src/runtime/proc.go:183
|
||||
// runtime.goexit
|
||||
// /home/dfc/go/src/runtime/asm_amd64.s:2059
|
||||
// github.com/pkg/errors_test.fn
|
||||
// /home/dfc/src/github.com/pkg/errors/example_test.go:48: inner
|
||||
// github.com/pkg/errors_test.fn
|
||||
// /home/dfc/src/github.com/pkg/errors/example_test.go:49: middle
|
||||
// github.com/pkg/errors_test.fn
|
||||
// /home/dfc/src/github.com/pkg/errors/example_test.go:50: outer
|
||||
}
|
||||
|
||||
func ExampleWrapf() {
|
||||
cause := errors.New("whoops")
|
||||
err := errors.Wrapf(cause, "oh noes #%d", 2)
|
||||
fmt.Println(err)
|
||||
|
||||
// Output: oh noes #2: whoops
|
||||
}
|
||||
|
||||
func ExampleErrorf_extended() {
|
||||
err := errors.Errorf("whoops: %s", "foo")
|
||||
fmt.Printf("%+v", err)
|
||||
|
||||
// Example output:
|
||||
// whoops: foo
|
||||
// github.com/pkg/errors_test.ExampleErrorf
|
||||
// /home/dfc/src/github.com/pkg/errors/example_test.go:101
|
||||
// testing.runExample
|
||||
// /home/dfc/go/src/testing/example.go:114
|
||||
// testing.RunExamples
|
||||
// /home/dfc/go/src/testing/example.go:38
|
||||
// testing.(*M).Run
|
||||
// /home/dfc/go/src/testing/testing.go:744
|
||||
// main.main
|
||||
// /github.com/pkg/errors/_test/_testmain.go:102
|
||||
// runtime.main
|
||||
// /home/dfc/go/src/runtime/proc.go:183
|
||||
// runtime.goexit
|
||||
// /home/dfc/go/src/runtime/asm_amd64.s:2059
|
||||
}
|
||||
|
||||
func Example_stackTrace() {
|
||||
type stackTracer interface {
|
||||
StackTrace() errors.StackTrace
|
||||
}
|
||||
|
||||
err, ok := errors.Cause(fn()).(stackTracer)
|
||||
if !ok {
|
||||
panic("oops, err does not implement stackTracer")
|
||||
}
|
||||
|
||||
st := err.StackTrace()
|
||||
fmt.Printf("%+v", st[0:2]) // top two frames
|
||||
|
||||
// Example output:
|
||||
// github.com/pkg/errors_test.fn
|
||||
// /home/dfc/src/github.com/pkg/errors/example_test.go:47
|
||||
// github.com/pkg/errors_test.Example_stackTrace
|
||||
// /home/dfc/src/github.com/pkg/errors/example_test.go:127
|
||||
}
|
||||
|
||||
func ExampleCause_printf() {
|
||||
err := errors.Wrap(func() error {
|
||||
return func() error {
|
||||
return errors.Errorf("hello %s", fmt.Sprintf("world"))
|
||||
}()
|
||||
}(), "failed")
|
||||
|
||||
fmt.Printf("%v", err)
|
||||
|
||||
// Output: failed: hello world
|
||||
}
|
535
vendor/github.com/pkg/errors/format_test.go
generated
vendored
Normal file
535
vendor/github.com/pkg/errors/format_test.go
generated
vendored
Normal file
|
@ -0,0 +1,535 @@
|
|||
package errors
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"io"
|
||||
"regexp"
|
||||
"strings"
|
||||
"testing"
|
||||
)
|
||||
|
||||
func TestFormatNew(t *testing.T) {
|
||||
tests := []struct {
|
||||
error
|
||||
format string
|
||||
want string
|
||||
}{{
|
||||
New("error"),
|
||||
"%s",
|
||||
"error",
|
||||
}, {
|
||||
New("error"),
|
||||
"%v",
|
||||
"error",
|
||||
}, {
|
||||
New("error"),
|
||||
"%+v",
|
||||
"error\n" +
|
||||
"github.com/pkg/errors.TestFormatNew\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:26",
|
||||
}, {
|
||||
New("error"),
|
||||
"%q",
|
||||
`"error"`,
|
||||
}}
|
||||
|
||||
for i, tt := range tests {
|
||||
testFormatRegexp(t, i, tt.error, tt.format, tt.want)
|
||||
}
|
||||
}
|
||||
|
||||
func TestFormatErrorf(t *testing.T) {
|
||||
tests := []struct {
|
||||
error
|
||||
format string
|
||||
want string
|
||||
}{{
|
||||
Errorf("%s", "error"),
|
||||
"%s",
|
||||
"error",
|
||||
}, {
|
||||
Errorf("%s", "error"),
|
||||
"%v",
|
||||
"error",
|
||||
}, {
|
||||
Errorf("%s", "error"),
|
||||
"%+v",
|
||||
"error\n" +
|
||||
"github.com/pkg/errors.TestFormatErrorf\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:56",
|
||||
}}
|
||||
|
||||
for i, tt := range tests {
|
||||
testFormatRegexp(t, i, tt.error, tt.format, tt.want)
|
||||
}
|
||||
}
|
||||
|
||||
func TestFormatWrap(t *testing.T) {
|
||||
tests := []struct {
|
||||
error
|
||||
format string
|
||||
want string
|
||||
}{{
|
||||
Wrap(New("error"), "error2"),
|
||||
"%s",
|
||||
"error2: error",
|
||||
}, {
|
||||
Wrap(New("error"), "error2"),
|
||||
"%v",
|
||||
"error2: error",
|
||||
}, {
|
||||
Wrap(New("error"), "error2"),
|
||||
"%+v",
|
||||
"error\n" +
|
||||
"github.com/pkg/errors.TestFormatWrap\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:82",
|
||||
}, {
|
||||
Wrap(io.EOF, "error"),
|
||||
"%s",
|
||||
"error: EOF",
|
||||
}, {
|
||||
Wrap(io.EOF, "error"),
|
||||
"%v",
|
||||
"error: EOF",
|
||||
}, {
|
||||
Wrap(io.EOF, "error"),
|
||||
"%+v",
|
||||
"EOF\n" +
|
||||
"error\n" +
|
||||
"github.com/pkg/errors.TestFormatWrap\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:96",
|
||||
}, {
|
||||
Wrap(Wrap(io.EOF, "error1"), "error2"),
|
||||
"%+v",
|
||||
"EOF\n" +
|
||||
"error1\n" +
|
||||
"github.com/pkg/errors.TestFormatWrap\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:103\n",
|
||||
}, {
|
||||
Wrap(New("error with space"), "context"),
|
||||
"%q",
|
||||
`"context: error with space"`,
|
||||
}}
|
||||
|
||||
for i, tt := range tests {
|
||||
testFormatRegexp(t, i, tt.error, tt.format, tt.want)
|
||||
}
|
||||
}
|
||||
|
||||
func TestFormatWrapf(t *testing.T) {
|
||||
tests := []struct {
|
||||
error
|
||||
format string
|
||||
want string
|
||||
}{{
|
||||
Wrapf(io.EOF, "error%d", 2),
|
||||
"%s",
|
||||
"error2: EOF",
|
||||
}, {
|
||||
Wrapf(io.EOF, "error%d", 2),
|
||||
"%v",
|
||||
"error2: EOF",
|
||||
}, {
|
||||
Wrapf(io.EOF, "error%d", 2),
|
||||
"%+v",
|
||||
"EOF\n" +
|
||||
"error2\n" +
|
||||
"github.com/pkg/errors.TestFormatWrapf\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:134",
|
||||
}, {
|
||||
Wrapf(New("error"), "error%d", 2),
|
||||
"%s",
|
||||
"error2: error",
|
||||
}, {
|
||||
Wrapf(New("error"), "error%d", 2),
|
||||
"%v",
|
||||
"error2: error",
|
||||
}, {
|
||||
Wrapf(New("error"), "error%d", 2),
|
||||
"%+v",
|
||||
"error\n" +
|
||||
"github.com/pkg/errors.TestFormatWrapf\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:149",
|
||||
}}
|
||||
|
||||
for i, tt := range tests {
|
||||
testFormatRegexp(t, i, tt.error, tt.format, tt.want)
|
||||
}
|
||||
}
|
||||
|
||||
func TestFormatWithStack(t *testing.T) {
|
||||
tests := []struct {
|
||||
error
|
||||
format string
|
||||
want []string
|
||||
}{{
|
||||
WithStack(io.EOF),
|
||||
"%s",
|
||||
[]string{"EOF"},
|
||||
}, {
|
||||
WithStack(io.EOF),
|
||||
"%v",
|
||||
[]string{"EOF"},
|
||||
}, {
|
||||
WithStack(io.EOF),
|
||||
"%+v",
|
||||
[]string{"EOF",
|
||||
"github.com/pkg/errors.TestFormatWithStack\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:175"},
|
||||
}, {
|
||||
WithStack(New("error")),
|
||||
"%s",
|
||||
[]string{"error"},
|
||||
}, {
|
||||
WithStack(New("error")),
|
||||
"%v",
|
||||
[]string{"error"},
|
||||
}, {
|
||||
WithStack(New("error")),
|
||||
"%+v",
|
||||
[]string{"error",
|
||||
"github.com/pkg/errors.TestFormatWithStack\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:189",
|
||||
"github.com/pkg/errors.TestFormatWithStack\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:189"},
|
||||
}, {
|
||||
WithStack(WithStack(io.EOF)),
|
||||
"%+v",
|
||||
[]string{"EOF",
|
||||
"github.com/pkg/errors.TestFormatWithStack\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:197",
|
||||
"github.com/pkg/errors.TestFormatWithStack\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:197"},
|
||||
}, {
|
||||
WithStack(WithStack(Wrapf(io.EOF, "message"))),
|
||||
"%+v",
|
||||
[]string{"EOF",
|
||||
"message",
|
||||
"github.com/pkg/errors.TestFormatWithStack\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:205",
|
||||
"github.com/pkg/errors.TestFormatWithStack\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:205",
|
||||
"github.com/pkg/errors.TestFormatWithStack\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:205"},
|
||||
}, {
|
||||
WithStack(Errorf("error%d", 1)),
|
||||
"%+v",
|
||||
[]string{"error1",
|
||||
"github.com/pkg/errors.TestFormatWithStack\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:216",
|
||||
"github.com/pkg/errors.TestFormatWithStack\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:216"},
|
||||
}}
|
||||
|
||||
for i, tt := range tests {
|
||||
testFormatCompleteCompare(t, i, tt.error, tt.format, tt.want, true)
|
||||
}
|
||||
}
|
||||
|
||||
func TestFormatWithMessage(t *testing.T) {
|
||||
tests := []struct {
|
||||
error
|
||||
format string
|
||||
want []string
|
||||
}{{
|
||||
WithMessage(New("error"), "error2"),
|
||||
"%s",
|
||||
[]string{"error2: error"},
|
||||
}, {
|
||||
WithMessage(New("error"), "error2"),
|
||||
"%v",
|
||||
[]string{"error2: error"},
|
||||
}, {
|
||||
WithMessage(New("error"), "error2"),
|
||||
"%+v",
|
||||
[]string{
|
||||
"error",
|
||||
"github.com/pkg/errors.TestFormatWithMessage\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:244",
|
||||
"error2"},
|
||||
}, {
|
||||
WithMessage(io.EOF, "addition1"),
|
||||
"%s",
|
||||
[]string{"addition1: EOF"},
|
||||
}, {
|
||||
WithMessage(io.EOF, "addition1"),
|
||||
"%v",
|
||||
[]string{"addition1: EOF"},
|
||||
}, {
|
||||
WithMessage(io.EOF, "addition1"),
|
||||
"%+v",
|
||||
[]string{"EOF", "addition1"},
|
||||
}, {
|
||||
WithMessage(WithMessage(io.EOF, "addition1"), "addition2"),
|
||||
"%v",
|
||||
[]string{"addition2: addition1: EOF"},
|
||||
}, {
|
||||
WithMessage(WithMessage(io.EOF, "addition1"), "addition2"),
|
||||
"%+v",
|
||||
[]string{"EOF", "addition1", "addition2"},
|
||||
}, {
|
||||
Wrap(WithMessage(io.EOF, "error1"), "error2"),
|
||||
"%+v",
|
||||
[]string{"EOF", "error1", "error2",
|
||||
"github.com/pkg/errors.TestFormatWithMessage\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:272"},
|
||||
}, {
|
||||
WithMessage(Errorf("error%d", 1), "error2"),
|
||||
"%+v",
|
||||
[]string{"error1",
|
||||
"github.com/pkg/errors.TestFormatWithMessage\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:278",
|
||||
"error2"},
|
||||
}, {
|
||||
WithMessage(WithStack(io.EOF), "error"),
|
||||
"%+v",
|
||||
[]string{
|
||||
"EOF",
|
||||
"github.com/pkg/errors.TestFormatWithMessage\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:285",
|
||||
"error"},
|
||||
}, {
|
||||
WithMessage(Wrap(WithStack(io.EOF), "inside-error"), "outside-error"),
|
||||
"%+v",
|
||||
[]string{
|
||||
"EOF",
|
||||
"github.com/pkg/errors.TestFormatWithMessage\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:293",
|
||||
"inside-error",
|
||||
"github.com/pkg/errors.TestFormatWithMessage\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:293",
|
||||
"outside-error"},
|
||||
}}
|
||||
|
||||
for i, tt := range tests {
|
||||
testFormatCompleteCompare(t, i, tt.error, tt.format, tt.want, true)
|
||||
}
|
||||
}
|
||||
|
||||
func TestFormatGeneric(t *testing.T) {
|
||||
starts := []struct {
|
||||
err error
|
||||
want []string
|
||||
}{
|
||||
{New("new-error"), []string{
|
||||
"new-error",
|
||||
"github.com/pkg/errors.TestFormatGeneric\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:315"},
|
||||
}, {Errorf("errorf-error"), []string{
|
||||
"errorf-error",
|
||||
"github.com/pkg/errors.TestFormatGeneric\n" +
|
||||
"\t.+/github.com/pkg/errors/format_test.go:319"},
|
||||
}, {errors.New("errors-new-error"), []string{
|
||||
"errors-new-error"},
|
||||
},
|
||||
}
|
||||
|
||||
wrappers := []wrapper{
|
||||
{
|
||||
func(err error) error { return WithMessage(err, "with-message") },
|
||||
[]string{"with-message"},
|
||||
}, {
|
||||
func(err error) error { return WithStack(err) },
|
||||
[]string{
|
||||
"github.com/pkg/errors.(func·002|TestFormatGeneric.func2)\n\t" +
|
||||
".+/github.com/pkg/errors/format_test.go:333",
|
||||
},
|
||||
}, {
|
||||
func(err error) error { return Wrap(err, "wrap-error") },
|
||||
[]string{
|
||||
"wrap-error",
|
||||
"github.com/pkg/errors.(func·003|TestFormatGeneric.func3)\n\t" +
|
||||
".+/github.com/pkg/errors/format_test.go:339",
|
||||
},
|
||||
}, {
|
||||
func(err error) error { return Wrapf(err, "wrapf-error%d", 1) },
|
||||
[]string{
|
||||
"wrapf-error1",
|
||||
"github.com/pkg/errors.(func·004|TestFormatGeneric.func4)\n\t" +
|
||||
".+/github.com/pkg/errors/format_test.go:346",
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
for s := range starts {
|
||||
err := starts[s].err
|
||||
want := starts[s].want
|
||||
testFormatCompleteCompare(t, s, err, "%+v", want, false)
|
||||
testGenericRecursive(t, err, want, wrappers, 3)
|
||||
}
|
||||
}
|
||||
|
||||
func testFormatRegexp(t *testing.T, n int, arg interface{}, format, want string) {
|
||||
got := fmt.Sprintf(format, arg)
|
||||
gotLines := strings.SplitN(got, "\n", -1)
|
||||
wantLines := strings.SplitN(want, "\n", -1)
|
||||
|
||||
if len(wantLines) > len(gotLines) {
|
||||
t.Errorf("test %d: wantLines(%d) > gotLines(%d):\n got: %q\nwant: %q", n+1, len(wantLines), len(gotLines), got, want)
|
||||
return
|
||||
}
|
||||
|
||||
for i, w := range wantLines {
|
||||
match, err := regexp.MatchString(w, gotLines[i])
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if !match {
|
||||
t.Errorf("test %d: line %d: fmt.Sprintf(%q, err):\n got: %q\nwant: %q", n+1, i+1, format, got, want)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
var stackLineR = regexp.MustCompile(`\.`)
|
||||
|
||||
// parseBlocks parses input into a slice, where:
|
||||
// - incase entry contains a newline, its a stacktrace
|
||||
// - incase entry contains no newline, its a solo line.
|
||||
//
|
||||
// Detecting stack boundaries only works incase the WithStack-calls are
|
||||
// to be found on the same line, thats why it is optionally here.
|
||||
//
|
||||
// Example use:
|
||||
//
|
||||
// for _, e := range blocks {
|
||||
// if strings.ContainsAny(e, "\n") {
|
||||
// // Match as stack
|
||||
// } else {
|
||||
// // Match as line
|
||||
// }
|
||||
// }
|
||||
//
|
||||
func parseBlocks(input string, detectStackboundaries bool) ([]string, error) {
|
||||
var blocks []string
|
||||
|
||||
stack := ""
|
||||
wasStack := false
|
||||
lines := map[string]bool{} // already found lines
|
||||
|
||||
for _, l := range strings.Split(input, "\n") {
|
||||
isStackLine := stackLineR.MatchString(l)
|
||||
|
||||
switch {
|
||||
case !isStackLine && wasStack:
|
||||
blocks = append(blocks, stack, l)
|
||||
stack = ""
|
||||
lines = map[string]bool{}
|
||||
case isStackLine:
|
||||
if wasStack {
|
||||
// Detecting two stacks after another, possible cause lines match in
|
||||
// our tests due to WithStack(WithStack(io.EOF)) on same line.
|
||||
if detectStackboundaries {
|
||||
if lines[l] {
|
||||
if len(stack) == 0 {
|
||||
return nil, errors.New("len of block must not be zero here")
|
||||
}
|
||||
|
||||
blocks = append(blocks, stack)
|
||||
stack = l
|
||||
lines = map[string]bool{l: true}
|
||||
continue
|
||||
}
|
||||
}
|
||||
|
||||
stack = stack + "\n" + l
|
||||
} else {
|
||||
stack = l
|
||||
}
|
||||
lines[l] = true
|
||||
case !isStackLine && !wasStack:
|
||||
blocks = append(blocks, l)
|
||||
default:
|
||||
return nil, errors.New("must not happen")
|
||||
}
|
||||
|
||||
wasStack = isStackLine
|
||||
}
|
||||
|
||||
// Use up stack
|
||||
if stack != "" {
|
||||
blocks = append(blocks, stack)
|
||||
}
|
||||
return blocks, nil
|
||||
}
|
||||
|
||||
func testFormatCompleteCompare(t *testing.T, n int, arg interface{}, format string, want []string, detectStackBoundaries bool) {
|
||||
gotStr := fmt.Sprintf(format, arg)
|
||||
|
||||
got, err := parseBlocks(gotStr, detectStackBoundaries)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
if len(got) != len(want) {
|
||||
t.Fatalf("test %d: fmt.Sprintf(%s, err) -> wrong number of blocks: got(%d) want(%d)\n got: %s\nwant: %s\ngotStr: %q",
|
||||
n+1, format, len(got), len(want), prettyBlocks(got), prettyBlocks(want), gotStr)
|
||||
}
|
||||
|
||||
for i := range got {
|
||||
if strings.ContainsAny(want[i], "\n") {
|
||||
// Match as stack
|
||||
match, err := regexp.MatchString(want[i], got[i])
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
if !match {
|
||||
t.Fatalf("test %d: block %d: fmt.Sprintf(%q, err):\ngot:\n%q\nwant:\n%q\nall-got:\n%s\nall-want:\n%s\n",
|
||||
n+1, i+1, format, got[i], want[i], prettyBlocks(got), prettyBlocks(want))
|
||||
}
|
||||
} else {
|
||||
// Match as message
|
||||
if got[i] != want[i] {
|
||||
t.Fatalf("test %d: fmt.Sprintf(%s, err) at block %d got != want:\n got: %q\nwant: %q", n+1, format, i+1, got[i], want[i])
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
type wrapper struct {
|
||||
wrap func(err error) error
|
||||
want []string
|
||||
}
|
||||
|
||||
func prettyBlocks(blocks []string, prefix ...string) string {
|
||||
var out []string
|
||||
|
||||
for _, b := range blocks {
|
||||
out = append(out, fmt.Sprintf("%v", b))
|
||||
}
|
||||
|
||||
return " " + strings.Join(out, "\n ")
|
||||
}
|
||||
|
||||
func testGenericRecursive(t *testing.T, beforeErr error, beforeWant []string, list []wrapper, maxDepth int) {
|
||||
if len(beforeWant) == 0 {
|
||||
panic("beforeWant must not be empty")
|
||||
}
|
||||
for _, w := range list {
|
||||
if len(w.want) == 0 {
|
||||
panic("want must not be empty")
|
||||
}
|
||||
|
||||
err := w.wrap(beforeErr)
|
||||
|
||||
// Copy required cause append(beforeWant, ..) modified beforeWant subtly.
|
||||
beforeCopy := make([]string, len(beforeWant))
|
||||
copy(beforeCopy, beforeWant)
|
||||
|
||||
beforeWant := beforeCopy
|
||||
last := len(beforeWant) - 1
|
||||
var want []string
|
||||
|
||||
// Merge two stacks behind each other.
|
||||
if strings.ContainsAny(beforeWant[last], "\n") && strings.ContainsAny(w.want[0], "\n") {
|
||||
want = append(beforeWant[:last], append([]string{beforeWant[last] + "((?s).*)" + w.want[0]}, w.want[1:]...)...)
|
||||
} else {
|
||||
want = append(beforeWant, w.want...)
|
||||
}
|
||||
|
||||
testFormatCompleteCompare(t, maxDepth, err, "%+v", want, false)
|
||||
if maxDepth > 0 {
|
||||
testGenericRecursive(t, err, want, list, maxDepth-1)
|
||||
}
|
||||
}
|
||||
}
|
8
vendor/github.com/pkg/errors/stack.go
generated
vendored
8
vendor/github.com/pkg/errors/stack.go
generated
vendored
|
@ -79,6 +79,14 @@ func (f Frame) Format(s fmt.State, verb rune) {
|
|||
// StackTrace is stack of Frames from innermost (newest) to outermost (oldest).
|
||||
type StackTrace []Frame
|
||||
|
||||
// Format formats the stack of Frames according to the fmt.Formatter interface.
|
||||
//
|
||||
// %s lists source files for each Frame in the stack
|
||||
// %v lists the source file and line number for each Frame in the stack
|
||||
//
|
||||
// Format accepts flags that alter the printing of some verbs, as follows:
|
||||
//
|
||||
// %+v Prints filename, function, and line number for each Frame in the stack.
|
||||
func (st StackTrace) Format(s fmt.State, verb rune) {
|
||||
switch verb {
|
||||
case 'v':
|
||||
|
|
292
vendor/github.com/pkg/errors/stack_test.go
generated
vendored
Normal file
292
vendor/github.com/pkg/errors/stack_test.go
generated
vendored
Normal file
|
@ -0,0 +1,292 @@
|
|||
package errors
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"runtime"
|
||||
"testing"
|
||||
)
|
||||
|
||||
var initpc, _, _, _ = runtime.Caller(0)
|
||||
|
||||
func TestFrameLine(t *testing.T) {
|
||||
var tests = []struct {
|
||||
Frame
|
||||
want int
|
||||
}{{
|
||||
Frame(initpc),
|
||||
9,
|
||||
}, {
|
||||
func() Frame {
|
||||
var pc, _, _, _ = runtime.Caller(0)
|
||||
return Frame(pc)
|
||||
}(),
|
||||
20,
|
||||
}, {
|
||||
func() Frame {
|
||||
var pc, _, _, _ = runtime.Caller(1)
|
||||
return Frame(pc)
|
||||
}(),
|
||||
28,
|
||||
}, {
|
||||
Frame(0), // invalid PC
|
||||
0,
|
||||
}}
|
||||
|
||||
for _, tt := range tests {
|
||||
got := tt.Frame.line()
|
||||
want := tt.want
|
||||
if want != got {
|
||||
t.Errorf("Frame(%v): want: %v, got: %v", uintptr(tt.Frame), want, got)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
type X struct{}
|
||||
|
||||
func (x X) val() Frame {
|
||||
var pc, _, _, _ = runtime.Caller(0)
|
||||
return Frame(pc)
|
||||
}
|
||||
|
||||
func (x *X) ptr() Frame {
|
||||
var pc, _, _, _ = runtime.Caller(0)
|
||||
return Frame(pc)
|
||||
}
|
||||
|
||||
func TestFrameFormat(t *testing.T) {
|
||||
var tests = []struct {
|
||||
Frame
|
||||
format string
|
||||
want string
|
||||
}{{
|
||||
Frame(initpc),
|
||||
"%s",
|
||||
"stack_test.go",
|
||||
}, {
|
||||
Frame(initpc),
|
||||
"%+s",
|
||||
"github.com/pkg/errors.init\n" +
|
||||
"\t.+/github.com/pkg/errors/stack_test.go",
|
||||
}, {
|
||||
Frame(0),
|
||||
"%s",
|
||||
"unknown",
|
||||
}, {
|
||||
Frame(0),
|
||||
"%+s",
|
||||
"unknown",
|
||||
}, {
|
||||
Frame(initpc),
|
||||
"%d",
|
||||
"9",
|
||||
}, {
|
||||
Frame(0),
|
||||
"%d",
|
||||
"0",
|
||||
}, {
|
||||
Frame(initpc),
|
||||
"%n",
|
||||
"init",
|
||||
}, {
|
||||
func() Frame {
|
||||
var x X
|
||||
return x.ptr()
|
||||
}(),
|
||||
"%n",
|
||||
`\(\*X\).ptr`,
|
||||
}, {
|
||||
func() Frame {
|
||||
var x X
|
||||
return x.val()
|
||||
}(),
|
||||
"%n",
|
||||
"X.val",
|
||||
}, {
|
||||
Frame(0),
|
||||
"%n",
|
||||
"",
|
||||
}, {
|
||||
Frame(initpc),
|
||||
"%v",
|
||||
"stack_test.go:9",
|
||||
}, {
|
||||
Frame(initpc),
|
||||
"%+v",
|
||||
"github.com/pkg/errors.init\n" +
|
||||
"\t.+/github.com/pkg/errors/stack_test.go:9",
|
||||
}, {
|
||||
Frame(0),
|
||||
"%v",
|
||||
"unknown:0",
|
||||
}}
|
||||
|
||||
for i, tt := range tests {
|
||||
testFormatRegexp(t, i, tt.Frame, tt.format, tt.want)
|
||||
}
|
||||
}
|
||||
|
||||
func TestFuncname(t *testing.T) {
|
||||
tests := []struct {
|
||||
name, want string
|
||||
}{
|
||||
{"", ""},
|
||||
{"runtime.main", "main"},
|
||||
{"github.com/pkg/errors.funcname", "funcname"},
|
||||
{"funcname", "funcname"},
|
||||
{"io.copyBuffer", "copyBuffer"},
|
||||
{"main.(*R).Write", "(*R).Write"},
|
||||
}
|
||||
|
||||
for _, tt := range tests {
|
||||
got := funcname(tt.name)
|
||||
want := tt.want
|
||||
if got != want {
|
||||
t.Errorf("funcname(%q): want: %q, got %q", tt.name, want, got)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestTrimGOPATH(t *testing.T) {
|
||||
var tests = []struct {
|
||||
Frame
|
||||
want string
|
||||
}{{
|
||||
Frame(initpc),
|
||||
"github.com/pkg/errors/stack_test.go",
|
||||
}}
|
||||
|
||||
for i, tt := range tests {
|
||||
pc := tt.Frame.pc()
|
||||
fn := runtime.FuncForPC(pc)
|
||||
file, _ := fn.FileLine(pc)
|
||||
got := trimGOPATH(fn.Name(), file)
|
||||
testFormatRegexp(t, i, got, "%s", tt.want)
|
||||
}
|
||||
}
|
||||
|
||||
func TestStackTrace(t *testing.T) {
|
||||
tests := []struct {
|
||||
err error
|
||||
want []string
|
||||
}{{
|
||||
New("ooh"), []string{
|
||||
"github.com/pkg/errors.TestStackTrace\n" +
|
||||
"\t.+/github.com/pkg/errors/stack_test.go:172",
|
||||
},
|
||||
}, {
|
||||
Wrap(New("ooh"), "ahh"), []string{
|
||||
"github.com/pkg/errors.TestStackTrace\n" +
|
||||
"\t.+/github.com/pkg/errors/stack_test.go:177", // this is the stack of Wrap, not New
|
||||
},
|
||||
}, {
|
||||
Cause(Wrap(New("ooh"), "ahh")), []string{
|
||||
"github.com/pkg/errors.TestStackTrace\n" +
|
||||
"\t.+/github.com/pkg/errors/stack_test.go:182", // this is the stack of New
|
||||
},
|
||||
}, {
|
||||
func() error { return New("ooh") }(), []string{
|
||||
`github.com/pkg/errors.(func·009|TestStackTrace.func1)` +
|
||||
"\n\t.+/github.com/pkg/errors/stack_test.go:187", // this is the stack of New
|
||||
"github.com/pkg/errors.TestStackTrace\n" +
|
||||
"\t.+/github.com/pkg/errors/stack_test.go:187", // this is the stack of New's caller
|
||||
},
|
||||
}, {
|
||||
Cause(func() error {
|
||||
return func() error {
|
||||
return Errorf("hello %s", fmt.Sprintf("world"))
|
||||
}()
|
||||
}()), []string{
|
||||
`github.com/pkg/errors.(func·010|TestStackTrace.func2.1)` +
|
||||
"\n\t.+/github.com/pkg/errors/stack_test.go:196", // this is the stack of Errorf
|
||||
`github.com/pkg/errors.(func·011|TestStackTrace.func2)` +
|
||||
"\n\t.+/github.com/pkg/errors/stack_test.go:197", // this is the stack of Errorf's caller
|
||||
"github.com/pkg/errors.TestStackTrace\n" +
|
||||
"\t.+/github.com/pkg/errors/stack_test.go:198", // this is the stack of Errorf's caller's caller
|
||||
},
|
||||
}}
|
||||
for i, tt := range tests {
|
||||
x, ok := tt.err.(interface {
|
||||
StackTrace() StackTrace
|
||||
})
|
||||
if !ok {
|
||||
t.Errorf("expected %#v to implement StackTrace() StackTrace", tt.err)
|
||||
continue
|
||||
}
|
||||
st := x.StackTrace()
|
||||
for j, want := range tt.want {
|
||||
testFormatRegexp(t, i, st[j], "%+v", want)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func stackTrace() StackTrace {
|
||||
const depth = 8
|
||||
var pcs [depth]uintptr
|
||||
n := runtime.Callers(1, pcs[:])
|
||||
var st stack = pcs[0:n]
|
||||
return st.StackTrace()
|
||||
}
|
||||
|
||||
func TestStackTraceFormat(t *testing.T) {
|
||||
tests := []struct {
|
||||
StackTrace
|
||||
format string
|
||||
want string
|
||||
}{{
|
||||
nil,
|
||||
"%s",
|
||||
`\[\]`,
|
||||
}, {
|
||||
nil,
|
||||
"%v",
|
||||
`\[\]`,
|
||||
}, {
|
||||
nil,
|
||||
"%+v",
|
||||
"",
|
||||
}, {
|
||||
nil,
|
||||
"%#v",
|
||||
`\[\]errors.Frame\(nil\)`,
|
||||
}, {
|
||||
make(StackTrace, 0),
|
||||
"%s",
|
||||
`\[\]`,
|
||||
}, {
|
||||
make(StackTrace, 0),
|
||||
"%v",
|
||||
`\[\]`,
|
||||
}, {
|
||||
make(StackTrace, 0),
|
||||
"%+v",
|
||||
"",
|
||||
}, {
|
||||
make(StackTrace, 0),
|
||||
"%#v",
|
||||
`\[\]errors.Frame{}`,
|
||||
}, {
|
||||
stackTrace()[:2],
|
||||
"%s",
|
||||
`\[stack_test.go stack_test.go\]`,
|
||||
}, {
|
||||
stackTrace()[:2],
|
||||
"%v",
|
||||
`\[stack_test.go:225 stack_test.go:272\]`,
|
||||
}, {
|
||||
stackTrace()[:2],
|
||||
"%+v",
|
||||
"\n" +
|
||||
"github.com/pkg/errors.stackTrace\n" +
|
||||
"\t.+/github.com/pkg/errors/stack_test.go:225\n" +
|
||||
"github.com/pkg/errors.TestStackTraceFormat\n" +
|
||||
"\t.+/github.com/pkg/errors/stack_test.go:276",
|
||||
}, {
|
||||
stackTrace()[:2],
|
||||
"%#v",
|
||||
`\[\]errors.Frame{stack_test.go:225, stack_test.go:284}`,
|
||||
}}
|
||||
|
||||
for i, tt := range tests {
|
||||
testFormatRegexp(t, i, tt.StackTrace, tt.format, tt.want)
|
||||
}
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue