我有一个记录器,将堆栈跟踪记录到stdout
。我想获取记录到字符串值中的堆栈跟踪,以便将其作为调试电子邮件发送。
这是我目前的代码:
func (l *Logger) withStack(writer io.Writer, err error) error {
err = errors.WithStack(err)
fmt.Fprintf(writer, "%+v\n", err)
return err
}
func (l *Logger) Error(err error) error {
// Logs stack trace to `stdout`...
l.withStack(os.Stdout, err)
// Here I want to get the string value of what was logged to `stdout`.
}
但如果stdout
堆栈跟踪如下所示:
foo
infrastructure/logger.(*Logger).withStack
/Users/lansana/Projects/Go/src/app/src/infrastructure/logger/logger.go:40
infrastructure/logger.(*Logger).Error
/Users/lansana/Projects/Go/src/app/src/infrastructure/logger/logger.go:50
main.main
/Users/lansana/Projects/Go/src/app/src/microservices/api/main.go:44
runtime.main
/usr/local/Cellar/go/1.9/libexec/src/runtime/proc.go:185
runtime.goexit
/usr/local/Cellar/go/1.9/libexec/src/runtime/asm_amd64.s:2337
...然后电子邮件中err.Error()
的结果只是foo
。
我想这是有道理的,因为错误本身只包含foo
而不是堆栈跟踪本身,但是如何才能将精确的堆栈跟踪作为字符串值?
答案 0 :(得分:1)
withStack
没有登录到stdout:它会记录到您提供的io.Writer
的任何实现。要轻松获取字符串,请考虑将其传递给bytes.Buffer
。
您的Error
功能可能如下所示:
func sendErrorMail(s string) error {
// Send the stack trace `s` by email
}
func (l *Logger) Error(err error) {
// Get the stack trace as a string
buf := new(bytes.Buffer)
l.withStack(buf, err)
sendErrorMail(buf.String())
}