-
Notifications
You must be signed in to change notification settings - Fork 17.7k
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
xerrors: Add a function to test an error's chain against a predicate function #30093
Comments
I also played with a version that returns the error that matches the predicate or nil, but
The example predicate I used in the previous thread:
There's talk in the original thread of updating
but note a subtle difference: For |
I think this is absolutely the cleanest API to expose to a user, and we should consider doing it. It does, as you say, have the same drawback of potentially becoming a silent bug in older Go versions. On the other hand, if you always write |
If a predicate function eventually adds support for unwrapping for the user, wouldn't this result in a Suppose you had errors E3 (outer-most), E2, and E1 (inner-most). None of which match the predicate function. Then calling: xerrors.IsFunc(E3, MyFunc) would result in a call tree like:
The problem is that both For sufficiently long error-chains, this can be kinda costly. |
But yes, adding |
I use a version that returns an error
same as the universal
Yes, but the helper might as well use the error-returning version. Also Code generation makes helper writing trivial (if it wasn't already). |
After discussing this internally, we've decided not to add We believe that the cleanest and best API to expose to users is one based on sentinel errors. You should write We will not update Nothing, of course, prevents third-party packages from adding |
I'm splitting this off from #29934 to allow for more focused discussion.
There are three common patterns used in Go code to make control flow decisions based on an error's value.
err == X
._, ok := err.(T); ok
f(err)
.The error values proposal provides
Is
andAs
functions to test an error's chain against a sentinel value or underlying type, respectively. It does, however, not currently provide direct support for the third pattern of predicate functions.Proposal: Add an
IsFunc
function to test an error's chain against a predicate function to thegolang.org/x/xerrors
anderrors
packages.IsFunc
can be used directly with existing predicate functions likeos.IsNotExist
:Why not update
os.IsNotExist
et al. to unwrap errors?No good way to write code that works with current and future versions of Go: You can't rely on
os.IsNotExist
unwrapping so you need to do it yourself to support pre-1.13 Go.This puts the onus on the user to determine if any given predicate function supports unwrapping, and as of what version.
Passing a wrapped error to a predicate which doesn't unwrap is a silent runtime bug. The error can't be detected at compile time, and it isn't even a runtime panic; you just silently take the wrong branch.
If we were starting entirely anew, then it might make sense to put the unwrapping in the predicate functions. Doing so at this time seems difficult to accomplish without encouraging the creation of many subtle bugs.
The text was updated successfully, but these errors were encountered: