From e026bec319502a85b76313633f1626689e0664be Mon Sep 17 00:00:00 2001 From: Michele Rastelli Date: Tue, 8 Nov 2022 12:15:55 +0100 Subject: [PATCH 1/2] CodeQL fixes --- .github/workflows/codeql.yml | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/.github/workflows/codeql.yml b/.github/workflows/codeql.yml index 14392e1ac..048635939 100644 --- a/.github/workflows/codeql.yml +++ b/.github/workflows/codeql.yml @@ -29,10 +29,6 @@ jobs: name: Analyze runs-on: ubuntu-latest - defaults: - run: - working-directory: driver - permissions: actions: read contents: read @@ -66,6 +62,7 @@ jobs: # If this step fails, then you should remove it and run the build manually (see below) - name: Autobuild uses: github/codeql-action/autobuild@v2 + working-directory: driver # â„šī¸ Command-line programs to run using the OS shell. # 📚 See https://docs.github.com/en/actions/using-workflows/workflow-syntax-for-github-actions#jobsjob_idstepsrun @@ -79,3 +76,4 @@ jobs: - name: Perform CodeQL Analysis uses: github/codeql-action/analyze@v2 + working-directory: driver From f2f7e44e146de523ea61e2cc198c2da95268fc1d Mon Sep 17 00:00:00 2001 From: Michele Rastelli Date: Tue, 8 Nov 2022 14:11:10 +0100 Subject: [PATCH 2/2] fixed http shutdown --- .../internal/net/ConnectionPoolImpl.java | 6 ++ .../test/java/resilience/retry/RetryTest.java | 11 ++-- .../resilience/shutdown/ShutdownTest.java | 58 +++++++++++++++++++ 3 files changed, 69 insertions(+), 6 deletions(-) create mode 100644 resilience-tests/src/test/java/resilience/shutdown/ShutdownTest.java diff --git a/driver/src/main/java/com/arangodb/internal/net/ConnectionPoolImpl.java b/driver/src/main/java/com/arangodb/internal/net/ConnectionPoolImpl.java index 05cd39b4a..c86f07a47 100644 --- a/driver/src/main/java/com/arangodb/internal/net/ConnectionPoolImpl.java +++ b/driver/src/main/java/com/arangodb/internal/net/ConnectionPoolImpl.java @@ -20,6 +20,7 @@ package com.arangodb.internal.net; +import com.arangodb.ArangoDBException; import com.arangodb.internal.velocystream.internal.VstConnection; import com.arangodb.internal.velocystream.internal.VstConnectionSync; import org.slf4j.Logger; @@ -42,6 +43,7 @@ public class ConnectionPoolImpl implements ConnectionPool { private final ConnectionFactory factory; private int current; private volatile String jwt = null; + private boolean closed = false; public ConnectionPoolImpl(final HostDescription host, final Integer maxConnections, final ConnectionFactory factory) { @@ -62,6 +64,9 @@ public Connection createConnection(final HostDescription host) { @Override public synchronized Connection connection() { + if (closed) { + throw new ArangoDBException("Connection pool already closed!"); + } final Connection connection; @@ -91,6 +96,7 @@ public void setJwt(String jwt) { @Override public synchronized void close() throws IOException { + closed = true; for (final Connection connection : connections) { connection.close(); } diff --git a/resilience-tests/src/test/java/resilience/retry/RetryTest.java b/resilience-tests/src/test/java/resilience/retry/RetryTest.java index 6eb074928..e83f8565d 100644 --- a/resilience-tests/src/test/java/resilience/retry/RetryTest.java +++ b/resilience-tests/src/test/java/resilience/retry/RetryTest.java @@ -33,9 +33,9 @@ class RetryTest extends SingleServerTest { static Stream arangoProvider() { return Stream.of( - dbBuilder().timeout(1_000).useProtocol(Protocol.VST).build(), - dbBuilder().timeout(1_000).useProtocol(Protocol.HTTP_VPACK).build(), - dbBuilder().timeout(1_000).useProtocol(Protocol.HTTP2_VPACK).build() + dbBuilder().useProtocol(Protocol.VST).build(), + dbBuilder().useProtocol(Protocol.HTTP_VPACK).build(), + dbBuilder().useProtocol(Protocol.HTTP2_VPACK).build() ); } @@ -57,9 +57,8 @@ void unreachableHost(ArangoDB arangoDB) { assertThat(thrown.getMessage()).contains("Cannot contact any host"); assertThat(thrown.getCause()).isNotNull(); assertThat(thrown.getCause()).isInstanceOf(ArangoDBMultipleException.class); - ((ArangoDBMultipleException) thrown.getCause()).getExceptions().forEach(e -> { - assertThat(e).isInstanceOf(ConnectException.class); - }); + ((ArangoDBMultipleException) thrown.getCause()).getExceptions().forEach(e -> + assertThat(e).isInstanceOf(ConnectException.class)); } long warnsCount = logs.getLoggedEvents().stream() diff --git a/resilience-tests/src/test/java/resilience/shutdown/ShutdownTest.java b/resilience-tests/src/test/java/resilience/shutdown/ShutdownTest.java new file mode 100644 index 000000000..1a8924196 --- /dev/null +++ b/resilience-tests/src/test/java/resilience/shutdown/ShutdownTest.java @@ -0,0 +1,58 @@ +package resilience.shutdown; + +import com.arangodb.ArangoDB; +import com.arangodb.ArangoDBException; +import com.arangodb.Protocol; +import io.vertx.core.http.HttpClosedException; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; +import resilience.SingleServerTest; + +import java.io.IOException; +import java.util.concurrent.Executors; +import java.util.concurrent.ScheduledExecutorService; +import java.util.concurrent.TimeUnit; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.catchThrowable; +import static org.junit.jupiter.api.Assumptions.assumeTrue; + +/** + * @author Michele Rastelli + */ +class ShutdownTest extends SingleServerTest { + + @ParameterizedTest + @EnumSource(Protocol.class) + void shutdown(Protocol protocol) throws InterruptedException { + ArangoDB arangoDB = dbBuilder() + .useProtocol(protocol) + .build(); + + arangoDB.getVersion(); + arangoDB.shutdown(); + Thread.sleep(1_000); + Throwable thrown = catchThrowable(arangoDB::getVersion); + assertThat(thrown).isInstanceOf(ArangoDBException.class); + assertThat(thrown.getMessage()).contains("closed"); + } + + @ParameterizedTest + @EnumSource(Protocol.class) + void shutdownWithPendingRequests(Protocol protocol) { + assumeTrue(protocol != Protocol.VST); + ArangoDB arangoDB = dbBuilder() + .useProtocol(protocol) + .build(); + + ScheduledExecutorService es = Executors.newSingleThreadScheduledExecutor(); + es.schedule(arangoDB::shutdown, 200, TimeUnit.MILLISECONDS); + Throwable thrown = catchThrowable(() -> arangoDB.db().query("return sleep(1)", Void.class)); + thrown.printStackTrace(); + assertThat(thrown).isInstanceOf(ArangoDBException.class); + assertThat(thrown.getCause()).isInstanceOf(IOException.class); + assertThat(thrown.getCause().getCause()).isInstanceOf(HttpClosedException.class); + es.shutdown(); + } + +}