Mercurial > cosocket
changeset 18:69efb6cdc127
Added some error-handling code, though the channel code is raising exceptions in it at the moment I think.
author | Atul Varma <varmaa@toolness.com> |
---|---|
date | Sun, 19 Apr 2009 21:45:46 -0700 |
parents | 7b652e2ac62e |
children | 264e243e396c |
files | cosocket.py |
diffstat | 1 files changed, 37 insertions(+), 3 deletions(-) [+] |
line wrap: on
line diff
--- a/cosocket.py Sun Apr 19 20:29:17 2009 -0700 +++ b/cosocket.py Sun Apr 19 21:45:46 2009 -0700 @@ -5,6 +5,7 @@ import asyncore import asynchat import types +import traceback class _AsyncChatCoroutineDispatcher(asynchat.async_chat): def __init__(self, coroutine, conn = None): @@ -16,15 +17,25 @@ if conn: self.return_from_yield() - def return_from_yield(self, message = None): + def return_from_yield(self, message = None, exception = None): try: - instruction = self.__coroutine.send(message) + if exception: + instruction = self.__coroutine.throw(exception) + else: + instruction = self.__coroutine.send(message) except StopIteration: if self.__coroutine_stack: self.__coroutine = self.__coroutine_stack.pop() self.return_from_yield() else: - self.close() + self.__coroutine = None + self.handle_close() + except Exception, e: + if self.__coroutine_stack: + self.__coroutine = self.__coroutine_stack.pop() + self.return_from_yield(exception = e) + else: + self.handle_error() else: if type(instruction) == types.GeneratorType: self.__coroutine_stack.append(self.__coroutine) @@ -33,6 +44,29 @@ else: instruction.execute(self) + def __close_coroutine(self, coroutine): + try: + coroutine.close() + except Exception: + self.log_info(traceback.format_exc(), 'error') + + def handle_close(self): + if self.__coroutine: + # Pass an exception back into the coroutine to kick + # it out of whatever yielding state it's in. + self.__close_coroutine(self.__coroutine) + self.__coroutine = None + while self.__coroutine_stack: + self.__close_coroutine(self.__coroutine_stack.pop()) + self.close() + + def log_info(self, message, type='info'): + # TODO: Use the logging module here. + print '%s: %s' % (type, message) + + def handle_error(self): + self.log_info(traceback.format_exc(), 'error') + def handle_connect(self): self.return_from_yield()