Skip to main content

Go Errors

· 2 min read

In Go, errors are returned as values. We can construct them in several ways.

Error constant

var (
errorA = errors.New("something wrong A")
)

With errorA defined, it can be used within the same package and returned when needed. It is also useful in testing, allowing comparisons against the error returned by a function using errors.Is.

func TestErrorWithIs(err error) {
if errors.Is(err, errorA) {
fmt.Printf("TestErrorWithIs: %v\n", err)
}
}

Custom Error Type

type CustomError struct {
Message string
}

func (e *CustomError) Error() string {
return e.Message
}

We can implement the error interface to create custom error types. This allows us to define more complex errors or a hierarchy of errors.

type SpecificCustomError struct {
CustomError
}

func NewSpecificCustomError() error {
return &SpecificCustomError{
CustomError: CustomError{
Message: "error due to a specific reason",
},
}
}

Checking for Custom Errors

To check equality for custom errors, use type assertion:

func TestErrorWithAs(err error) {
var specificCustomError *SpecificCustomError
if errors.As(err, &specificCustomError) {
fmt.Printf("TestErrorWithAs: %v\n", err)
}
}

Alternatively, compare by assigning the error to a variable of the custom error type:

var (
customError = NewSpecificCustomError()
)

func TestErrorWithEqual(err error) {
if err == customError {
fmt.Printf("TestErrorWithEqual: %v\n", err)
}
if err == NewSpecificCustomError() {
fmt.Println("this won't print anything")
}
}

Note: Comparing with == will fail on wrapped errors. Use errors.Is to check for a specific error.

A full example of the above can be found here in the playground.

Caveats

Error constants have the limitation that they lack dynamic information since the error message is fixed. Additionally, as they are part of the package's public API, they should be thoughtfully designed to avoid exposing internal details.

In Dave Cheney's post, he discusses strategies for error handling in Go. One takeaway is to go with error wrapping. The Go 2 error handling proposal also suggests changes to error handling, which might influence future practices.

References