Explorar o código

Clean-up and document the PeriodicTask.is_due method

Ask Solem %!s(int64=15) %!d(string=hai) anos
pai
achega
e138e1c8c3
Modificáronse 1 ficheiros con 29 adicións e 9 borrados
  1. 29 9
      celery/task/base.py

+ 29 - 9
celery/task/base.py

@@ -586,16 +586,36 @@ class PeriodicTask(Task):
         super(PeriodicTask, self).__init__()
 
     def remaining_estimate(self, last_run_at):
-        rem = (last_run_at + self.run_every) - datetime.now()
-        now = False
-        if rem.days == -1:
-            now = True
-            rem = self.run_every
-        return now, rem.seconds + (rem.microseconds / 10e5)
+        return (last_run_at + self.run_every) - datetime.now()
+
+    def timedelta_seconds(self, d):
+        if d.days < 0:
+            return 0
+        return d.days * 86400 + d.seconds + (d.microseconds / 10e5)
 
     def is_due(self, last_run_at):
-        """Returns ``True`` if the task is due.
+        """Returns tuple of two items ``(is_due, next_time_to_run)``,
+        where next time to run is in seconds.
+
+        e.g.
+
+        * ``(True, 20)``, means the task should be run now, and the next
+            time to run is in 20 seconds.
+
+        * ``(False, 12)``, means the task should be run in 12 seconds.
+
+        You can override this to decide the interval at runtime,
+        but keep in mind the value of ``CELERYBEAT_MAX_LOOP_INTERVAL``, which
+        decides the maximum number of seconds celerybeat can sleep between
+        re-checking the periodic task intervals. So if you dynamically change
+        the next run at value, and the max interval is set to 5 minutes, it
+        will take 5 minutes for the change to take effect, so you may
+        consider lowering the value of ``CELERYBEAT_MAX_LOOP_INTERVAL`` if
+        responsiveness if of importance to you.
 
-        You can override this to decide the interval at runtime.
         """
-        return self.remaining_estimate(last_run_at)
+        rem_delta = self.remaining_estimate(last_run_at)
+        rem = self.timedelta_seconds(rem_delta)
+        if rem == 0:
+            return True, self.timedelta_seconds(self.run_every)
+        return False, rem