[Zope-dev] thread restrictions?

Robin Becker robin@jessikat.demon.co.uk
Fri, 23 Jul 1999 02:53:51 +0100


Are there any restrictions on using threads in ExternalMethods I am trying to figure
out why my cpu usage goes to 100% after calling the function TGA_CALC below as an
ExternalMethod. The OrderedJobs thingy is intended to arbitrate a first come first
served policy for my cpu hog calculations which being memory intensive as well I want
only one job ever to be initialised and running. 

#TZGA.py proxy for the real calculation
from DateTime import DateTime
from OrderedJobs import OrderedJobs
from Queue import Full
_Jobs=OrderedJobs()

def     _TGA_RUN():
        for i in xrange(1000):
                t=DateTime('GMT').rfc822()
        return t

def TGA_CALC():
        global _Jobs
        try:
                return _Jobs.add(_TGA_RUN,args=(),kwargs={})
        except Full:
                raise "couldn't add job "
##########################################

##### the OrderedJobs module
'''
Module to implement ordered locking
'''
from thread import *
from Queue import Queue, Full

class _Item:
        def __init__(self,func=None,args=(),kwargs={}):
                self.args=args
                self.kwargs=kwargs
                self.func=func
                self.lock=allocate_lock()

class OrderedJobs:
        def __init__(self,maxsize=5):
                self.Q=Queue(maxsize)
                self.serve=1
                self.T=start_new_thread(self.run,())

        def run(self):
                while self.serve:
                        if not self.Q.empty():
                                item=self.Q.get(0)
                                if item.func:
                                        item.result=apply(item.func,
                                                    item.args,item.kwargs)
                                else:
                                        item.result=None
                                item.lock.release()

        def add(self,func,args=(),kwargs={}):
                if self.Q.full(): raise Full
                item=_Item(func,args,kwargs)
                item.lock.acquire()
                self.Q.put(item)
                item.lock.acquire()
                item.lock.release()
                return item.result

if __name__=='__main__':
        import time
        def testJob(n,delay):
                print 'starting testJob ',n, delay
                time.sleep(delay)
                print 'finished testJob ',n
                return None
        def addJob(i,delay):
                print 'adding job',i
                try:
                        Q.add(testJob,(i,3.7))
                except Full:
                        print "couldn't add job ",i

        Q=OrderedJobs()
        for i in range(1,18):
                start_new_thread(addJob,(i,3.7))
                time.sleep(0.7)
###############################
-- 
Robin Becker