2525
2626import static org .assertj .core .api .Assertions .assertThat ;
2727import static org .mockito .BDDMockito .given ;
28+ import static org .mockito .Mockito .mock ;
2829import static org .mockito .Mockito .when ;
2930
3031import com .datastax .oss .driver .api .core .CqlIdentifier ;
32+ import com .datastax .oss .driver .api .core .DefaultConsistencyLevel ;
3133import com .datastax .oss .driver .api .core .RequestRoutingType ;
3234import com .datastax .oss .driver .api .core .config .DefaultDriverOption ;
3335import com .datastax .oss .driver .api .core .config .DriverExecutionProfile ;
36+ import com .datastax .oss .driver .api .core .cql .BoundStatement ;
37+ import com .datastax .oss .driver .api .core .cql .ColumnDefinitions ;
38+ import com .datastax .oss .driver .api .core .cql .PreparedStatement ;
39+ import com .datastax .oss .driver .api .core .cql .SimpleStatement ;
40+ import com .datastax .oss .driver .api .core .cql .Statement ;
3441import com .datastax .oss .driver .api .core .metadata .Metadata ;
3542import com .datastax .oss .driver .api .core .metadata .Node ;
3643import com .datastax .oss .driver .api .core .metadata .TokenMap ;
3744import com .datastax .oss .driver .api .core .metadata .token .Token ;
3845import com .datastax .oss .driver .api .core .session .Request ;
46+ import com .datastax .oss .driver .internal .core .cql .DefaultBoundStatement ;
3947import com .datastax .oss .driver .internal .core .loadbalancing .BasicLoadBalancingPolicy .RequestRoutingMethod ;
4048import com .datastax .oss .driver .internal .core .session .DefaultSession ;
4149import com .datastax .oss .driver .shaded .guava .common .collect .ImmutableList ;
4250import com .datastax .oss .driver .shaded .guava .common .collect .ImmutableMap ;
4351import com .datastax .oss .driver .shaded .guava .common .collect .ImmutableSet ;
4452import com .datastax .oss .protocol .internal .util .Bytes ;
4553import java .nio .ByteBuffer ;
54+ import java .util .Collections ;
4655import java .util .Optional ;
4756import java .util .Queue ;
4857import java .util .UUID ;
@@ -165,6 +174,132 @@ public void should_dispatch_to_regular_query_plan_when_request_is_regular() {
165174 assertThat (plan2 ).containsExactlyInAnyOrder (node1 , node2 , node3 );
166175 }
167176
177+ @ Test
178+ public void
179+ should_dispatch_to_regular_query_plan_when_simple_local_serial_select_and_config_preserve () {
180+ // Given
181+ initPolicy ("PRESERVE_REPLICA_ORDER" );
182+ SimpleStatement statement =
183+ SimpleStatement .builder (
184+ "SELECT * FROM unique_key_value "
185+ + "WHERE unique_key=? AND unique_value=? AND context=?" )
186+ .setConsistencyLevel (DefaultConsistencyLevel .LOCAL_SERIAL )
187+ .setRoutingKeyspace (KEYSPACE )
188+ .setRoutingKey (ROUTING_KEY )
189+ .build ();
190+ given (tokenMap .getReplicasList (KEYSPACE , null , ROUTING_KEY ))
191+ .willReturn (ImmutableList .of (node1 , node2 ));
192+
193+ // When
194+ Queue <Node > plan = policy .newQueryPlan (statement , session );
195+
196+ // Then
197+ assertThat (statement .isLWT ()).isFalse ();
198+ assertThat (statement .getRequestRoutingType ()).isNull ();
199+ assertThat (policy .getRequestRoutingMethod (statement )).isEqualTo (RequestRoutingMethod .REGULAR );
200+ assertThat (plan ).containsExactlyInAnyOrder (node1 , node2 , node3 );
201+ }
202+
203+ @ Test
204+ public void
205+ should_dispatch_to_regular_query_plan_when_prepared_statement_routing_type_is_regular () {
206+ // Given
207+ initPolicy ("PRESERVE_REPLICA_ORDER" );
208+ BoundStatement statement = newRegularBoundStatementWithLocalSerialConsistency ();
209+ given (tokenMap .getReplicasList (KEYSPACE , null , ROUTING_KEY ))
210+ .willReturn (ImmutableList .of (node1 , node2 ));
211+
212+ // When
213+ Queue <Node > plan = policy .newQueryPlan (statement , session );
214+
215+ // Then
216+ assertThat (statement .isLWT ()).isFalse ();
217+ assertThat (statement .getRequestRoutingType ()).isEqualTo (RequestRoutingType .LWT );
218+ assertThat (policy .getRequestRoutingMethod (statement ))
219+ .isEqualTo (RequestRoutingMethod .PRESERVE_REPLICA_ORDER );
220+ assertThat (plan ).containsExactlyInAnyOrder (node1 , node2 , node3 );
221+ }
222+
223+ @ Test
224+ public void should_dispatch_to_regular_query_plan_when_local_serial_select_and_config_regular () {
225+ // Given
226+ initPolicy ("REGULAR" );
227+ SimpleStatement statement =
228+ SimpleStatement .builder (
229+ "SELECT * FROM unique_key_value "
230+ + "WHERE unique_key=? AND unique_value=? AND context=?" )
231+ .setConsistencyLevel (DefaultConsistencyLevel .LOCAL_SERIAL )
232+ .setRoutingKeyspace (KEYSPACE )
233+ .setRoutingKey (ROUTING_KEY )
234+ .build ();
235+ given (tokenMap .getReplicasList (KEYSPACE , null , ROUTING_KEY ))
236+ .willReturn (ImmutableList .of (node1 , node2 ));
237+
238+ // When
239+ Queue <Node > plan = policy .newQueryPlan (statement , session );
240+
241+ // Then
242+ assertThat (statement .isLWT ()).isFalse ();
243+ assertThat (policy .getRequestRoutingMethod (statement )).isEqualTo (RequestRoutingMethod .REGULAR );
244+ assertThat (plan ).containsExactlyInAnyOrder (node1 , node2 , node3 );
245+ }
246+
247+ @ Test
248+ public void should_dispatch_to_regular_query_plan_when_profile_has_local_serial_consistency () {
249+ // Given
250+ initPolicy ("PRESERVE_REPLICA_ORDER" );
251+ DriverExecutionProfile serialProfile = mock (DriverExecutionProfile .class );
252+ when (serialProfile .getString (DefaultDriverOption .REQUEST_CONSISTENCY ))
253+ .thenReturn ("LOCAL_SERIAL" );
254+ SimpleStatement statement =
255+ SimpleStatement .builder (
256+ "SELECT * FROM unique_key_value "
257+ + "WHERE unique_key=? AND unique_value=? AND context=?" )
258+ .setExecutionProfile (serialProfile )
259+ .setRoutingKeyspace (KEYSPACE )
260+ .setRoutingKey (ROUTING_KEY )
261+ .build ();
262+ given (tokenMap .getReplicasList (KEYSPACE , null , ROUTING_KEY ))
263+ .willReturn (ImmutableList .of (node1 , node2 ));
264+
265+ // When
266+ Queue <Node > plan = policy .newQueryPlan (statement , session );
267+
268+ // Then
269+ assertThat (statement .getConsistencyLevel ()).isNull ();
270+ assertThat (policy .getRequestRoutingMethod (statement )).isEqualTo (RequestRoutingMethod .REGULAR );
271+ assertThat (plan ).containsExactlyInAnyOrder (node1 , node2 , node3 );
272+ }
273+
274+ @ Test
275+ public void
276+ should_dispatch_to_regular_query_plan_when_profile_name_has_local_serial_consistency () {
277+ // Given
278+ initPolicy ("PRESERVE_REPLICA_ORDER" );
279+ DriverExecutionProfile serialProfile = mock (DriverExecutionProfile .class );
280+ when (config .getProfile ("serial" )).thenReturn (serialProfile );
281+ when (serialProfile .getString (DefaultDriverOption .REQUEST_CONSISTENCY ))
282+ .thenReturn ("LOCAL_SERIAL" );
283+ SimpleStatement statement =
284+ SimpleStatement .builder (
285+ "SELECT * FROM unique_key_value "
286+ + "WHERE unique_key=? AND unique_value=? AND context=?" )
287+ .setExecutionProfileName ("serial" )
288+ .setRoutingKeyspace (KEYSPACE )
289+ .setRoutingKey (ROUTING_KEY )
290+ .build ();
291+ given (tokenMap .getReplicasList (KEYSPACE , null , ROUTING_KEY ))
292+ .willReturn (ImmutableList .of (node1 , node2 ));
293+
294+ // When
295+ Queue <Node > plan = policy .newQueryPlan (statement , session );
296+
297+ // Then
298+ assertThat (statement .getConsistencyLevel ()).isNull ();
299+ assertThat (policy .getRequestRoutingMethod (statement )).isEqualTo (RequestRoutingMethod .REGULAR );
300+ assertThat (plan ).containsExactlyInAnyOrder (node1 , node2 , node3 );
301+ }
302+
168303 @ Test
169304 public void should_dispatch_to_preserve_query_plan_when_lwt_and_config_preserve () {
170305 // Given
@@ -186,6 +321,37 @@ public void should_dispatch_to_preserve_query_plan_when_lwt_and_config_preserve(
186321 assertThat (plan3 ).containsExactly (node2 , node1 , node3 );
187322 }
188323
324+ private BoundStatement newRegularBoundStatementWithLocalSerialConsistency () {
325+ PreparedStatement preparedStatement = mock (PreparedStatement .class );
326+ ColumnDefinitions variableDefinitions = mock (ColumnDefinitions .class );
327+ when (preparedStatement .isLWT ()).thenReturn (false );
328+ when (preparedStatement .getRequestRoutingType ()).thenReturn (RequestRoutingType .REGULAR );
329+ when (preparedStatement .getVariableDefinitions ()).thenReturn (variableDefinitions );
330+ return new DefaultBoundStatement (
331+ preparedStatement ,
332+ variableDefinitions ,
333+ new ByteBuffer [0 ],
334+ null ,
335+ null ,
336+ KEYSPACE ,
337+ ROUTING_KEY ,
338+ null ,
339+ Collections .emptyMap (),
340+ null ,
341+ false ,
342+ Statement .NO_DEFAULT_TIMESTAMP ,
343+ null ,
344+ Integer .MIN_VALUE ,
345+ DefaultConsistencyLevel .LOCAL_SERIAL ,
346+ null ,
347+ null ,
348+ null ,
349+ null ,
350+ null ,
351+ Statement .NO_NOW_IN_SECONDS ,
352+ null );
353+ }
354+
189355 @ Test
190356 public void should_dispatch_to_regular_query_plan_when_lwt_but_config_regular () {
191357 // Given
0 commit comments