Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How can I capture all exceptions from a wxPython application?

I'm writing a little debug app for a bit of kit we're developing and I'd like to roll it out to a few users to see if they can provoke any crashes. Does anyone know a way of effectively wrapping a wxPython app to catch any and all unhandled exceptions that would cause the app to crash?

Ideally I'd want to capture all output (not just errors) and log it to a file. Any unhandled exceptions ought to log to the current file and then allow the exception to pass on as per usual (i.e. the logging process ought to be transparent).

I'm sure someone must have done something along these lines before, but I've not managed to turn up anything that looks useful via google.

like image 699
Jon Cage Avatar asked Oct 03 '08 10:10

Jon Cage


People also ask

How do you capture exceptions in Python?

Catching Exceptions in Python In Python, exceptions can be handled using a try statement. The critical operation which can raise an exception is placed inside the try clause. The code that handles the exceptions is written in the except clause.

Does exception catch all exceptions Python?

Try and Except Statement – Catching all ExceptionsTry and except statements are used to catch and handle exceptions in Python. Statements that can raise exceptions are kept inside the try clause and the statements that handle the exception are written inside except clause.

How does Python handle generic exceptions?

You can also provide a generic except clause, which handles any exception. After the except clause(s), you can include an else-clause. The code in the else-block executes if the code in the try: block does not raise an exception. The else-block is a good place for code that does not need the try: block's protection.

What is the name of the most general of all Python exceptions?

The BaseException class is, as the name suggests, the base class for all built-in exceptions in Python. Typically, this exception is never raised on its own, and should instead be inherited by other, lesser exception classes that can be raised.


2 Answers

For the exception handling, assuming your log file is opened as log:

import sys
import traceback

def excepthook(type, value, tb):
    message = 'Uncaught exception:\n'
    message += ''.join(traceback.format_exception(type, value, tb))
    log.write(message)

sys.excepthook = excepthook
like image 116
monopocalypse Avatar answered Sep 28 '22 18:09

monopocalypse


For logging standard output, you can use a stdout wrapper, such as this one:

from __future__ import with_statement

class OutWrapper(object):
    def __init__(self, realOutput, logFileName):
        self._realOutput = realOutput
        self._logFileName = logFileName

    def _log(self, text):
        with open(self._logFileName, 'a') as logFile:
            logFile.write(text)

    def write(self, text):
        self._log(text)
        self._realOutput.write(text)

You then have to initialize it in your main Python file (the one that runs everything):

import sys    
sys.stdout = OutWrapper(sys.stdout, r'c:\temp\log.txt')

As to logging exceptions, the easiest thing to do is to wrap MainLoop method of wx.App in a try..except, then extract the exception information, save it in some way, and then re-raise the exception through raise, e.g.:

try:
    app.MainLoop()
except:
    exc_info = sys.exc_info()
    saveExcInfo(exc_info) # this method you have to write yourself
    raise
like image 26
DzinX Avatar answered Sep 28 '22 17:09

DzinX