However, the current implementation of error handling is atrocious.
If Go would take sum types and question marks from Rust, Go would keep the general error handling strategy and philosophy with the difference of being way less verbose and more ergonomic.
Go is an incomplete language masquerading as a simple one.
> Completeness -- the design must cover as many important situations as is practical. All reasonably expected cases should be covered. Completeness can be sacrificed in favor of any other quality. In fact, completeness must be sacrificed whenever implementation simplicity is jeopardized. Consistency can be sacrificed to achieve completeness if simplicity is retained; especially worthless is consistency of interface.
are you seriously suggesting that Go's insistence of requiring the programmer to scatter "if err != nil {}" after most function calls - with no compiler assistance if you forget - is complete either in the sense of "having all necessary parts, elements, or steps" or "being finished"?
it's terrible, causes bugs and it seems incredibly unlikely to me that it won't be improved.
How, exactly, are going to forget a necessary `if err != nil` without your test suite blowing up?
If you do hate other developers for some reason, why not leave out some `err != nil`s to really drive home your hatred towards them?
A language with generics and sum types (so you can implement something like Either, Try, or Result) doesn't let you use the result of a fallible function call without handling the error explicitly. And if the result is unit/void, most compilers/linters will still warn you if you haven't used the Either/Try/Result type that's returned.
But ultimately it doesn't matter. Write in whatever language you feel comfortable and most productive.
Well, unless you're starting a new security-sensitive project and want to write in C. Just... stop.
Assuming you don't hate other developers, and given the tests you would write in any language, how do you foresee missing an error branch? Again, not specifically trying to test for something that a sufficiently advanced type system would catch, just your regular level documenting that demonstrates to other developers that you don't hate them.
> then you can just as easily forget to add a proper test for that error condition
If an error condition is easily forgotten in the documentation, then who cares about the implementation thereof? It is obviously not important. In fact, it is arguable that your program is incorrect if you do handle the condition in such a case.
But in this case you don't need to know about what paths have been executed. It will be obvious that an error path was not handled when your program does not adhere to function that is documented.
It isn't a perfect solution, but it works at community level without needing to wait for the Go team to take care of or changing the language/toolchain.
Does this happen? Is there any data on how often error checking is forgotten?
if err != nil { return nil }
With how boilerplate the correct version is, you learn to skip over it entirely, meaning it can be hard to spot that anything is wrong here. Linters do exist for this now, but they have so many false positives on other error handling cases that most people don't bother with them.
Opinions about languages are going to vary a lot, and I don't think it's productive to debate this kind of thing.
I prefer languages with stronger, more expressive type systems, but I'll freely admit that I code slower (though usually more correctly) in languages like that. Some people prefer languages where they can easily hold all the language's syntax and rules and quirks in their head, and fire out code quickly.
All of that is fine. There's no objective truth there. I agree with the GP that Go feels incomplete. Before generics, it felt embarrassingly incomplete. But if you're fine and happy and productive with it as it is, that's great!
The former is just macros for error definition
The latter is just a wrapper around box dyn error
The go ecosystem frequently utilizes `go generate` to handle boilerplate code generation. That’s the exact same way `thiserror` utilizes macros to generate plain error structs. While macros can do more, in this case it’s the same.
Really an overblown problem from people that don't use Go much tbh. I work with people that used extensivly Java / C# / C++ and it's not the thing they complain about. They usually enjoy the fact that it's not exception based.
The question mark is interesting, but as the try proposal discovered, how do you solve the leaking problem? That doesn't have a good solution yet.
Doesn't compute for me. Care to explain?
Again, needing to be explicit about your intent to do anything with an error is faulty. The values are not dependent. Just because some languages have gotten it wrong doesn't mean they all should.
I'm not sure why you say that the values of a sum type must be "dependent," or what you mean by that. Maybe/Option is a sum type of Nothing or Some<T>. There's no dependency there. If my webserver can return JSON or XML, I might represent that with a sum type holding either a JSON object or an XML tree, but there's no dependency between those two things that I can see.