From 7b967e295f7eca8b0b714e13a4f8dd5ef5659b97 Mon Sep 17 00:00:00 2001 From: Tim Renouf Date: Tue, 4 Oct 2016 17:46:10 +0100 Subject: [PATCH 1/2] Fixed explicit connect after connection has disconnected https://github.com/ably/ably-java/issues/167 says that, after a disconnect caused by a network outage, then waiting long enough for the connection to go disconnected state and the channels to be detached, an explicit AblyRealtime.connection.connect() is not immediately actioned. Instead it does not connect until up to a couple of minutes later. It looks like the condition is incorrect in ConnectionManager.connect() to see if a connection attempt is already underway, so the explicit connect does not do anything. Instead it waits until the next time it would have attempted a reconnect anyway. Fixed. Also fixed so that the connect happens even if there is a connection thread already started. --- .../main/java/io/ably/lib/transport/ConnectionManager.java | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/lib/src/main/java/io/ably/lib/transport/ConnectionManager.java b/lib/src/main/java/io/ably/lib/transport/ConnectionManager.java index 8482ce25e..c94aca507 100644 --- a/lib/src/main/java/io/ably/lib/transport/ConnectionManager.java +++ b/lib/src/main/java/io/ably/lib/transport/ConnectionManager.java @@ -162,10 +162,11 @@ public String getHost() { public void connect() { boolean connectionExist = state.state == ConnectionState.connected; - boolean connectionAttemptAvailable = (requestedState != null && requestedState.state != ConnectionState.connecting) || + boolean connectionAttemptInProgress = (requestedState != null && requestedState.state == ConnectionState.connecting) || state.state == ConnectionState.connecting; - if(!connectionExist && !connectionAttemptAvailable && startThread()) { + if(!connectionExist && !connectionAttemptInProgress) { + startThread(); // Start thread if not already started. requestState(ConnectionState.connecting); } } From ea369a309b3f25eaa55c7d31dada9d3438216656 Mon Sep 17 00:00:00 2001 From: Tim Renouf Date: Tue, 4 Oct 2016 19:43:53 +0100 Subject: [PATCH 2/2] RealtimeConnectFailTest.connect_while_disconnected new test This tests the fix for https://github.com/ably/ably-java/issues/167 --- .../realtime/RealtimeConnectFailTest.java | 32 +++++++++++++++++++ 1 file changed, 32 insertions(+) diff --git a/lib/src/test/java/io/ably/lib/test/realtime/RealtimeConnectFailTest.java b/lib/src/test/java/io/ably/lib/test/realtime/RealtimeConnectFailTest.java index cf9377064..b80e9ca1f 100644 --- a/lib/src/test/java/io/ably/lib/test/realtime/RealtimeConnectFailTest.java +++ b/lib/src/test/java/io/ably/lib/test/realtime/RealtimeConnectFailTest.java @@ -124,6 +124,38 @@ public void connect_fail_suspended() { } } + /** + * Verify that the connection in the disconnected state (after attempts to + * connect to a non-existent ws host) allows an immediate explicit connect + * attempt, instead of ignoring the explicit connect and waiting till the + * next scheduled retry. + */ + @Test + public void connect_while_disconnected() { + try { + TestVars testVars = Setup.getTestVars(); + ClientOptions opts = testVars.createOptions(testVars.keys[0].keyStr); + opts.realtimeHost = "non.existent.host"; + AblyRealtime ably = new AblyRealtime(opts); + ConnectionWaiter connectionWaiter = new ConnectionWaiter(ably.connection); + + connectionWaiter.waitFor(ConnectionState.disconnected); + assertEquals("Verify disconnected state is reached", ConnectionState.disconnected, ably.connection.state); + + long before = System.currentTimeMillis(); + ably.connection.connect(); + connectionWaiter.waitFor(ConnectionState.connecting); + assertTrue("Verify explicit connect is actioned immediately", System.currentTimeMillis() - before < 1000L); + + ably.close(); + connectionWaiter.waitFor(ConnectionState.closed); + assertEquals("Verify closed state is reached", ConnectionState.closed, ably.connection.state); + } catch (AblyException e) { + e.printStackTrace(); + fail("init0: Unexpected exception instantiating library"); + } + } + /** * Verify that the connection enters the disconnected state, after a token * used for successful connection expires