util: Status desc for outlier detection ejection (#11036) · grpc/grpc-java@10cb4a3

@@ -19,8 +19,8 @@

1919

import static com.google.common.truth.Truth.assertThat;

2020

import static com.google.common.truth.Truth.assertWithMessage;

2121

import static io.grpc.ConnectivityState.READY;

22+

import static io.grpc.ConnectivityState.TRANSIENT_FAILURE;

2223

import static org.mockito.ArgumentMatchers.any;

23-

import static org.mockito.ArgumentMatchers.eq;

2424

import static org.mockito.Mockito.doAnswer;

2525

import static org.mockito.Mockito.mock;

2626

import static org.mockito.Mockito.times;

5050

import io.grpc.LoadBalancerProvider;

5151

import io.grpc.Metadata;

5252

import io.grpc.Status;

53+

import io.grpc.Status.Code;

5354

import io.grpc.SynchronizationContext;

5455

import io.grpc.internal.FakeClock;

5556

import io.grpc.internal.FakeClock.ScheduledTask;

@@ -1203,9 +1204,21 @@ public void successRateAndFailurePercentage_successRateOutlier_() { // with heal

12031204

// The one subchannel that was returning errors should be ejected.

12041205

assertEjectedSubchannels(ImmutableSet.of(ImmutableSet.copyOf(servers.get(0).getAddresses())));

12051206

if (hasHealthConsumer) {

1206-

verify(healthListeners.get(servers.get(0))).onSubchannelState(eq(

1207-

ConnectivityStateInfo.forTransientFailure(Status.UNAVAILABLE)

1208-

));

1207+

ArgumentCaptor<ConnectivityStateInfo> csiCaptor = ArgumentCaptor.forClass(

1208+

ConnectivityStateInfo.class);

1209+

verify(healthListeners.get(servers.get(0)), times(2)).onSubchannelState(csiCaptor.capture());

1210+

List<ConnectivityStateInfo> connectivityStateInfos = csiCaptor.getAllValues();

1211+1212+

// The subchannel went through two state transitions...

1213+

assertThat(connectivityStateInfos).hasSize(2);

1214+

// ...it first went to the READY state...

1215+

assertThat(connectivityStateInfos.get(0).getState()).isEqualTo(READY);

1216+1217+

// ...and then to TRANSIENT_FAILURE as outlier detection ejected it.

1218+

assertThat(connectivityStateInfos.get(1).getState()).isEqualTo(TRANSIENT_FAILURE);

1219+

assertThat(connectivityStateInfos.get(1).getStatus().getCode()).isEqualTo(Code.UNAVAILABLE);

1220+

assertThat(connectivityStateInfos.get(1).getStatus().getDescription()).isEqualTo(

1221+

"The subchannel has been ejected by outlier detection");

12091222

}

12101223

}

12111224

@@ -1264,9 +1277,21 @@ public void successRateAndFailurePercentage_errorPercentageOutlier_() { // with

12641277

// The one subchannel that was returning errors should be ejected.

12651278

assertEjectedSubchannels(ImmutableSet.of(ImmutableSet.copyOf(servers.get(0).getAddresses())));

12661279

if (hasHealthConsumer) {

1267-

verify(healthListeners.get(servers.get(0))).onSubchannelState(eq(

1268-

ConnectivityStateInfo.forTransientFailure(Status.UNAVAILABLE)

1269-

));

1280+

ArgumentCaptor<ConnectivityStateInfo> csiCaptor = ArgumentCaptor.forClass(

1281+

ConnectivityStateInfo.class);

1282+

verify(healthListeners.get(servers.get(0)), times(2)).onSubchannelState(csiCaptor.capture());

1283+

List<ConnectivityStateInfo> connectivityStateInfos = csiCaptor.getAllValues();

1284+1285+

// The subchannel went through two state transitions...

1286+

assertThat(connectivityStateInfos).hasSize(2);

1287+

// ...it first went to the READY state...

1288+

assertThat(connectivityStateInfos.get(0).getState()).isEqualTo(READY);

1289+1290+

// ...and then to TRANSIENT_FAILURE as outlier detection ejected it.

1291+

assertThat(connectivityStateInfos.get(1).getState()).isEqualTo(TRANSIENT_FAILURE);

1292+

assertThat(connectivityStateInfos.get(1).getStatus().getCode()).isEqualTo(Code.UNAVAILABLE);

1293+

assertThat(connectivityStateInfos.get(1).getStatus().getDescription()).isEqualTo(

1294+

"The subchannel has been ejected by outlier detection");

12701295

}

12711296

}

12721297