Thursday, May 24, 2012

The Go Programming Language Has Exceptions

It seems like every other post I read about Go states that the Go programming language doesn't have exceptions. This is followed by either an excited explanation on why exceptions are bad and why you don't want them anyway, or an explanation on why Go is deficient because it doesn't have exceptions. It's time to set the record straight. Go has exceptions. Now I really want to believe it. So close your eyes and repeat the following ten times "Go has exceptions". It's OK I'll wait for you to finish. Are you done? Do you believe it? OK now that you know that Go has exceptions in your heart of hearts. I should probably point out that Go really doesn't have exceptions. If you look at the language spec you'll see that there is no section on exceptions. There is no "try", "catch" or "throw" keywords, and nothing on "finally". Even though Go doesn't have exceptions it does have constructs which exhibit exception like semantics that can be used when you want to use exceptions for error handling. Their just not called exceptions.

In the Go language spec there is a section on handling panics. If you read it carefully you'll notice that the description of "panic" sounds a lot like the description of "throw". You may also notice that "recover" sounds lot like "catch", and you can use "defer" in place of "finally". There is no replacement for the "try" key word as Go's "panic", "recover" and "defer" work on function boundaries not on "try/catch" scopes. So there you have it. Even though Go doesn't have exceptions it does have constructs that can be used to handle exceptional error conditions and that closely resemble exceptions.

This raises the question. If Go has exception like constructs, why do people frequently claim that it doesn't have exceptions and you only handle errors via returning an "error" value? I think there are two reasons for this. First of all in the early days of Go there was no "recover" keyword. Any call to panic would terminate the program so people got used to the idea that Go didn't have an exception mechanism. Secondly the convention is for packages to handle any uses of "panic" internally and then to return error values to their callers. This convention means that you never have to worry about recovering from someone else's panic when calling into a Go package. You can however use exception handling internal to your package or in your application, but you don't have to. So it's possible to write Go code and never encounter exceptions. Ensuring that a libraries panics won't leak into your code solves many of the problems with exceptions.

So can we please stop saying that Go doesn't have exceptions? While it may be technically accurate it's misleading. Instead why don't we just say that Go has two complementary error handling mechanisms, one is by returning error values, but much nicer than C's, the other is exception like, but it solves many of the issues with exceptions.


  1. They're different.

    In Java etc, you can use catch to do flow control within a function, similar to an if statement.


In Go, a panic destroys the entire stack frame and you're on your way up the stack. You can't proceed down an alternate path of execution in your function.

    1. in this case return error value instead of panic!!

    2. Just wrap them in a closure inside of the function to get a restricted scope.

  2. Yes they are different (hence my use of "exception like"), but they can be used to solve similar problems that exceptions are used for. You can even simulate flow control within a function just like Java exceptions using lambdas. See My point is that just saying that Go doesn't have exceptions without further explanation is misleading.

  3. Pointer please: what are the issues with exceptions?

  4. Go Programming Language is recently invented by google. It focuses on the comfort of development, speedy compilation and simultaneous computing.

  5. Nice to read this post which is really good thanks for sharing this information.

  6. "Their just not called exceptions."

    Their -> They're

  7. I would say that error handling in Go is easy. However, troubleshooting the root cause of an error in Go sucks. As soon as a functions catches the error and returns its own error value, the root cause of the error is lost.

    An example of this is when I was using a library that called a web service. The library kept returning an error saying it couldn't connect to the server. I checked the server and it was running. I could connect with my browser just fine. It turns out the server I was using had a self-signed certificate that I had imported into my browser but not to my system CA certificates. The library didn't tell me it was an SSL error. It simply said that it couldn't connect.

    I think this is what people are complaining about when they say Go doesn't have exceptions. Sure you can raise a panic but you can't chain panics and/or errors to show the root cause of a problem.