You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
80 lines
2.6 KiB
Python
80 lines
2.6 KiB
Python
from queue import Queue
|
|
|
|
|
|
class IntervalTaskMaster ():
|
|
def __init__(self, socketio):
|
|
self.socketio = socketio
|
|
self.tasks_by_id = {}
|
|
self.tasks_id = 0
|
|
self.queue = Queue()
|
|
|
|
def start (self):
|
|
self.socketio.start_background_task(self.background_task)
|
|
|
|
def background_task(self):
|
|
st = 0
|
|
while True:
|
|
# print (f"IntervalTaskMaster is running with {len(self.tasks_by_id)} pending tasks")
|
|
# Add any items in the queue
|
|
while not self.queue.empty():
|
|
task_id, callback, time, interval = self.queue.get()
|
|
print (f"CREATING TASK {task_id} interval:{interval}")
|
|
self.tasks_by_id[task_id] = Task(task_id, callback, time, interval)
|
|
|
|
remove_intervals = []
|
|
for task_id, task in self.tasks_by_id.items():
|
|
print (f"servicing task {task_id}")
|
|
ran_task = task.service(st)
|
|
if not task.interval and ran_task:
|
|
remove_intervals.append(task_id)
|
|
for task_id in remove_intervals:
|
|
print (f"deleting task {task_id}")
|
|
del self.tasks_by_id[task_id]
|
|
st = self.calc_current_sleep_time_ms()
|
|
# print (f"taskmaster sleeping {st}")
|
|
self.socketio.sleep(st/1000)
|
|
|
|
def calc_current_sleep_time_ms(self):
|
|
min_time = None
|
|
for task in self.tasks_by_id.values():
|
|
if min_time == None or task.time < min_time:
|
|
min_time = task.time
|
|
if min_time is None:
|
|
return 1000
|
|
else:
|
|
return min(10000, min_time / 2)
|
|
|
|
def setTimeout (self, callback, time, interval=False):
|
|
task_id = self.tasks_id
|
|
self.tasks_id += 1
|
|
self.queue.put((task_id, callback, time, interval))
|
|
return task_id
|
|
|
|
def clearTimeout (self, task_id):
|
|
try:
|
|
del self.tasks_by_id[task_id]
|
|
return True
|
|
except KeyError:
|
|
pass
|
|
|
|
def setInterval(self, callback, time):
|
|
return self.setTimeout(callback, time, True)
|
|
|
|
def clearInterval(self, task_id):
|
|
return self.clearTimeout(task_id)
|
|
|
|
class Task ():
|
|
def __init__(self, task_id, callback, time, interval=False):
|
|
self.task_id = task_id
|
|
self.callback = callback
|
|
self.time = time
|
|
self.interval = interval
|
|
self.current_timer = time
|
|
|
|
def service (self, elapsed_time):
|
|
self.current_timer -= elapsed_time
|
|
if self.current_timer <= 0:
|
|
self.current_timer = 0
|
|
self.callback()
|
|
return True
|