]> git.ipfire.org Git - oddments/collecty.git/commitdiff
Replace those complicated wait construct by a efficient Timer class.
authorMichael Tremer <michael.tremer@ipfire.org>
Sat, 4 Aug 2012 17:13:20 +0000 (17:13 +0000)
committerMichael Tremer <michael.tremer@ipfire.org>
Sat, 4 Aug 2012 17:16:43 +0000 (17:16 +0000)
Timer is a low-resolution timeout system that lets us have
long timeouts very energy-efficient and interuptable.

collecty/__init__.py
collecty/plugins/__init__.py
collecty/plugins/base.py

index 5e684f46069a8101f8cf5e9293122f66a8cb2bb5..b7e1f22a802f249129048575f11c6e4c43d33304 100644 (file)
@@ -47,14 +47,13 @@ class Collecty(object):
        # The default interval, when all data is written to disk.
        SUBMIT_INTERVAL = 300
 
-       HEARTBEAT = 2
-
        def __init__(self):
                self.config = configparser.ConfigParser()
                self.instances = []
 
                # Indicates whether this process should be running or not.
                self.running = True
+               self.timer = plugins.Timer(self.SUBMIT_INTERVAL, heartbeat=2)
 
                # Add all automatic plugins.
                self.add_autocreate_plugins()
@@ -110,14 +109,11 @@ class Collecty(object):
                        i.start()
 
                # Regularly submit all data to disk.
-               counter = self.SUBMIT_INTERVAL / self.HEARTBEAT
                while self.running:
-                       time.sleep(self.HEARTBEAT)
-                       counter -= 1
+                       self.timer.reset()
 
-                       if counter == 0:
+                       if self.timer.wait():
                                self.submit_all()
-                               counter = self.SUBMIT_INTERVAL / self.HEARTBEAT
 
                # Wait until all instances are finished.
                while self.instances:
@@ -142,6 +138,8 @@ class Collecty(object):
                log.debug(_("Received shutdown signal"))
 
                self.running = False
+               if self.timer:
+                       self.timer.cancel()
 
                # Propagating shutdown to all threads.
                for i in self.instances:
index a8af8157272bd79739f61ea0de3d935d888c4678..71cf971cf60b765a3281a05b136a2bedc6212135 100644 (file)
@@ -19,6 +19,8 @@
 #                                                                             #
 ###############################################################################
 
+from base import Timer
+
 import cpu
 import loadavg
 import memory
index 472a3a0c7e6d810fbfcea05f55ea175ba856be1e..e85653ea64779ce941debe9f8bb4128e874f3798 100644 (file)
@@ -28,6 +28,34 @@ import time
 from ..constants import *
 from ..i18n import _
 
+class Timer(object):
+       def __init__(self, timeout, heartbeat=1):
+               self.timeout = timeout
+               self.heartbeat = heartbeat
+
+               self.reset()
+
+       def reset(self):
+               # Save start time.
+               self.start = time.time()
+
+               # Has this timer been killed?
+               self.killed = False
+
+       @property
+       def elapsed(self):
+               return time.time() - self.start
+
+       def cancel(self):
+               self.killed = True
+
+       def wait(self):
+               while self.elapsed < self.timeout and not self.killed:
+                       time.sleep(self.heartbeat)
+
+               return self.elapsed > self.timeout
+
+
 class Plugin(threading.Thread):
        # The name of this plugin.
        name = None
@@ -56,10 +84,6 @@ class Plugin(threading.Thread):
                self.log = logging.getLogger("collecty.plugins.%s" % self.name)
                self.log.propagate = 1
 
-               # Keepalive options
-               self.heartbeat = 2
-               self.running = True
-
                self.data = []
 
                # Create the database file.
@@ -68,6 +92,10 @@ class Plugin(threading.Thread):
                # Run some custom initialization.
                self.init()
 
+               # Keepalive options
+               self.running = True
+               self.timer = Timer(self.interval)
+
                self.log.info(_("Successfully initialized."))
        
        def __repr__(self):
@@ -164,19 +192,15 @@ class Plugin(threading.Thread):
        def run(self):
                self.log.debug(_("Started."))
 
-               counter = 0
                while self.running:
-                       if counter == 0:
+                       # Reset the timer.
+                       self.timer.reset()
+
+                       # Wait until the timer has successfully elapsed.
+                       if self.timer.wait():
                                self.log.debug(_("Collecting..."))
                                self._read()
 
-                               self.log.debug(_("Sleeping for %.4fs.") % self.interval)
-
-                               counter = self.interval / self.heartbeat
-
-                       time.sleep(self.heartbeat)
-                       counter -= 1
-
                self._submit()
                self.log.debug(_("Stopped."))
 
@@ -184,6 +208,10 @@ class Plugin(threading.Thread):
                self.log.debug(_("Received shutdown signal."))
                self.running = False
 
+               # Kill any running timers.
+               if self.timer:
+                       self.timer.cancel()
+
        @property
        def now(self):
                """