So I am scheduling a callback using
ioloop.IOLoop.instance().add_timeout(time, callback_func)
But my callback_func
may throw Exception
which I want to catch.
Tried whats suggested in this answer but doesn't seem to work. Or maybe I am not doing it the right way. Any help on this would be great.
Code is somewhat like this:
start.py
class Start:
# ... other methods ...
@staticmethod
def initialize():
OtherClass.initialize()
def main():
Start.initialize()
if __name__ == "__main__":
main()
ioloop.IOLoop.instance().start()
other_class.py
class OtherClass:
@staticmethod
def initialize():
ioloop.IOLoop.instance().add_timeout(time, callback_func)
@staticmethod
def callback_func():
# Need to catch any exception which occurs here.
If the callback_func
is your own code, then by far the simplest way to catch all exceptions there is to simply wrap the whole function body in try / except:
@staticmethod
def callback_func():
try:
# ... your code ...
except Exception as exc:
# handle it
It's simple and everyone who reads your code will understand it, no surprises.
If you want to do something exotic and Tornado-specific, use an ExceptionStackContext:
from tornado import ioloop
from tornado.stack_context import ExceptionStackContext
class OtherClass:
@staticmethod
def initialize():
ioloop.IOLoop.instance().add_timeout(1, OtherClass.callback_func)
@staticmethod
def callback_func():
# Need to catch any exception which occurs here.
1 / 0
class Start:
# ... other methods ...
@staticmethod
def initialize():
with ExceptionStackContext(Start.handler):
OtherClass.initialize()
@staticmethod
def handler(exc_type, exc_value, exc_traceback):
print("Caught %r in Handler" % exc_type)
return True # Tell Tornado that we handled it.
def main():
Start.initialize()
if __name__ == "__main__":
main()
ioloop.IOLoop.instance().start()
Best of all, use coroutines instead of callbacks. Coroutines are as efficient as callbacks, but give you regular Python exception handling semantics. See my article Refactoring Tornado Coroutines and the Tornado guide.