BROOKLYN-242: fix race in BasicTest.get() Project: http://git-wip-us.apache.org/repos/asf/brooklyn-server/repo Commit: http://git-wip-us.apache.org/repos/asf/brooklyn-server/commit/3df2b8b4 Tree: http://git-wip-us.apache.org/repos/asf/brooklyn-server/tree/3df2b8b4 Diff: http://git-wip-us.apache.org/repos/asf/brooklyn-server/diff/3df2b8b4
Branch: refs/heads/master Commit: 3df2b8b4c131eedd889a319a8ba1f03cfe32e547 Parents: 0b9682b Author: Aled Sage <[email protected]> Authored: Tue Mar 22 12:44:11 2016 +0000 Committer: Aled Sage <[email protected]> Committed: Tue Mar 22 12:44:11 2016 +0000 ---------------------------------------------------------------------- .../brooklyn/util/core/task/BasicTask.java | 11 +++++++- .../core/effector/EffectorBasicTest.java | 29 ++++++++++++++++++++ 2 files changed, 39 insertions(+), 1 deletion(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/brooklyn-server/blob/3df2b8b4/core/src/main/java/org/apache/brooklyn/util/core/task/BasicTask.java ---------------------------------------------------------------------- diff --git a/core/src/main/java/org/apache/brooklyn/util/core/task/BasicTask.java b/core/src/main/java/org/apache/brooklyn/util/core/task/BasicTask.java index efd3001..410ba12 100644 --- a/core/src/main/java/org/apache/brooklyn/util/core/task/BasicTask.java +++ b/core/src/main/java/org/apache/brooklyn/util/core/task/BasicTask.java @@ -451,7 +451,16 @@ public class BasicTask<T> implements TaskInternal<T> { } Long remaining = end==null ? null : end - System.currentTimeMillis(); if (isDone()) { - return internalFuture.get(1, TimeUnit.MILLISECONDS); + // Don't just call internalFuture.get(1ms) - see comment in isDone() about setting of endTimeUtc, + // and see BROOKLYN-242. + if (internalFuture == null) { + assert cancelled: "task="+this+"; endTimeUtc="+endTimeUtc+"; cancelled="+cancelled+"; isDone=true; null internal future"; + throw new CancellationException(); + } else if (remaining == null) { + return internalFuture.get(); + } else { + return internalFuture.get(Math.max(remaining, 1000), TimeUnit.MILLISECONDS); + } } else if (remaining == null) { return internalFuture.get(); } else if (remaining > 0) { http://git-wip-us.apache.org/repos/asf/brooklyn-server/blob/3df2b8b4/core/src/test/java/org/apache/brooklyn/core/effector/EffectorBasicTest.java ---------------------------------------------------------------------- diff --git a/core/src/test/java/org/apache/brooklyn/core/effector/EffectorBasicTest.java b/core/src/test/java/org/apache/brooklyn/core/effector/EffectorBasicTest.java index 05b3a10..8af533f 100644 --- a/core/src/test/java/org/apache/brooklyn/core/effector/EffectorBasicTest.java +++ b/core/src/test/java/org/apache/brooklyn/core/effector/EffectorBasicTest.java @@ -18,6 +18,8 @@ */ package org.apache.brooklyn.core.effector; +import static org.testng.Assert.assertEquals; + import java.util.List; import java.util.concurrent.Callable; @@ -25,6 +27,7 @@ import org.apache.brooklyn.api.entity.EntitySpec; import org.apache.brooklyn.api.mgmt.HasTaskChildren; import org.apache.brooklyn.api.mgmt.Task; import org.apache.brooklyn.core.entity.Entities; +import org.apache.brooklyn.core.entity.StartableApplication; import org.apache.brooklyn.core.entity.trait.FailingEntity; import org.apache.brooklyn.core.entity.trait.Startable; import org.apache.brooklyn.core.location.SimulatedLocation; @@ -36,11 +39,13 @@ import org.apache.brooklyn.util.collections.MutableMap; import org.apache.brooklyn.util.core.task.Tasks; import org.apache.brooklyn.util.exceptions.Exceptions; import org.apache.brooklyn.util.text.Strings; +import org.apache.brooklyn.util.time.Duration; import org.testng.Assert; import org.testng.annotations.BeforeMethod; import org.testng.annotations.Test; import com.google.common.collect.ImmutableList; +import com.google.common.collect.Lists; public class EffectorBasicTest extends BrooklynAppUnitTestSupport { @@ -92,6 +97,30 @@ public class EffectorBasicTest extends BrooklynAppUnitTestSupport { Assert.assertTrue(starting.getTags().contains(ManagementContextInternal.EFFECTOR_TAG)); } + @Test + public void testInvokeEffectorListWithEmpty() throws Exception{ + Entities.invokeEffectorList(app, ImmutableList.<StartableApplication>of(), Startable.STOP).get(Duration.THIRTY_SECONDS); + } + + @Test + public void testInvokeEffectorList() throws Exception{ + List<TestEntity> entities = Lists.newArrayList(); + for (int i = 0; i < 10; i++) { + entities.add(app.addChild(EntitySpec.create(TestEntity.class))); + } + Entities.invokeEffectorList(app, entities, Startable.STOP).get(Duration.THIRTY_SECONDS); + for (TestEntity entity : entities) { + assertEquals(entity.getCallHistory(), ImmutableList.of("stop")); + } + } + + @Test(expectedExceptions=IllegalStateException.class, expectedExceptionsMessageRegExp=".*no longer managed.*") + public void testInvokeEffectorListWithEmptyUsingUnmanagedContext() throws Exception{ + TestEntity entity = app.addChild(EntitySpec.create(TestEntity.class)); + Entities.unmanage(entity); + Entities.invokeEffectorList(entity, ImmutableList.<StartableApplication>of(), Startable.STOP).get(Duration.THIRTY_SECONDS); + } + // check various failure situations private FailingEntity createFailingEntity() {
