[PyQt] Disabling qFatal on unhandled exceptions
luke.campagnola at gmail.com
Thu Jul 13 21:33:26 BST 2017
On Thu, Jul 13, 2017 at 10:47 AM, Florian Bruhin <me at the-compiler.org> wrote:
> > 2. Python should almost *never* voluntarily abort. This is one of the most
> > fundamental and important differences between C++ and Python. The most
> > common behavior is simply to call an error handler and move on, but even in
> > situations where we are forced to end the process, it is dangerous to
> > *abort* because this circumvents all of Python's shutdown machinery--files
> > are not closed, destructors are not called, atexit callbacks are not
> > invoked.
> So what are you going to do when you're in the middle of running C++
> code and there's a Python exception? You have two choices: Either call
> abort(), or return *some* non-sensical value (like nullptr, or 0, or an
> empty string) to Qt, and handle the exception once you're back in
That's true when you require a non-trivial return value from the
python code, but slots do not have return values. It is perfectly
reasonable to just pass the exception to sys.excepthook and move on in
this case. Perhaps this is the source of our confusion here--in cases
like QNetworkAccessManager::createRequest, I agree that the most
sensible option is to abort if an exception is raised. Most of the
time, however, python will be invoked either as a slot or as an event
handler, neither of which (usually) has a return value.
What if the criteria is changed such that an uncaught exception only
leads to abort for functions with non-void return values?
I might want an exception for functions that return a boolean as well,
but the consequences of that would have to be considered carefully..
> > At best, this looks to the user like PyQt has caused a segfault
> > (except that even fauthandler will provide no useful information).
> Huh? Except the stacktrace printed by PyQt you mean?
The stack trace is the output of sys.excepthook; that I expected. The
surprise is that the process aborts after the exception--this is the
part that looks like a segmentation fault (in an interactive session,
for example, we would expect to return to the python prompt after the
exception hook; usually only a segfault will kill the process
completely). Very few Python developers, especially existing PyQt
developers, will expect this behavior, and it's very difficult to
determine why the process aborted following the exception, unless you
happen to have come across the incompatibilities note on the pyqt
website. I would recommend at least printing a message explaining why
the process aborted.
More information about the PyQt