| /* |
| * |
| * Copyright 2018 gRPC authors. |
| * |
| * Licensed under the Apache License, Version 2.0 (the "License"); |
| * you may not use this file except in compliance with the License. |
| * You may obtain a copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, software |
| * distributed under the License is distributed on an "AS IS" BASIS, |
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| * See the License for the specific language governing permissions and |
| * limitations under the License. |
| * |
| */ |
| |
| #include "src/core/ext/filters/client_channel/retry_throttle.h" |
| |
| #include <gtest/gtest.h> |
| |
| #include "test/core/util/test_config.h" |
| |
| namespace grpc_core { |
| namespace internal { |
| namespace { |
| |
| TEST(ServerRetryThrottleData, Basic) { |
| // Max token count is 4, so threshold for retrying is 2. |
| // Token count starts at 4. |
| // Each failure decrements by 1. Each success increments by 1.6. |
| auto throttle_data = |
| MakeRefCounted<ServerRetryThrottleData>(4000, 1600, nullptr); |
| // Failure: token_count=3. Above threshold. |
| EXPECT_TRUE(throttle_data->RecordFailure()); |
| // Success: token_count=4. Not incremented beyond max. |
| throttle_data->RecordSuccess(); |
| // Failure: token_count=3. Above threshold. |
| EXPECT_TRUE(throttle_data->RecordFailure()); |
| // Failure: token_count=2. At threshold, so no retries. |
| EXPECT_FALSE(throttle_data->RecordFailure()); |
| // Failure: token_count=1. Below threshold, so no retries. |
| EXPECT_FALSE(throttle_data->RecordFailure()); |
| // Failure: token_count=0. Below threshold, so no retries. |
| EXPECT_FALSE(throttle_data->RecordFailure()); |
| // Failure: token_count=0. Below threshold, so no retries. Not |
| // decremented below min. |
| EXPECT_FALSE(throttle_data->RecordFailure()); |
| // Success: token_count=1.6. |
| throttle_data->RecordSuccess(); |
| // Success: token_count=3.2. |
| throttle_data->RecordSuccess(); |
| // Failure: token_count=2.2. Above threshold. |
| EXPECT_TRUE(throttle_data->RecordFailure()); |
| // Failure: token_count=1.2. Below threshold, so no retries. |
| EXPECT_FALSE(throttle_data->RecordFailure()); |
| // Success: token_count=2.8. |
| throttle_data->RecordSuccess(); |
| // Failure: token_count=1.8. Below threshold, so no retries. |
| EXPECT_FALSE(throttle_data->RecordFailure()); |
| // Success: token_count=3.4. |
| throttle_data->RecordSuccess(); |
| // Failure: token_count=2.4. Above threshold. |
| EXPECT_TRUE(throttle_data->RecordFailure()); |
| } |
| |
| TEST(ServerRetryThrottleData, Replacement) { |
| // Create old throttle data. |
| // Max token count is 4, so threshold for retrying is 2. |
| // Token count starts at 4. |
| // Each failure decrements by 1. Each success increments by 1. |
| auto old_throttle_data = |
| MakeRefCounted<ServerRetryThrottleData>(4000, 1000, nullptr); |
| // Failure: token_count=3. Above threshold. |
| EXPECT_TRUE(old_throttle_data->RecordFailure()); |
| // Create new throttle data. |
| // Max token count is 10, so threshold for retrying is 5. |
| // Token count starts at 7.5 (ratio inherited from old_throttle_data). |
| // Each failure decrements by 1. Each success increments by 3. |
| auto throttle_data = MakeRefCounted<ServerRetryThrottleData>( |
| 10000, 3000, old_throttle_data.get()); |
| // Failure via old_throttle_data: token_count=6.5. |
| EXPECT_TRUE(old_throttle_data->RecordFailure()); |
| // Failure: token_count=5.5. |
| EXPECT_TRUE(old_throttle_data->RecordFailure()); |
| // Failure via old_throttle_data: token_count=4.5. Below threshold. |
| EXPECT_FALSE(old_throttle_data->RecordFailure()); |
| // Failure: token_count=3.5. Below threshold. |
| EXPECT_FALSE(throttle_data->RecordFailure()); |
| // Success: token_count=6.5. |
| throttle_data->RecordSuccess(); |
| // Failure via old_throttle_data: token_count=5.5. Above threshold. |
| EXPECT_TRUE(old_throttle_data->RecordFailure()); |
| // Failure: token_count=4.5. Below threshold. |
| EXPECT_FALSE(throttle_data->RecordFailure()); |
| } |
| |
| TEST(ServerRetryThrottleMap, Replacement) { |
| ServerRetryThrottleMap::Init(); |
| const char kServerName[] = "server_name"; |
| // Create old throttle data. |
| // Max token count is 4, so threshold for retrying is 2. |
| // Token count starts at 4. |
| // Each failure decrements by 1. Each success increments by 1. |
| auto old_throttle_data = |
| ServerRetryThrottleMap::GetDataForServer(kServerName, 4000, 1000); |
| // Failure: token_count=3. Above threshold. |
| EXPECT_TRUE(old_throttle_data->RecordFailure()); |
| // Create new throttle data. |
| // Max token count is 10, so threshold for retrying is 5. |
| // Token count starts at 7.5 (ratio inherited from old_throttle_data). |
| // Each failure decrements by 1. Each success increments by 3. |
| auto throttle_data = |
| ServerRetryThrottleMap::GetDataForServer(kServerName, 10000, 3000); |
| // Failure via old_throttle_data: token_count=6.5. |
| EXPECT_TRUE(old_throttle_data->RecordFailure()); |
| // Failure: token_count=5.5. |
| EXPECT_TRUE(old_throttle_data->RecordFailure()); |
| // Failure via old_throttle_data: token_count=4.5. Below threshold. |
| EXPECT_FALSE(old_throttle_data->RecordFailure()); |
| // Failure: token_count=3.5. Below threshold. |
| EXPECT_FALSE(throttle_data->RecordFailure()); |
| // Success: token_count=6.5. |
| throttle_data->RecordSuccess(); |
| // Failure via old_throttle_data: token_count=5.5. Above threshold. |
| EXPECT_TRUE(old_throttle_data->RecordFailure()); |
| // Failure: token_count=4.5. Below threshold. |
| EXPECT_FALSE(throttle_data->RecordFailure()); |
| // Clean up. |
| ServerRetryThrottleMap::Shutdown(); |
| } |
| |
| } // namespace |
| } // namespace internal |
| } // namespace grpc_core |
| |
| int main(int argc, char** argv) { |
| grpc::testing::TestEnvironment env(argc, argv); |
| ::testing::InitGoogleTest(&argc, argv); |
| return RUN_ALL_TESTS(); |
| } |