From 027e91c980eb581ca91cc1366390f68a9527f5eb Mon Sep 17 00:00:00 2001 From: Zane Bitter Date: Fri, 31 May 2013 21:34:36 +0200 Subject: [PATCH] scheduler: Fix inifinite loop for no-wait tasks When a task run by a DependencyTaskGroup completed immediately (i.e. it was marked as done right after calling start()), the corresponding entry in the dependency graph was never removed. As a result the DependencyTaskGroup would continue running forever (or until it timed out). Fixes bug #1186389 Change-Id: I9715b54a61d1c3adc22403bc39f8673306bffead --- heat/engine/scheduler.py | 4 ++-- heat/tests/test_scheduler.py | 8 +++++++- 2 files changed, 9 insertions(+), 3 deletions(-) diff --git a/heat/engine/scheduler.py b/heat/engine/scheduler.py index a553c8e4..7ad19a68 100644 --- a/heat/engine/scheduler.py +++ b/heat/engine/scheduler.py @@ -301,8 +301,8 @@ class DependencyTaskGroup(object): Iterate over all subtasks that are currently running - i.e. they have been started but have not yet completed. """ - return itertools.ifilter(lambda (k, r): r and r.started(), - self._runners.iteritems()) + running = lambda (k, r): k in self._graph and r.started() + return itertools.ifilter(running, self._runners.iteritems()) class PollingTaskGroup(object): diff --git a/heat/tests/test_scheduler.py b/heat/tests/test_scheduler.py index 6f829393..f331085b 100644 --- a/heat/tests/test_scheduler.py +++ b/heat/tests/test_scheduler.py @@ -164,7 +164,7 @@ class DependencyTaskGroupTest(mox.MoxTestBase): @contextlib.contextmanager def _dep_test(self, *edges): - dummy = DummyTask() + dummy = DummyTask(getattr(self, 'steps', 3)) class TaskMaker(object): def __init__(self, name): @@ -188,6 +188,12 @@ class DependencyTaskGroupTest(mox.MoxTestBase): scheduler.TaskRunner(tg)(wait_time=None) self.mox.VerifyAll() + def test_no_steps(self): + self.steps = 0 + self.mox.StubOutWithMock(scheduler.TaskRunner, '_sleep') + with self._dep_test(('second', 'first')) as dummy: + scheduler.TaskRunner._sleep(None).AndReturn(None) + def test_single_node(self): with self._dep_test(('only', None)) as dummy: dummy.do_step(1, 'only').AndReturn(None) -- 2.45.2