PlexKodiConnect/resources/lib/plexnet/signalslot/contrib/task/task.py

76 lines
1.9 KiB
Python
Raw Normal View History

2018-09-30 21:16:17 +10:00
import sys
import eventlet
import contexter
import six
class Task(object):
@classmethod
def get_or_create(cls, signal, kwargs=None, logger=None):
if not hasattr(cls, '_registry'):
cls._registry = []
task = cls(signal, kwargs, logger=logger)
if task not in cls._registry:
cls._registry.append(task)
return cls._registry[cls._registry.index(task)]
def __init__(self, signal, kwargs=None, logger=None):
self.signal = signal
self.kwargs = kwargs or {}
self.logger = logger
self.failures = 0
self.task_semaphore = eventlet.semaphore.BoundedSemaphore(1)
def __call__(self, semaphores=None):
semaphores = semaphores or []
with contexter.Contexter(self.task_semaphore, *semaphores):
result = self._do()
if result:
self.failures = 0
else:
self.failures += 1
return result
def _do(self):
try:
self._emit()
except Exception:
self._exception(*sys.exc_info())
return False
else:
self._completed()
return True
finally:
self._clean()
def _clean(self):
pass
def _completed(self):
if self.logger:
self.logger.info('[%s] Completed' % self)
def _exception(self, e_type, e_value, e_traceback):
if self.logger:
self.logger.exception('[%s] Raised exception: %s' % (
self, e_value))
else:
six.reraise(e_type, e_value, e_traceback)
def _emit(self):
if self.logger:
self.logger.info('[%s] Running' % self)
self.signal.emit(**self.kwargs)
def __eq__(self, other):
return (self.signal == other.signal and self.kwargs == other.kwargs)
def __str__(self):
return '%s: %s' % (self.signal.__class__.__name__, self.kwargs)