pkg / errors

Simple error handling primitives

Home Page:https://godoc.org/github.com/pkg/errors

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Format Stacktrace %+v also returns function name

stephanwesten opened this issue · comments

Following test code:

import (
	"fmt"
	"testing"

	"github.com/pkg/errors"
)

func TestErrors(t *testing.T) {
	err := fmt.Errorf("test")
	err2 := errors.Wrap(err, "msg")

	type stackTracer interface {
		StackTrace() errors.StackTrace
	}

	err3, ok := err2.(stackTracer)
	if !ok {
		panic("oops, err does not implement stackTracer")
	}

	st := err3.StackTrace()[0:1]
	fmt.Printf("%+v \n", st)
}

outputs:

=== RUN TestErrors
code.xxx.org/xxx/xxx/lib/services.TestErrors
/Users/swesten/go/src/code.xxx.org/xxx/xxx/lib/services/errors_test.go:12
--- PASS: TestErrors (0.00s)
PASS

According to the docs:
// %+v equivalent to %+s:%d
// %+s path of source file relative to the compile time GOPATH
// %d source line

The function name should not have been printed (and also what I expected), however the function name is printed as you can see in the output.

In the code you can also see fn.Name() for the 's' format:

func (f Frame) Format(s fmt.State, verb rune) {
	switch verb {
	case 's':
		switch {
		case s.Flag('+'):
			pc := f.pc()
			fn := runtime.FuncForPC(pc)
			if fn == nil {
				io.WriteString(s, "unknown")
			} else {
				file, _ := fn.FileLine(pc)
				fmt.Fprintf(s, "%s\n\t%s", fn.Name(), file)
			}
		default:
			io.WriteString(s, path.Base(f.file()))
		}
....

I have question, documentation says that:

%+s   function name and path of source file relative to the compile time
      GOPATH separated by \n\t (<funcname>\n\t<path>)

Is this incorrect then too?

By including the function name and the new line, it is harder to use the output in another error's output. The new line makes the formatting ugly. The consumer should do the formatting. Not this package.

While I understand that you find this behavior unwanted; it appears that the code you are getting your documentation from is out of date (specifically does not include the updated documentation so that it reflects actual behavior)

You can see from the original issue #136 that the decision was made:

Just document the current behaviour. We probably cannot change the output at this point.

Which is true. At this point, we cannot be sure how many people are relying upon the actual behavior rather than what the documentation said. So, the documentation was fixed to reflect the actual behavior.

Sadly I don't think we can fix this in the scope of a 1.x release. I doubt there will be a v2 release people should move to the Go teams errors package when it becomes available.