Search in sources :

Example 1 with SpeculativeExecutionPolicy

use of com.datastax.oss.driver.api.core.specex.SpeculativeExecutionPolicy in project java-driver by datastax.

the class CqlRequestHandlerSpeculativeExecutionTest method should_fail_if_no_more_nodes_and_initial_execution_is_last.

@Test
@UseDataProvider("idempotentConfig")
public void should_fail_if_no_more_nodes_and_initial_execution_is_last(boolean defaultIdempotence, Statement<?> statement) throws Exception {
    RequestHandlerTestHarness.Builder harnessBuilder = RequestHandlerTestHarness.builder().withDefaultIdempotence(defaultIdempotence);
    PoolBehavior node1Behavior = harnessBuilder.customBehavior(node1);
    harnessBuilder.withResponse(node2, defaultFrameOf(new Error(ProtocolConstants.ErrorCode.IS_BOOTSTRAPPING, "mock message")));
    try (RequestHandlerTestHarness harness = harnessBuilder.build()) {
        SpeculativeExecutionPolicy speculativeExecutionPolicy = harness.getContext().getSpeculativeExecutionPolicy(DriverExecutionProfile.DEFAULT_NAME);
        long firstExecutionDelay = 100L;
        when(speculativeExecutionPolicy.nextExecution(any(Node.class), eq(null), eq(statement), eq(1))).thenReturn(firstExecutionDelay);
        CompletionStage<AsyncResultSet> resultSetFuture = new CqlRequestHandler(statement, harness.getSession(), harness.getContext(), "test").handle();
        node1Behavior.verifyWrite();
        node1Behavior.setWriteSuccess();
        // do not simulate a response from node1 yet
        // Discard the timeout task
        harness.nextScheduledTimeout();
        // Run the next scheduled task to start the speculative execution. node2 will reply with a
        // BOOTSTRAPPING error, causing a RETRY_NEXT; but the query plan is now empty so the
        // speculative execution stops.
        // next scheduled timeout should be the first speculative execution. Get it and run it.
        CapturedTimeout speculativeExecution1 = harness.nextScheduledTimeout();
        assertThat(speculativeExecution1.getDelay(TimeUnit.MILLISECONDS)).isEqualTo(firstExecutionDelay);
        speculativeExecution1.task().run(speculativeExecution1);
        // node1 now replies with the same response, that triggers a RETRY_NEXT
        node1Behavior.setResponseSuccess(defaultFrameOf(new Error(ProtocolConstants.ErrorCode.IS_BOOTSTRAPPING, "mock message")));
        // But again the query plan is empty so that should fail the request
        assertThatStage(resultSetFuture).isFailed(error -> {
            assertThat(error).isInstanceOf(AllNodesFailedException.class);
            Map<Node, List<Throwable>> nodeErrors = ((AllNodesFailedException) error).getAllErrors();
            assertThat(nodeErrors).containsOnlyKeys(node1, node2);
            assertThat(nodeErrors.get(node1).get(0)).isInstanceOf(BootstrappingException.class);
            assertThat(nodeErrors.get(node2).get(0)).isInstanceOf(BootstrappingException.class);
        });
    }
}
Also used : AllNodesFailedException(com.datastax.oss.driver.api.core.AllNodesFailedException) AsyncResultSet(com.datastax.oss.driver.api.core.cql.AsyncResultSet) Node(com.datastax.oss.driver.api.core.metadata.Node) Error(com.datastax.oss.protocol.internal.response.Error) SpeculativeExecutionPolicy(com.datastax.oss.driver.api.core.specex.SpeculativeExecutionPolicy) List(java.util.List) CapturedTimeout(com.datastax.oss.driver.internal.core.util.concurrent.CapturingTimer.CapturedTimeout) Test(org.junit.Test) UseDataProvider(com.tngtech.java.junit.dataprovider.UseDataProvider)

Example 2 with SpeculativeExecutionPolicy

use of com.datastax.oss.driver.api.core.specex.SpeculativeExecutionPolicy in project java-driver by datastax.

the class CqlRequestHandlerSpeculativeExecutionTest method should_schedule_speculative_executions.

@Test
@UseDataProvider("idempotentConfig")
public void should_schedule_speculative_executions(boolean defaultIdempotence, Statement<?> statement) throws Exception {
    RequestHandlerTestHarness.Builder harnessBuilder = RequestHandlerTestHarness.builder().withDefaultIdempotence(defaultIdempotence);
    PoolBehavior node1Behavior = harnessBuilder.customBehavior(node1);
    PoolBehavior node2Behavior = harnessBuilder.customBehavior(node2);
    PoolBehavior node3Behavior = harnessBuilder.customBehavior(node3);
    try (RequestHandlerTestHarness harness = harnessBuilder.build()) {
        SpeculativeExecutionPolicy speculativeExecutionPolicy = harness.getContext().getSpeculativeExecutionPolicy(DriverExecutionProfile.DEFAULT_NAME);
        long firstExecutionDelay = 100L;
        long secondExecutionDelay = 200L;
        when(speculativeExecutionPolicy.nextExecution(any(Node.class), eq(null), eq(statement), eq(1))).thenReturn(firstExecutionDelay);
        when(speculativeExecutionPolicy.nextExecution(any(Node.class), eq(null), eq(statement), eq(2))).thenReturn(secondExecutionDelay);
        when(speculativeExecutionPolicy.nextExecution(any(Node.class), eq(null), eq(statement), eq(3))).thenReturn(-1L);
        new CqlRequestHandler(statement, harness.getSession(), harness.getContext(), "test").handle();
        node1Behavior.verifyWrite();
        node1Behavior.setWriteSuccess();
        // Discard the timeout task
        harness.nextScheduledTimeout();
        CapturedTimeout speculativeExecution1 = harness.nextScheduledTimeout();
        assertThat(speculativeExecution1.getDelay(TimeUnit.MILLISECONDS)).isEqualTo(firstExecutionDelay);
        verifyNoMoreInteractions(nodeMetricUpdater1);
        speculativeExecution1.task().run(speculativeExecution1);
        verify(nodeMetricUpdater1).incrementCounter(DefaultNodeMetric.SPECULATIVE_EXECUTIONS, DriverExecutionProfile.DEFAULT_NAME);
        node2Behavior.verifyWrite();
        node2Behavior.setWriteSuccess();
        CapturedTimeout speculativeExecution2 = harness.nextScheduledTimeout();
        assertThat(speculativeExecution2.getDelay(TimeUnit.MILLISECONDS)).isEqualTo(secondExecutionDelay);
        verifyNoMoreInteractions(nodeMetricUpdater2);
        speculativeExecution2.task().run(speculativeExecution2);
        verify(nodeMetricUpdater2).incrementCounter(DefaultNodeMetric.SPECULATIVE_EXECUTIONS, DriverExecutionProfile.DEFAULT_NAME);
        node3Behavior.verifyWrite();
        node3Behavior.setWriteSuccess();
        // No more scheduled tasks since the policy returns 0 on the third call.
        assertThat(harness.nextScheduledTimeout()).isNull();
    // Note that we don't need to complete any response, the test is just about checking that
    // executions are started.
    }
}
Also used : Node(com.datastax.oss.driver.api.core.metadata.Node) SpeculativeExecutionPolicy(com.datastax.oss.driver.api.core.specex.SpeculativeExecutionPolicy) CapturedTimeout(com.datastax.oss.driver.internal.core.util.concurrent.CapturingTimer.CapturedTimeout) Test(org.junit.Test) UseDataProvider(com.tngtech.java.junit.dataprovider.UseDataProvider)

Example 3 with SpeculativeExecutionPolicy

use of com.datastax.oss.driver.api.core.specex.SpeculativeExecutionPolicy in project java-driver by datastax.

the class CqlRequestHandlerSpeculativeExecutionTest method should_fail_if_no_more_nodes_and_speculative_execution_is_last.

@Test
@UseDataProvider("idempotentConfig")
public void should_fail_if_no_more_nodes_and_speculative_execution_is_last(boolean defaultIdempotence, Statement<?> statement) throws Exception {
    RequestHandlerTestHarness.Builder harnessBuilder = RequestHandlerTestHarness.builder().withDefaultIdempotence(defaultIdempotence);
    PoolBehavior node1Behavior = harnessBuilder.customBehavior(node1);
    PoolBehavior node2Behavior = harnessBuilder.customBehavior(node2);
    try (RequestHandlerTestHarness harness = harnessBuilder.build()) {
        SpeculativeExecutionPolicy speculativeExecutionPolicy = harness.getContext().getSpeculativeExecutionPolicy(DriverExecutionProfile.DEFAULT_NAME);
        long firstExecutionDelay = 100L;
        when(speculativeExecutionPolicy.nextExecution(any(Node.class), eq(null), eq(statement), eq(1))).thenReturn(firstExecutionDelay);
        CompletionStage<AsyncResultSet> resultSetFuture = new CqlRequestHandler(statement, harness.getSession(), harness.getContext(), "test").handle();
        node1Behavior.verifyWrite();
        node1Behavior.setWriteSuccess();
        // do not simulate a response from node1 yet
        // Discard the timeout task
        harness.nextScheduledTimeout();
        // next scheduled timeout should be the first speculative execution. Get it and run it.
        CapturedTimeout speculativeExecution1 = harness.nextScheduledTimeout();
        assertThat(speculativeExecution1.getDelay(TimeUnit.MILLISECONDS)).isEqualTo(firstExecutionDelay);
        speculativeExecution1.task().run(speculativeExecution1);
        // node1 now replies with a BOOTSTRAPPING error that triggers a RETRY_NEXT
        // but the query plan is empty so the initial execution stops
        node1Behavior.setResponseSuccess(defaultFrameOf(new Error(ProtocolConstants.ErrorCode.IS_BOOTSTRAPPING, "mock message")));
        // Same thing with node2, so the speculative execution should reach the end of the query plan
        // and fail the request
        node2Behavior.setResponseSuccess(defaultFrameOf(new Error(ProtocolConstants.ErrorCode.IS_BOOTSTRAPPING, "mock message")));
        assertThatStage(resultSetFuture).isFailed(error -> {
            assertThat(error).isInstanceOf(AllNodesFailedException.class);
            Map<Node, List<Throwable>> nodeErrors = ((AllNodesFailedException) error).getAllErrors();
            assertThat(nodeErrors).containsOnlyKeys(node1, node2);
            assertThat(nodeErrors.get(node1).get(0)).isInstanceOf(BootstrappingException.class);
            assertThat(nodeErrors.get(node2).get(0)).isInstanceOf(BootstrappingException.class);
        });
    }
}
Also used : AllNodesFailedException(com.datastax.oss.driver.api.core.AllNodesFailedException) AsyncResultSet(com.datastax.oss.driver.api.core.cql.AsyncResultSet) Node(com.datastax.oss.driver.api.core.metadata.Node) Error(com.datastax.oss.protocol.internal.response.Error) SpeculativeExecutionPolicy(com.datastax.oss.driver.api.core.specex.SpeculativeExecutionPolicy) List(java.util.List) CapturedTimeout(com.datastax.oss.driver.internal.core.util.concurrent.CapturingTimer.CapturedTimeout) Test(org.junit.Test) UseDataProvider(com.tngtech.java.junit.dataprovider.UseDataProvider)

Example 4 with SpeculativeExecutionPolicy

use of com.datastax.oss.driver.api.core.specex.SpeculativeExecutionPolicy in project java-driver by datastax.

the class CqlRequestHandlerSpeculativeExecutionTest method should_fail_if_no_nodes.

@Test
@UseDataProvider("idempotentConfig")
public void should_fail_if_no_nodes(boolean defaultIdempotence, Statement<?> statement) {
    RequestHandlerTestHarness.Builder harnessBuilder = RequestHandlerTestHarness.builder().withDefaultIdempotence(defaultIdempotence);
    try (RequestHandlerTestHarness harness = harnessBuilder.build()) {
        SpeculativeExecutionPolicy speculativeExecutionPolicy = harness.getContext().getSpeculativeExecutionPolicy(DriverExecutionProfile.DEFAULT_NAME);
        long firstExecutionDelay = 100L;
        when(speculativeExecutionPolicy.nextExecution(any(Node.class), eq(null), eq(statement), eq(1))).thenReturn(firstExecutionDelay);
        CompletionStage<AsyncResultSet> resultSetFuture = new CqlRequestHandler(statement, harness.getSession(), harness.getContext(), "test").handle();
        // Discard the timeout task
        harness.nextScheduledTimeout();
        assertThatStage(resultSetFuture).isFailed(error -> assertThat(error).isInstanceOf(NoNodeAvailableException.class));
    }
}
Also used : AsyncResultSet(com.datastax.oss.driver.api.core.cql.AsyncResultSet) Node(com.datastax.oss.driver.api.core.metadata.Node) SpeculativeExecutionPolicy(com.datastax.oss.driver.api.core.specex.SpeculativeExecutionPolicy) NoNodeAvailableException(com.datastax.oss.driver.api.core.NoNodeAvailableException) Test(org.junit.Test) UseDataProvider(com.tngtech.java.junit.dataprovider.UseDataProvider)

Example 5 with SpeculativeExecutionPolicy

use of com.datastax.oss.driver.api.core.specex.SpeculativeExecutionPolicy in project java-driver by datastax.

the class ContinuousGraphRequestHandlerSpeculativeExecutionTest method should_fail_if_no_more_nodes_and_speculative_execution_is_last.

@Test
@UseDataProvider(location = DseTestDataProviders.class, value = "idempotentGraphConfig")
public void should_fail_if_no_more_nodes_and_speculative_execution_is_last(boolean defaultIdempotence, GraphStatement<?> statement) throws Exception {
    GraphRequestHandlerTestHarness.Builder harnessBuilder = GraphRequestHandlerTestHarness.builder().withDefaultIdempotence(defaultIdempotence);
    PoolBehavior node1Behavior = harnessBuilder.customBehavior(node1);
    PoolBehavior node2Behavior = harnessBuilder.customBehavior(node2);
    try (GraphRequestHandlerTestHarness harness = harnessBuilder.build()) {
        SpeculativeExecutionPolicy speculativeExecutionPolicy = harness.getContext().getSpeculativeExecutionPolicy(DriverExecutionProfile.DEFAULT_NAME);
        long firstExecutionDelay = 100L;
        when(speculativeExecutionPolicy.nextExecution(any(Node.class), eq(null), eq(statement), eq(1))).thenReturn(firstExecutionDelay);
        GraphBinaryModule module = createGraphBinaryModule(harness.getContext());
        CompletionStage<AsyncGraphResultSet> resultSetFuture = new ContinuousGraphRequestHandler(statement, harness.getSession(), harness.getContext(), "test", module, graphSupportChecker).handle();
        node1Behavior.verifyWrite();
        node1Behavior.setWriteSuccess();
        // do not simulate a response from node1 yet
        // next scheduled timeout should be the first speculative execution. Get it and run it.
        CapturedTimeout speculativeExecution1 = harness.nextScheduledTimeout();
        assertThat(speculativeExecution1.getDelay(TimeUnit.MILLISECONDS)).isEqualTo(firstExecutionDelay);
        speculativeExecution1.task().run(speculativeExecution1);
        // node1 now replies with a BOOTSTRAPPING error that triggers a RETRY_NEXT
        // but the query plan is empty so the initial execution stops
        node1Behavior.setResponseSuccess(defaultDseFrameOf(new Error(ProtocolConstants.ErrorCode.IS_BOOTSTRAPPING, "mock message")));
        // Same thing with node2, so the speculative execution should reach the end of the query plan
        // and fail the request
        node2Behavior.setResponseSuccess(defaultDseFrameOf(new Error(ProtocolConstants.ErrorCode.IS_BOOTSTRAPPING, "mock message")));
        assertThatStage(resultSetFuture).isFailed(error -> {
            assertThat(error).isInstanceOf(AllNodesFailedException.class);
            Map<Node, List<Throwable>> nodeErrors = ((AllNodesFailedException) error).getAllErrors();
            assertThat(nodeErrors).containsOnlyKeys(node1, node2);
            assertThat(nodeErrors.get(node1).get(0)).isInstanceOf(BootstrappingException.class);
            assertThat(nodeErrors.get(node2).get(0)).isInstanceOf(BootstrappingException.class);
        });
    }
}
Also used : PoolBehavior(com.datastax.oss.driver.internal.core.cql.PoolBehavior) AllNodesFailedException(com.datastax.oss.driver.api.core.AllNodesFailedException) Node(com.datastax.oss.driver.api.core.metadata.Node) DefaultNode(com.datastax.oss.driver.internal.core.metadata.DefaultNode) Error(com.datastax.oss.protocol.internal.response.Error) SpeculativeExecutionPolicy(com.datastax.oss.driver.api.core.specex.SpeculativeExecutionPolicy) GraphTestUtils.createGraphBinaryModule(com.datastax.dse.driver.internal.core.graph.GraphTestUtils.createGraphBinaryModule) GraphBinaryModule(com.datastax.dse.driver.internal.core.graph.binary.GraphBinaryModule) AsyncGraphResultSet(com.datastax.dse.driver.api.core.graph.AsyncGraphResultSet) List(java.util.List) CapturedTimeout(com.datastax.oss.driver.internal.core.util.concurrent.CapturingTimer.CapturedTimeout) Test(org.junit.Test) UseDataProvider(com.tngtech.java.junit.dataprovider.UseDataProvider)

Aggregations

SpeculativeExecutionPolicy (com.datastax.oss.driver.api.core.specex.SpeculativeExecutionPolicy)18 Test (org.junit.Test)17 UseDataProvider (com.tngtech.java.junit.dataprovider.UseDataProvider)16 Node (com.datastax.oss.driver.api.core.metadata.Node)14 CapturedTimeout (com.datastax.oss.driver.internal.core.util.concurrent.CapturingTimer.CapturedTimeout)12 GraphTestUtils.createGraphBinaryModule (com.datastax.dse.driver.internal.core.graph.GraphTestUtils.createGraphBinaryModule)8 GraphBinaryModule (com.datastax.dse.driver.internal.core.graph.binary.GraphBinaryModule)8 Error (com.datastax.oss.protocol.internal.response.Error)8 PoolBehavior (com.datastax.oss.driver.internal.core.cql.PoolBehavior)7 DefaultNode (com.datastax.oss.driver.internal.core.metadata.DefaultNode)7 AsyncGraphResultSet (com.datastax.dse.driver.api.core.graph.AsyncGraphResultSet)6 AsyncResultSet (com.datastax.oss.driver.api.core.cql.AsyncResultSet)6 AllNodesFailedException (com.datastax.oss.driver.api.core.AllNodesFailedException)4 List (java.util.List)4 NoNodeAvailableException (com.datastax.oss.driver.api.core.NoNodeAvailableException)2 ConstantSpeculativeExecutionPolicy (com.datastax.oss.driver.internal.core.specex.ConstantSpeculativeExecutionPolicy)2 NoSpeculativeExecutionPolicy (com.datastax.oss.driver.internal.core.specex.NoSpeculativeExecutionPolicy)2 CqlSession (com.datastax.oss.driver.api.core.CqlSession)1 DriverConfig (com.datastax.oss.driver.api.core.config.DriverConfig)1 ProgrammaticDriverConfigLoaderBuilder (com.datastax.oss.driver.api.core.config.ProgrammaticDriverConfigLoaderBuilder)1