-
Notifications
You must be signed in to change notification settings - Fork 13
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Expose traceTree or some variant #71
Comments
Hey, @bufdev! I think exporting traceTree is okay: it doesn't have any internal details—not even the program counters. It's just a plain data structure. (Thinking out loud, probably: Although I agree—exporting this is not my favorite solution. However, it seems better than an overly complicated error tree walker, which is the other option we were considering here to optimize on allocs during formatting. We might still do that in the future, but it could be an internal detail for formatting and the public @prashantv Do you have thoughts on this? |
Oh, that'd be great then if possible :-) But no worries either way. One suggestion: If you do expose |
@bufdev Just confirming one thing for what you were trying to do: you didn't need to know/track the parent/child relationships between errors, right? You just wanted errors and their traces? |
Yea I'm not interested in the relationships between the errors. |
Since we allow annotating an error with a specific frame, I wonder if we should expose the converse -- an API that extracts a single frame from an error (if it's an errtrace wrapped error). The caller can then build up the same tree by unwrapping. I'm OK with also having more APIs to expose the tree, though I'd start with the lowest-level first, then the more common need (customization options for formatting). |
I like starting with that. // UnwrapFrame unwraps the errtrace frame
// stored inside the given error.
//
// inner is the error inside the errtrace, if any.
// ok reports whether a frame was available.
func UnwrapFrame(error) (inner error, frame Frame, ok bool) (I want to not take the name "unwrap" in case we want to provide an errors.Unwrap analog per #38 (comment).) So a user could do something like: // func printTrace(w io.Writer, err error) {
err, frame, ok := UnwrapFrame(err)
for ok {
printFrame(w, frame)
err, frame, ok = UnwrapFrame(err)
}
if err == nil {
// end of stack
return
}
if multi, ok := err.(interface{ Unwrap() []error }); ok {
for _, err := range multi.Unwrap() {
fmt.Fprintln(w) // separate traces with newlines
printTrace(w, err)
}
} |
Per discussion in #71, add an UnwrapFrame function that wraps the outermost errtrace frame from an error. As a result of this change, it's possible to implement buildTraceTree or a variant of it using exported functionality exclusively. This makes it possible for users to use a different trace formatting mechanism than the trees generated by FormatString. Resolves #71
Per discussion in #71, add an UnwrapFrame function that wraps the outermost errtrace frame from an error. As a result of this change, it's possible to implement buildTraceTree or a variant of it using exported functionality exclusively. This makes it possible for users to use a different trace formatting mechanism than the trees generated by FormatString. Resolves #71
This was motivated by wanting to get a printout of just the stack trace, without the underlying error message. That use was was a situation where I had error interceptor logic in place, but didn't control the underlying location where the error was printed, as that was controlled by a different library (github.com/spf13/cobra). I just wanted to get a stack trace to print out to a debug logger, but realized I couldn't just yet.
This could take different forms:
traceTree
directly. Likely not great, you probably don't want users mucking with this.traceTree
under the hood.traceTree
fully, but exposeFormatTrace/FormatTraceString
or the like that just drops the error itself (would solve my original issue, but isn't as universal).Potentially the most idiomatic way to do this would be to expose some custom error type where I can use
errors.Is/As
, which would solve the problem more generally, but I assume this was ruled out.I may be missing something here, just starting to muck around with the library - apologies if this is polluting the issue space!
The text was updated successfully, but these errors were encountered: