包堆栈实现了捕获、操作和格式化,提供了比runtime包更简单的API。
官方文档: https://godoc.org/github.com/go-stack/stack
import “github.com/go-stack/stack”
package main
import (
"fmt"
"github.com/go-stack/stack"
)
func main() {
logCaller("%+s")
logCaller("%v %[1]n()")
}
func logCaller(format string) {
fmt.Printf(format+"\n", stack.Caller(1))
}
运行结果:
test/main.go
main.go:11 main()
type Call struct {
frame runtime.Frame
}
func Caller(skip int) Call
调用方从当前goroutine的堆栈中返回一个调用。参数skip是要提升的堆栈帧数,0表示调用函数。
func (c Call) Format(s fmt.State, verb rune)
实现了fmt格式。支持以下格式化程序。
%s source file
%d line number
%n function name
%k last segment of the package path
%v equivalent to %s:%d
它接受以下大多数动词的“+”和“#”标志。
%+s path of source file relative to the compile time GOPATH,
or the module path joined to the path of source file relative
to module root
%#s full path of source file
%+n import path qualified function name
%+k full package path
%+v equivalent to %+s:%d
%#v equivalent to %#s:%d
package main
import (
"fmt"
"github.com/go-stack/stack"
)
func main() {
fmt.Printf("%s\n", stack.Caller(0))
fmt.Printf("%d\n", stack.Caller(0))
fmt.Printf("%n\n", stack.Caller(0))
fmt.Printf("%k\n", stack.Caller(0))
fmt.Printf("%v\n", stack.Caller(0))
fmt.Println()
fmt.Printf("%+s\n", stack.Caller(0))
fmt.Printf("%#s\n", stack.Caller(0))
fmt.Printf("%+n\n", stack.Caller(0))
fmt.Printf("%+k\n", stack.Caller(0))
fmt.Printf("%+v\n", stack.Caller(0))
fmt.Printf("%#v\n", stack.Caller(0))
}
运行结果:
main.go
11
main
main
main.go:14
test/main.go
/root/gocode/src/test/main.go
main.main
main
test/main.go:21
/root/gocode/src/test/main.go:22