Skip to content

Commit 06c92cd

Browse files
committed
fix(spanner): pin inline read-write transactions to default endpoint
1 parent 9fd84fc commit 06c92cd

2 files changed

Lines changed: 93 additions & 0 deletions

File tree

java-spanner/google-cloud-spanner/src/main/java/com/google/cloud/spanner/spi/v1/KeyAwareChannel.java

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -785,6 +785,7 @@ private void maybeTrackReadWriteBegin(TransactionSelector selector) {
785785
if (selector.getSelectorCase() == TransactionSelector.SelectorCase.BEGIN
786786
&& !selector.getBegin().hasReadOnly()) {
787787
shouldRecordTransactionAffinity = true;
788+
allowDefaultAffinity = true;
788789
}
789790
}
790791

java-spanner/google-cloud-spanner/src/test/java/com/google/cloud/spanner/spi/v1/KeyAwareChannelTest.java

Lines changed: 92 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -930,6 +930,98 @@ public void readOnlyTransactionRoutesEachReadIndependently() throws Exception {
930930
assertThat(harness.defaultManagedChannel.callCount()).isEqualTo(2);
931931
}
932932

933+
@Test
934+
public void readWriteInlinedBeginExecuteSqlOnDefaultRecordsDefaultAffinity() throws Exception {
935+
TestHarness harness = createHarness();
936+
ByteString transactionId = ByteString.copyFromUtf8("rw-inline-sql-default");
937+
938+
ClientCall<ExecuteSqlRequest, ResultSet> beginCall =
939+
harness.channel.newCall(SpannerGrpc.getExecuteSqlMethod(), CallOptions.DEFAULT);
940+
beginCall.start(new CapturingListener<ResultSet>(), new Metadata());
941+
beginCall.sendMessage(
942+
ExecuteSqlRequest.newBuilder()
943+
.setSession(SESSION)
944+
.setTransaction(
945+
TransactionSelector.newBuilder()
946+
.setBegin(
947+
TransactionOptions.newBuilder()
948+
.setReadWrite(TransactionOptions.ReadWrite.getDefaultInstance())
949+
.build()))
950+
.build());
951+
952+
@SuppressWarnings("unchecked")
953+
RecordingClientCall<ExecuteSqlRequest, ResultSet> beginDelegate =
954+
(RecordingClientCall<ExecuteSqlRequest, ResultSet>)
955+
harness.defaultManagedChannel.latestCall();
956+
beginDelegate.emitOnMessage(
957+
ResultSet.newBuilder()
958+
.setMetadata(
959+
ResultSetMetadata.newBuilder()
960+
.setTransaction(Transaction.newBuilder().setId(transactionId)))
961+
.build());
962+
963+
seedCache(harness, createTwoRangeCacheUpdate());
964+
965+
ClientCall<ExecuteSqlRequest, ResultSet> nextCall =
966+
harness.channel.newCall(SpannerGrpc.getExecuteSqlMethod(), CallOptions.DEFAULT);
967+
nextCall.start(new CapturingListener<ResultSet>(), new Metadata());
968+
nextCall.sendMessage(
969+
ExecuteSqlRequest.newBuilder()
970+
.setSession(SESSION)
971+
.setTransaction(TransactionSelector.newBuilder().setId(transactionId))
972+
.setRoutingHint(RoutingHint.newBuilder().setKey(bytes("b")).build())
973+
.build());
974+
975+
assertThat(harness.defaultManagedChannel.callCount()).isEqualTo(3);
976+
assertThat(harness.endpointCache.callCountForAddress("server-a:1234")).isEqualTo(0);
977+
}
978+
979+
@Test
980+
public void readWriteInlinedBeginReadOnDefaultRecordsDefaultAffinity() throws Exception {
981+
TestHarness harness = createHarness();
982+
ByteString transactionId = ByteString.copyFromUtf8("rw-inline-read-default");
983+
984+
ClientCall<ReadRequest, PartialResultSet> beginCall =
985+
harness.channel.newCall(SpannerGrpc.getStreamingReadMethod(), CallOptions.DEFAULT);
986+
beginCall.start(new CapturingListener<PartialResultSet>(), new Metadata());
987+
beginCall.sendMessage(
988+
ReadRequest.newBuilder()
989+
.setSession(SESSION)
990+
.setTransaction(
991+
TransactionSelector.newBuilder()
992+
.setBegin(
993+
TransactionOptions.newBuilder()
994+
.setReadWrite(TransactionOptions.ReadWrite.getDefaultInstance())
995+
.build()))
996+
.build());
997+
998+
@SuppressWarnings("unchecked")
999+
RecordingClientCall<ReadRequest, PartialResultSet> beginDelegate =
1000+
(RecordingClientCall<ReadRequest, PartialResultSet>)
1001+
harness.defaultManagedChannel.latestCall();
1002+
beginDelegate.emitOnMessage(
1003+
PartialResultSet.newBuilder()
1004+
.setMetadata(
1005+
ResultSetMetadata.newBuilder()
1006+
.setTransaction(Transaction.newBuilder().setId(transactionId)))
1007+
.build());
1008+
1009+
seedCache(harness, createTwoRangeCacheUpdate());
1010+
1011+
ClientCall<ReadRequest, PartialResultSet> nextCall =
1012+
harness.channel.newCall(SpannerGrpc.getStreamingReadMethod(), CallOptions.DEFAULT);
1013+
nextCall.start(new CapturingListener<PartialResultSet>(), new Metadata());
1014+
nextCall.sendMessage(
1015+
ReadRequest.newBuilder()
1016+
.setSession(SESSION)
1017+
.setTransaction(TransactionSelector.newBuilder().setId(transactionId))
1018+
.setRoutingHint(RoutingHint.newBuilder().setKey(bytes("b")).build())
1019+
.build());
1020+
1021+
assertThat(harness.defaultManagedChannel.callCount()).isEqualTo(3);
1022+
assertThat(harness.endpointCache.callCountForAddress("server-a:1234")).isEqualTo(0);
1023+
}
1024+
9331025
@Test
9341026
public void readOnlyInlinedBeginExecuteSqlRoutesSubsequentRequestsIndependently()
9351027
throws Exception {

0 commit comments

Comments
 (0)