Python global exception handling

Question:

I want to catch KeyboardInterrupt globally, and deal with it nicely. I don’t want to encase my entire script in a huge try/except statement. Is there any way to do this?

Asked By: Kye

||

Answers:

Does your script have a function you call to start it?

main()

then just do:

try:
    main()
except:
    ...

If you don’t have a main but just a huge script that runs line-by-line, then you should put it in a main.

Answered By: Claudiu

There’s no other way to do this, apart from encasing your entire script in a main() function and surrounding that with a try..except block – which is pretty much the same:

def main():
    # Your script goes here
    pass

if __name__ == "__main__":
    try:
        main()
    except KeyboardInterrupt:
        # cleanup code here
        pass
Answered By: Tamás

If this is a script for execution on the command line, you can encapsulate your run-time logic in main(), call it in an if __name__ == '__main__' and wrap that.

if __name__ == '__main__':
    try:
        main()
    except KeyboardInterrupt:
        print 'Killed by user'
        sys.exit(0)
Answered By: Rob Cowie

You can also use signal like this:

import signal, time

def handler(signum, frame):
    print 'I just clicked on CTRL-C '

signal.signal(signal.SIGINT, handler)

print "waiting for 10 s"
time.sleep(10)

Output:

waiting for 10 s
^CI just clicked on CTRL-C

N.B: Don’t mix the use of signal with threads.

Answered By: mouad

You could change sys.excepthook if you really don’t want to use a try/except.

import sys
def my_except_hook(exctype, value, traceback):
    if exctype == KeyboardInterrupt:
        print "Handler code goes here"
    else:
        sys.__excepthook__(exctype, value, traceback)
sys.excepthook = my_except_hook
Answered By: multipleinterfaces
Categories: questions Tags: ,
Answers are sorted by their score. The answer accepted by the question owner as the best is marked with
at the top-right corner.