/
SharedScheduler.py
82 lines (70 loc) · 2.75 KB
/
SharedScheduler.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
# __BEGIN_LICENSE__
# Copyright (C) 2008-2010 United States Government as represented by
# the Administrator of the National Aeronautics and Space Administration.
# All Rights Reserved.
# __END_LICENSE__
import sched, time, asyncore, sys
from printTraceback import printTraceback
class ExitSchedulerLoop(Exception):
pass
def asyncoreListenWait(delay):
if asyncore.socket_map:
asyncore.poll(delay)
else:
# asyncore.poll() returns immediately if there are no sockets to watch;
# avoid busy loop
time.sleep(delay)
class SchedulerPlus(sched.scheduler):
def __init__(self, timefunc, delayfunc):
def _delayPlus(delay):
return self.runActionCatchExceptions(delayfunc, (delay,))
sched.scheduler.__init__(self, timefunc, _delayPlus)
self._collectResponseHandlers = []
def runActionCatchExceptions(self, action, args):
try:
action(*args)
if self._collectResponseHandlers:
response = self._collectResponseHandlers[-1]()
if response != None:
raise ExitSchedulerLoop(response)
except ExitSchedulerLoop:
# pass this on so we exit the scheduler loop
raise
except:
printTraceback()
caughtException = True
else:
caughtException = False
return caughtException
def enterSimple(self, delay, action, argument=(), priority=1):
def _handler(*args):
#print 'enterSimple handler: args=%s' % str(args)
self.runActionCatchExceptions(action, args)
return self.enter(delay, priority, _handler, argument)
def cancelSimple(self, event):
return self.cancel(event)
def enterPeriodic(self, period, action, argument=(), priority=1):
event = [None]
def _handler(*args):
#print 'enterPeriodic handler: args=%s' % str(args)
caughtException = self.runActionCatchExceptions(action, args)
if not caughtException:
event[0] = self.enterSimple(period, _handler, argument, priority)
event[0] = self.enterSimple(period, _handler, argument, priority)
return event
def cancelPeriodic(self, event):
return self.cancel(event[0])
def runForever(self):
try:
self._exitNow = False
while 1:
self.run()
self.delayfunc(3600)
except ExitSchedulerLoop, args:
return args[0]
def waitForResponse(self, collectResponseHandler):
self._collectResponseHandlers.append(collectResponseHandler)
result = self.runForever()
self._collectResponseHandlers.pop(-1)
return result
scheduler = SchedulerPlus(time.time, asyncoreListenWait)