From 07c26e50dc62ef7157ee8ad7ab7ff1edf9b1c1da Mon Sep 17 00:00:00 2001 From: Adriano Petrich Date: Wed, 6 Jun 2018 16:32:09 +0100 Subject: [PATCH] Make cron-triggers not play catchup Currently if the API is stopped for a length and restarted the crontrigger jobs will have their next execution in the past and will do a catchup running a lot of times. That happens because the next execution is calculated based on the first time it was executed. This change makes it be the next execution time be the max of the calculated time and utcnow so that if the server is lagging we keep uptodate with the calculated next execution times. Change-Id: I05b35261b1adbe17a1b0316eee95da12634c3978 Closes-bug: 1719882 --- mistral/services/periodic.py | 5 ++++- mistral/tests/unit/engine/test_cron_trigger.py | 8 ++++++++ 2 files changed, 12 insertions(+), 1 deletion(-) diff --git a/mistral/services/periodic.py b/mistral/services/periodic.py index d5e2b660b..b10ea50a0 100644 --- a/mistral/services/periodic.py +++ b/mistral/services/periodic.py @@ -12,6 +12,7 @@ # See the License for the specific language governing permissions and # limitations under the License. +import datetime import json from oslo_config import cfg @@ -121,9 +122,11 @@ def advance_cron_trigger(t): delete_trust=False ) else: # if remaining execution = None or > 0. + # In case the we are lagging or if the api stopped for some time + # we use the max of the current time or the next scheduled time. next_time = triggers.get_next_execution_time( t.pattern, - t.next_execution_time + max(datetime.datetime.utcnow(), t.next_execution_time) ) # Update the cron trigger with next execution details diff --git a/mistral/tests/unit/engine/test_cron_trigger.py b/mistral/tests/unit/engine/test_cron_trigger.py index 9089ac65b..5791e0818 100644 --- a/mistral/tests/unit/engine/test_cron_trigger.py +++ b/mistral/tests/unit/engine/test_cron_trigger.py @@ -12,6 +12,7 @@ # See the License for the specific language governing permissions and # limitations under the License. import datetime +import time import mock from oslo_config import cfg @@ -120,7 +121,9 @@ class ProcessCronTriggerTest(base.EngineTestCase): next_trigger = next_triggers[0] next_execution_time_before = next_trigger.next_execution_time + ts_before = datetime.datetime.utcnow() + time.sleep(1) # this is to simulate lagging periodic.process_cron_triggers_v2(None, None) next_triggers = triggers.get_next_cron_triggers() @@ -130,6 +133,11 @@ class ProcessCronTriggerTest(base.EngineTestCase): next_trigger = next_triggers[0] next_execution_time_after = next_trigger.next_execution_time + self.assertGreater( + next_execution_time_after, + ts_before + ) + self.assertNotEqual( next_execution_time_before, next_execution_time_after