On May 12, 2009, at 10:47 AM, Phil Christensen wrote:
I don't know if I agree with the need for such a feature (that is,
deferred __init__ usage), but it was a very interesting coding
challenge I wanted to take a whack at. I *think* I might have found a
solution, but I don't know if it falls under the heading of "decorator
abuse" ;-)

Ugh, that code got fairly mangled by my email client. Here's an attachment.

-phil

from twisted.internet import defer, reactor
from twisted.enterprise import adbapi

def deferredInit(func):
    if not(hasattr(deferredInit, 'waiting')):
        deferredInit.waiting = {}
    
    def _deferredInit(self, *args, **kwargs):
        waiting_for_init = self in deferredInit.waiting
        
        if not(waiting_for_init):
            if(hasattr(self, 'initDeferred')):
                deferredInit.waiting[self] = self.initDeferred
            else:
                raise RuntimeError("%s doesn't seem to support deferred instantion." % self.__class__.__name__)
        
        def _finish(result):
            del deferredInit.waiting[self]
            return func(self, *args, **kwargs)
        
        def _finish_error(failure):
            print '_finish_err: %s' % failure
        
        resultDeferred = defer.Deferred()
        resultDeferred.addCallbacks(_finish, _finish_error)
        
        deferredInit.waiting[self].addCallbacks(resultDeferred.callback, resultDeferred.errback)
        
        return resultDeferred
    
    return _deferredInit

class TestDeferredInit(object):
    def __init__(self):
        self.pool = adbapi.ConnectionPool("MySQLdb", 'localhost', 'modu', 'modu')
        self.initDeferred = self.pool.runQuery("SELECT 'it worked';")
        def _finish_init(msg):
            self.msg = msg
        def _finish_init_error(failure):
            print '_finish_init_err: %s' % failure
        self.initDeferred.addCallbacks(_finish_init, _finish_init_error)
    
    @deferredInit
    def query(self):
        return self.msg

if(__name__ == '__main__'):
    def _print(msg):
        print msg
        reactor.stop()
    
    def _print_error(failure):
        print '_print_err: %s' % failure
    
    test = TestDeferredInit()
    
    d = test.query()
    d.addCallbacks(_print, _print_error)
    
    reactor.run()

_______________________________________________
Twisted-Python mailing list
Twisted-Python@twistedmatrix.com
http://twistedmatrix.com/cgi-bin/mailman/listinfo/twisted-python

Reply via email to