Repository: curator Updated Branches: refs/heads/CURATOR-126 785e9f6c8 -> a8a3e1475
CURATOR-126 - Added a unit test to reproduce this case. Project: http://git-wip-us.apache.org/repos/asf/curator/repo Commit: http://git-wip-us.apache.org/repos/asf/curator/commit/a8a3e147 Tree: http://git-wip-us.apache.org/repos/asf/curator/tree/a8a3e147 Diff: http://git-wip-us.apache.org/repos/asf/curator/diff/a8a3e147 Branch: refs/heads/CURATOR-126 Commit: a8a3e14755ea69aaa186a40e67173ad7b686d9e3 Parents: 785e9f6 Author: Cameron McKenzie <came...@unico.com.au> Authored: Tue Jul 29 09:28:14 2014 +1000 Committer: Cameron McKenzie <came...@unico.com.au> Committed: Tue Jul 29 09:28:14 2014 +1000 ---------------------------------------------------------------------- .../framework/imps/TestFrameworkBackground.java | 86 ++++++++++++++++++++ 1 file changed, 86 insertions(+) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/curator/blob/a8a3e147/curator-framework/src/test/java/org/apache/curator/framework/imps/TestFrameworkBackground.java ---------------------------------------------------------------------- diff --git a/curator-framework/src/test/java/org/apache/curator/framework/imps/TestFrameworkBackground.java b/curator-framework/src/test/java/org/apache/curator/framework/imps/TestFrameworkBackground.java index 44792d9..f9fea4f 100644 --- a/curator-framework/src/test/java/org/apache/curator/framework/imps/TestFrameworkBackground.java +++ b/curator-framework/src/test/java/org/apache/curator/framework/imps/TestFrameworkBackground.java @@ -20,12 +20,15 @@ package org.apache.curator.framework.imps; import com.google.common.collect.Lists; + import org.apache.curator.test.BaseClassForTests; import org.apache.curator.utils.CloseableUtils; import org.apache.curator.framework.CuratorFramework; import org.apache.curator.framework.CuratorFrameworkFactory; import org.apache.curator.framework.api.BackgroundCallback; import org.apache.curator.framework.api.CuratorEvent; +import org.apache.curator.framework.api.UnhandledErrorListener; +import org.apache.curator.framework.imps.OperationAndData.ErrorCallback; import org.apache.curator.framework.state.ConnectionState; import org.apache.curator.framework.state.ConnectionStateListener; import org.apache.curator.retry.RetryNTimes; @@ -35,10 +38,12 @@ import org.apache.curator.test.Timing; import org.apache.zookeeper.KeeperException.Code; import org.testng.Assert; import org.testng.annotations.Test; + import java.util.Arrays; import java.util.List; import java.util.concurrent.CountDownLatch; import java.util.concurrent.atomic.AtomicBoolean; +import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicLong; import java.util.concurrent.atomic.AtomicReference; @@ -215,4 +220,85 @@ public class TestFrameworkBackground extends BaseClassForTests } } + + /** + * CURATOR-126 + * Shutdown the Curator client while there are still background operations running. + */ + @Test + public void testShutdown() throws Exception + { + final int MAX_CLOSE_WAIT_MS = 5000; + Timing timing = new Timing(); + CuratorFramework client = CuratorFrameworkFactory.builder().connectString(server.getConnectString()).sessionTimeoutMs(timing.session()). + connectionTimeoutMs(timing.connection()).retryPolicy(new RetryOneTime(1)).maxCloseWaitMs(MAX_CLOSE_WAIT_MS).build(); + try + { + client.start(); + + BackgroundCallback callback = new BackgroundCallback() + { + @Override + public void processResult(CuratorFramework client, CuratorEvent event) throws Exception + { + } + }; + + final CountDownLatch operationReadyLatch = new CountDownLatch(1); + + //This gets called just before the operation is run. + ((CuratorFrameworkImpl)client).debugListener = new CuratorFrameworkImpl.DebugBackgroundListener() + { + @Override + public void listen(OperationAndData<?> data) + { + operationReadyLatch.countDown(); + + try { + Thread.sleep(MAX_CLOSE_WAIT_MS / 2); + } catch(InterruptedException e) { + } + } + }; + + Assert.assertTrue(client.getZookeeperClient().blockUntilConnectedOrTimedOut(), "Failed to connect"); + + server.stop(); + + BackgroundOperation<String> background = new BackgroundOperation<String>() + { + + @Override + public void performBackgroundOperation(OperationAndData<String> data) + throws Exception + { + } + }; + + ErrorCallback<String> errorCallback = new ErrorCallback<String>() + { + + @Override + public void retriesExhausted( + OperationAndData<String> operationAndData) + { + } + }; + + OperationAndData<String> operation = new OperationAndData<String>(background, + "thedata", callback, errorCallback, null); + + ((CuratorFrameworkImpl)client).queueOperation(operation); + + operationReadyLatch.await(); + + client.close(); + } + finally + { + CloseableUtils.closeQuietly(client); + } + } + + }