clear interrupt if evaluation a (nested) ImmediateSupplier
Project: http://git-wip-us.apache.org/repos/asf/brooklyn-server/repo Commit: http://git-wip-us.apache.org/repos/asf/brooklyn-server/commit/d214ca99 Tree: http://git-wip-us.apache.org/repos/asf/brooklyn-server/tree/d214ca99 Diff: http://git-wip-us.apache.org/repos/asf/brooklyn-server/diff/d214ca99 Branch: refs/heads/master Commit: d214ca99a865707db6d82b5f843c8a921657c886 Parents: ed81635 Author: Alex Heneveld <[email protected]> Authored: Tue Mar 7 15:21:17 2017 +0000 Committer: Alex Heneveld <[email protected]> Committed: Wed Mar 8 09:30:28 2017 +0000 ---------------------------------------------------------------------- .../util/core/task/BasicExecutionContext.java | 9 +++- .../brooklyn/core/entity/EntityConfigTest.java | 57 +++++++++++++------- 2 files changed, 47 insertions(+), 19 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/brooklyn-server/blob/d214ca99/core/src/main/java/org/apache/brooklyn/util/core/task/BasicExecutionContext.java ---------------------------------------------------------------------- diff --git a/core/src/main/java/org/apache/brooklyn/util/core/task/BasicExecutionContext.java b/core/src/main/java/org/apache/brooklyn/util/core/task/BasicExecutionContext.java index f35a68a..6bccf10 100644 --- a/core/src/main/java/org/apache/brooklyn/util/core/task/BasicExecutionContext.java +++ b/core/src/main/java/org/apache/brooklyn/util/core/task/BasicExecutionContext.java @@ -140,7 +140,14 @@ public class BasicExecutionContext extends AbstractExecutionContext { if (!(callableOrSupplier instanceof ImmediateSupplier)) { callableOrSupplier = InterruptingImmediateSupplier.of(callableOrSupplier); } - return ((ImmediateSupplier<T>)callableOrSupplier).getImmediately(); + boolean wasAlreadyInterrupted = Thread.interrupted(); + try { + return ((ImmediateSupplier<T>)callableOrSupplier).getImmediately(); + } finally { + if (wasAlreadyInterrupted) { + Thread.currentThread().interrupt(); + } + } } finally { BasicExecutionManager.getPerThreadCurrentTask().set(previousTask); http://git-wip-us.apache.org/repos/asf/brooklyn-server/blob/d214ca99/core/src/test/java/org/apache/brooklyn/core/entity/EntityConfigTest.java ---------------------------------------------------------------------- diff --git a/core/src/test/java/org/apache/brooklyn/core/entity/EntityConfigTest.java b/core/src/test/java/org/apache/brooklyn/core/entity/EntityConfigTest.java index c551ba6..b583b1e 100644 --- a/core/src/test/java/org/apache/brooklyn/core/entity/EntityConfigTest.java +++ b/core/src/test/java/org/apache/brooklyn/core/entity/EntityConfigTest.java @@ -303,8 +303,13 @@ public class EntityConfigTest extends BrooklynAppUnitTestSupport { return this; } - protected ConfigNonBlockingFixture usingImmediateSupplier() { - blockingVal = immediateSupplier(); + protected ConfigNonBlockingFixture usingImmediateSupplierNoSleep() { + blockingVal = immediateSupplier(false); + return this; + } + + protected ConfigNonBlockingFixture usingImmediateSupplierWithSleep() { + blockingVal = immediateSupplier(true); return this; } @@ -344,24 +349,18 @@ public class EntityConfigTest extends BrooklynAppUnitTestSupport { }; } - private DeferredSupplier<String> immediateSupplier() { + private DeferredSupplier<String> immediateSupplier(final boolean withSleep) { class DeferredImmediateSupplier implements DeferredSupplier<String>, ImmediateSupplier<String> { @Override public Maybe<String> getImmediately() { try { - // Do a blocking operation (which would cause interrupt, if called in - // InterruptingImmediateSupplier). This is to simulate use-cases like - // use of `$brooklyn:external("vault", "aws.secretKey")`, which is not - // blocked by other Brooklyn tasks, but will do IO operations. - Thread.sleep(1); + sleepIfNeeded(); log.trace("acquiring"); if (latch.tryAcquire()) { latch.release(); return Maybe.of("myval"); } else { - // TODO After Alex's changes in PR #565, use: - // Maybe.absent(new ImmediateSupplier.ImmediateValueNotAvailableException())); - return Maybe.absent(); + return Maybe.absent(new ImmediateSupplier.ImmediateValueNotAvailableException()); } } catch (InterruptedException e) { log.trace("interrupted"); @@ -370,7 +369,7 @@ public class EntityConfigTest extends BrooklynAppUnitTestSupport { } @Override public String get() { try { - Thread.sleep(1); // See explanation in getImmediately() + sleepIfNeeded(); log.trace("acquiring"); if (!latch.tryAcquire()) latch.acquire(); latch.release(); @@ -381,6 +380,20 @@ public class EntityConfigTest extends BrooklynAppUnitTestSupport { } return "myval"; } + private void sleepIfNeeded() throws InterruptedException { + if (withSleep) { + try { + // Do a blocking operation (which would cause interrupt, if called in + // InterruptingImmediateSupplier). This is to simulate use-cases like + // use of `$brooklyn:external("vault", "aws.secretKey")`, which is not + // blocked by other Brooklyn tasks, but will do IO operations. + Thread.sleep(1); + } catch (InterruptedException e) { + log.debug("Sleep was interrupted during eval (expected in many cases)", e); + throw Exceptions.propagate(e); + } + } + } } return new DeferredImmediateSupplier(); } @@ -487,7 +500,7 @@ public class EntityConfigTest extends BrooklynAppUnitTestSupport { new ConfigNonBlockingFixture().usingDeferredSupplier().runGetConfigNonBlockingInMap(); } - @Test // fast + @Test public void testGetInterruptingImmediateSupplierNonBlockingKey() throws Exception { new ConfigNonBlockingFixture().usingInterruptingImmediateSupplier().runGetConfigNonBlockingInKey(); } @@ -496,13 +509,21 @@ public class EntityConfigTest extends BrooklynAppUnitTestSupport { new ConfigNonBlockingFixture().usingInterruptingImmediateSupplier().runGetConfigNonBlockingInMap(); } - @Test // fast - public void testGetImmediateSupplierNonBlockingKey() throws Exception { - new ConfigNonBlockingFixture().usingImmediateSupplier().runGetConfigNonBlockingInKey(); + @Test + public void testGetImmediateSupplierNoSleepNonBlockingKey() throws Exception { + new ConfigNonBlockingFixture().usingImmediateSupplierNoSleep().runGetConfigNonBlockingInKey(); + } + @Test + public void testGetImmediateSupplierNoSleepNonBlockingMap() throws Exception { + new ConfigNonBlockingFixture().usingImmediateSupplierNoSleep().runGetConfigNonBlockingInMap(); + } + @Test + public void testGetImmediateSupplierWithSleepNonBlockingKey() throws Exception { + new ConfigNonBlockingFixture().usingImmediateSupplierWithSleep().runGetConfigNonBlockingInKey(); } @Test - public void testGetImmediateSupplierNonBlockingMap() throws Exception { - new ConfigNonBlockingFixture().usingImmediateSupplier().runGetConfigNonBlockingInMap(); + public void testGetImmediateSupplierWithSleepNonBlockingMap() throws Exception { + new ConfigNonBlockingFixture().usingImmediateSupplierWithSleep().runGetConfigNonBlockingInMap(); } @Test
