Firstly, rust has sum types, so it's possible to have exhaustive matches and know you've handled every case. This isn't possible in go. For comparison:
// go
val, err := doSomething()
switch err.(type) {
case *SomeErrorType:
// handle
default:
panic("inexhaustive error check (at runtime, only if that error type is hit)")
}
// rust
let (val, err) = do_something()
match err {
Err::SomeErrType(inner) => { /* handle */ },
}
// won't compile if the match isn't exhaustive
Note as well that you have to return the error interface, not some more specific type, in go because of the "nil struct is not a nil interface" gotcha. Juggling around structs that are returned as errors is basically impossible to do safely, so everyone returns the error interface. This is another way the language causes error handling to be worse.
Next, generics in rust allow for nicer chaining of computation in the presence of errors. Let me show you two examples. Again, the go and rust code is as identical as I can make it:
// go
val1, err := computation1()
if err != nil {
return nil, err
}
val2, err := computation2(val1)
if err != nil {
return nil, err
}
return computation3(val2)
// equivalent rust
computation1().and_then(computation2).and_then(computation3)
// also equivalent rust
let val1 = computation1()?;
let val2 = computation2(val1)?;
computation3(val2)
The ability to have a generic 'Result<T, E>' type to chain computation allows for code to be more readable, while still having all the benefits of errors being values.
The ability to have a generic 'Option<T>' instead of 'nil' also is very helpful, but enough has already been written about null pointers that I don't wish to rehash it here.
Finally, in practice, rust's higher level features (namely macros) allows libraries to create very powerful developer abstractions around errors, like those offered in the 'failures' crate, all without having any runtime overhead.
In practice, all of these things also combine to result in libraries offering better error types and allowing callers to handle errors well.