|
|
|
@ -212,7 +212,11 @@ struct ClientStats { |
|
|
|
|
class BalancerServiceImpl : public BalancerService { |
|
|
|
|
public: |
|
|
|
|
using Stream = ServerReaderWriter<LoadBalanceResponse, LoadBalanceRequest>; |
|
|
|
|
using ResponseDelayPair = std::pair<LoadBalanceResponse, int>; |
|
|
|
|
struct ResponseConfig { |
|
|
|
|
LoadBalanceResponse response; |
|
|
|
|
int delay_ms; |
|
|
|
|
std::string for_target; |
|
|
|
|
}; |
|
|
|
|
|
|
|
|
|
explicit BalancerServiceImpl(int client_load_reporting_interval_seconds) |
|
|
|
|
: client_load_reporting_interval_seconds_( |
|
|
|
@ -229,10 +233,15 @@ class BalancerServiceImpl : public BalancerService { |
|
|
|
|
EXPECT_EQ(context->client_metadata().find(g_kCallCredsMdKey), |
|
|
|
|
context->client_metadata().end()); |
|
|
|
|
LoadBalanceRequest request; |
|
|
|
|
std::vector<ResponseDelayPair> responses_and_delays; |
|
|
|
|
std::string target; |
|
|
|
|
std::vector<ResponseConfig> response_configs; |
|
|
|
|
|
|
|
|
|
if (!stream->Read(&request)) { |
|
|
|
|
goto done; |
|
|
|
|
} else { |
|
|
|
|
if (request.has_initial_request()) { |
|
|
|
|
target = request.initial_request().name(); |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
IncreaseRequestCount(); |
|
|
|
|
gpr_log(GPR_INFO, "LB[%p]: received initial message '%s'", this, |
|
|
|
@ -249,11 +258,14 @@ class BalancerServiceImpl : public BalancerService { |
|
|
|
|
|
|
|
|
|
{ |
|
|
|
|
grpc::internal::MutexLock lock(&mu_); |
|
|
|
|
responses_and_delays = responses_and_delays_; |
|
|
|
|
response_configs = response_configs_; |
|
|
|
|
} |
|
|
|
|
for (const auto& response_and_delay : responses_and_delays) { |
|
|
|
|
SendResponse(stream, response_and_delay.first, |
|
|
|
|
response_and_delay.second); |
|
|
|
|
for (const auto& response_config : response_configs) { |
|
|
|
|
if (response_config.for_target.empty() || |
|
|
|
|
response_config.for_target == target) { |
|
|
|
|
SendResponse(stream, response_config.response, |
|
|
|
|
response_config.delay_ms); |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
{ |
|
|
|
|
grpc::internal::MutexLock lock(&mu_); |
|
|
|
@ -295,16 +307,16 @@ class BalancerServiceImpl : public BalancerService { |
|
|
|
|
return Status::OK; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
void add_response(const LoadBalanceResponse& response, int send_after_ms) { |
|
|
|
|
void add_response(const LoadBalanceResponse& response, int send_after_ms, |
|
|
|
|
std::string for_target = "") { |
|
|
|
|
grpc::internal::MutexLock lock(&mu_); |
|
|
|
|
responses_and_delays_.push_back(std::make_pair(response, send_after_ms)); |
|
|
|
|
response_configs_.push_back({response, send_after_ms, for_target}); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
void Start() { |
|
|
|
|
grpc::internal::MutexLock lock(&mu_); |
|
|
|
|
serverlist_done_ = false; |
|
|
|
|
responses_and_delays_.clear(); |
|
|
|
|
load_report_queue_.clear(); |
|
|
|
|
response_configs_.clear(); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
void Shutdown() { |
|
|
|
@ -372,7 +384,7 @@ class BalancerServiceImpl : public BalancerService { |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
const int client_load_reporting_interval_seconds_; |
|
|
|
|
std::vector<ResponseDelayPair> responses_and_delays_; |
|
|
|
|
std::vector<ResponseConfig> response_configs_; |
|
|
|
|
|
|
|
|
|
grpc::internal::Mutex mu_; |
|
|
|
|
grpc::internal::CondVar serverlist_cond_; |
|
|
|
@ -613,8 +625,8 @@ class GrpclbEnd2endTest : public ::testing::Test { |
|
|
|
|
|
|
|
|
|
void ScheduleResponseForBalancer(size_t i, |
|
|
|
|
const LoadBalanceResponse& response, |
|
|
|
|
int delay_ms) { |
|
|
|
|
balancers_[i]->service_.add_response(response, delay_ms); |
|
|
|
|
int delay_ms, std::string target = "") { |
|
|
|
|
balancers_[i]->service_.add_response(response, delay_ms, target); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
Status SendRpc(EchoResponse* response = nullptr, int timeout_ms = 1000, |
|
|
|
@ -1383,6 +1395,29 @@ TEST_F(SingleBalancerTest, BackendsRestart) { |
|
|
|
|
EXPECT_EQ(1U, balancers_[0]->service_.response_count()); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
TEST_F(SingleBalancerTest, TargetFromLbPolicyConfig) { |
|
|
|
|
constexpr char kServiceConfigWithTarget[] = |
|
|
|
|
"{\n" |
|
|
|
|
" \"loadBalancingConfig\":[\n" |
|
|
|
|
" { \"grpclb\":{\n" |
|
|
|
|
" \"targetName\":\"test_target\"\n" |
|
|
|
|
" }}\n" |
|
|
|
|
" ]\n" |
|
|
|
|
"}"; |
|
|
|
|
|
|
|
|
|
SetNextResolutionAllBalancers(kServiceConfigWithTarget); |
|
|
|
|
const size_t kNumRpcsPerAddress = 1; |
|
|
|
|
ScheduleResponseForBalancer( |
|
|
|
|
0, BalancerServiceImpl::BuildResponseForBackends(GetBackendPorts(), {}), |
|
|
|
|
0, "test_target"); |
|
|
|
|
// Make sure that trying to connect works without a call.
|
|
|
|
|
channel_->GetState(true /* try_to_connect */); |
|
|
|
|
// We need to wait for all backends to come online.
|
|
|
|
|
WaitForAllBackends(); |
|
|
|
|
// Send kNumRpcsPerAddress RPCs per server.
|
|
|
|
|
CheckRpcSendOk(kNumRpcsPerAddress * num_backends_); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
class UpdatesTest : public GrpclbEnd2endTest { |
|
|
|
|
public: |
|
|
|
|
UpdatesTest() : GrpclbEnd2endTest(4, 3, 0) {} |
|
|
|
|