Take the 2-minute tour ×

What's the idiomatic way to exit a program with some error code?

The documentation for Exit says "The program terminates immediately; deferred functions are not run.", and log.Fatal just calls Exit. For things that aren't heinous errors, terminating the program without running deferred functions seems extreme.

Am I supposed to pass around some state that indicate that there's been an error, and then call Exit(1) at some point where I know that I can exit safely, with all deferred functions having been run?

share|improve this question
What about having a global variable state which is clean by default and set to dirty on non-fatal error. And before your main() exits, you can check for that variable. Not perfectly nice, but it might be the easiest solution in some cases. (I am glad comments can't be donwvoted :)) –  topskip Sep 23 '13 at 17:22
Yeah, that's basically what I ended up doing. I find it inelegant because I have to avoid deferring anything in main (because I still call Exit(1) to set the return code, and don't want to kill my deferred fn), so I stuck what used to be my main (which was only three lines, one of which is a defer) into a function. I'm hoping someone will have a better way. So far, one person has replied with os.Exit, and then deleted their reply when I commented out that I quote the os.Exit docs in my post, and now there's another answer that points me to os.Exit. –  dan Sep 23 '13 at 19:49

4 Answers 4

up vote 3 down vote accepted

I do something along these lines in most of my real main packages, so that the return err convention is adopted as soon as possible, and has a proper termination:

func main() {
    if err := run(); err != nil {
        fmt.Fprintf(os.Stderr, "error: %v\n", err)

func run() error {
    err := something()
    if err != nil {
        return err
    // etc
share|improve this answer

Yes, actually. The os package provides this.

package main

import "os"

func main() {


Edit: so it looks like you know of Exit. This article gives an overview of Panic which will let deferred functions run before returning. Using this in conjunction with an exit may be what you're looking for. http://blog.golang.org/defer-panic-and-recover

share|improve this answer
I am pretty sure @dan knows about it. –  topskip Sep 23 '13 at 17:23
Maybe I misread or he edited but I thought he was talking about something else. –  d1str0 Sep 23 '13 at 17:27

As mentioned by fas, you have func Exit(exitcode int) from the os package.

However, if you need the defered function to be applied, you always can use the defer keywork like this:


You perform all your operation, affect a error variable and at the very end, when everything is cleaned up, you can exit safely.

Otherwise, you could also use panic/recover: http://play.golang.org/p/903e76GnQ-

When you have an error, you panic, end you cleanup where you catch (recover) it.

share|improve this answer

In python I commonly use pattern which converted to go looks like this:

func run() int {
    // here goes
    // the code

    return 1

func main() {
share|improve this answer

Your Answer


