3 ms·
It's really a joke :) Fundamentally, the Go team made the correct choice between explicit and implicit error handling. Yet one would hope for a bit terser synt
by alquemist 6y ago
It's really a joke :)
Fundamentally, the Go team made the correct choice between explicit and implicit error handling. Yet one would hope for a bit terser syntax and language supported stack traces, 11 years after launch.
For a good overview of the issue: https://go.googlesource.com/proposal/+/master/design/go2draft-error-handling-overview.md https://go.googlesource.com/proposal/+/master/design/go2draf....
- mseepgood 6y ago> Yet one would hope for a bit terser syntax and language supported stack traces, 11 years after launch. The Go team tried, but the community shot it down. Your link was the first proposal, and this was the second proposal: https://github.com/golang/proposal/blob/master/design/32437-try-builtin.md https://github.com/golang/proposal/blob/master/design/32437-...
- Groxx 6y agoAs one who didn't like either proposal: I'm thrilled that they were shot down. Both worked fine (great, even) in simple cases, but fell apart when needing to add context / wrapping to multiple possible errors. Simple cases are already simple. It's the harder spots that need help.
- alquemist 6y agoCan you please share some examples of the harder spots?
- Groxx 6y agoBoth have at least one shared issue which makes 2+ error wrapping noisy or nasty: func whatev() (err error) { defer helper(&err, "mightFail context to help debugging", some, vars) try(mightFail()) defer helper(&err, "alsoMightFail context to help debugging", some, vars) try(alsoMightFail()) } if the second call fails, your error has now been wrapped twice. There are of course ways to deal with this. You can add a "already wrapped" sentinel of some kind (say, a * bool that they check and modify), or use a `helper := once(helperfn)` to do that same kind of thing internally... but that's more verbose. And can't be done generically without reflection (though `func(*error, string, ...interface{})` would be quite common, which might be good enough). Inline handlers shown in many examples are even worse since they can't be composed as easily, so you'd probably end up maintaining a bool var between all handlers. By hand. They both also require naming your `error` return value, which requires naming all returned values, which has been a depressingly large source of shadowing and not-initialized-value mistakes in my experience. Improperly-initialized values especially, as those tend to cause problems a fair distance from the cause, and sometimes go unnoticed for quite a while. tl;dr it adds more easily-forgotten boilerplate to non-trivial error handling, and makes it and related code more mistake-prone. I'd rather have `return fmt.Errorf(err, ...)`, it fairly naturally resists growing more complex as your func grows more complex.
- alquemist 6y agoThanks, appreciated. Your example rhymes with u/jhoechtl remark that there is no standardized way to manage stack traces, aka stacked error contexts. Perhaps the Golang elves will come up with an elegant solution. By 2025 :)
- deleted 6y ago[deleted]