Skip to content

Commit d470caf

Browse files
authored
odcds: add a test that ODCDS with EDS using xds-federation works (#41041)
Commit Message: odcds: add a test that ODCDS with EDS using xds-federation works Signed-off-by: Adi Suissa-Peleg <[email protected]>
1 parent 51a47f6 commit d470caf

File tree

1 file changed

+73
-0
lines changed

1 file changed

+73
-0
lines changed

test/extensions/filters/http/on_demand/odcds_integration_test.cc

Lines changed: 73 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -747,6 +747,13 @@ class OdCdsXdstpIntegrationTest : public XdsTpConfigsIntegration {
747747
return builder.listener();
748748
}
749749

750+
envoy::config::endpoint::v3::ClusterLoadAssignment
751+
buildClusterLoadAssignment(const std::string& name, size_t upstream_idx) {
752+
return ConfigHelper::buildClusterLoadAssignment(
753+
name, Network::Test::getLoopbackAddressString(ipVersion()),
754+
fake_upstreams_[upstream_idx]->localAddress()->ip()->port());
755+
}
756+
750757
bool compareRequest(const std::string& type_url,
751758
const std::vector<std::string>& expected_resource_subscriptions,
752759
const std::vector<std::string>& expected_resource_unsubscriptions,
@@ -919,6 +926,72 @@ TEST_P(OdCdsXdstpIntegrationTest, OnDemandClusterDiscoveryAsksForNonexistentClus
919926
cleanupUpstreamAndDownstream();
920927
}
921928

929+
// tests a scenario when:
930+
// - making a request to an unknown cluster
931+
// - odcds initiates a connection with a request for the cluster
932+
// - a response contains an EDS cluster
933+
// - an EDS request is sent to the same authority
934+
// - an EDS response is received
935+
// - request is resumed
936+
TEST_P(OdCdsXdstpIntegrationTest, OnDemandCdsWithEds) {
937+
initialize();
938+
codec_client_ = makeHttpConnection(makeClientConnection(lookupPort("http")));
939+
const std::string cds_cluster_name =
940+
"xdstp://authority1.com/envoy.config.cluster.v3.Cluster/on_demand_clusters/"
941+
"new_cluster_with_eds";
942+
const std::string eds_service_name =
943+
"xdstp://authority1.com/envoy.config.endpoint.v3.ClusterLoadAssignment/on_demand_clusters/"
944+
"new_cluster_with_eds";
945+
946+
envoy::config::cluster::v3::Cluster new_cluster_with_eds;
947+
new_cluster_with_eds.set_name(cds_cluster_name);
948+
new_cluster_with_eds.set_type(envoy::config::cluster::v3::Cluster::EDS);
949+
auto* eds_cluster_config = new_cluster_with_eds.mutable_eds_cluster_config();
950+
eds_cluster_config->set_service_name(eds_service_name);
951+
ConfigHelper::setHttp2(new_cluster_with_eds);
952+
953+
Http::TestRequestHeaderMapImpl request_headers{{":method", "GET"},
954+
{":path", "/"},
955+
{":scheme", "http"},
956+
{":authority", "vhost.first"},
957+
{"Pick-This-Cluster", cds_cluster_name}};
958+
IntegrationStreamDecoderPtr response = codec_client_->makeHeaderOnlyRequest(request_headers);
959+
960+
// Authority1 should receive the ODCDS request.
961+
EXPECT_TRUE(compareDiscoveryRequest(
962+
Config::TestTypeUrl::get().Cluster, "", {cds_cluster_name}, {cds_cluster_name}, {}, true,
963+
Grpc::Status::WellKnownGrpcStatus::Ok, "", authority1_xds_stream_.get()));
964+
sendDiscoveryResponse<envoy::config::cluster::v3::Cluster>(
965+
Config::TestTypeUrl::get().Cluster, {new_cluster_with_eds}, {new_cluster_with_eds}, {}, "1",
966+
{}, authority1_xds_stream_.get());
967+
// After the CDS response, Envoy will send an EDS request for the new cluster.
968+
EXPECT_TRUE(compareDiscoveryRequest(
969+
Config::TestTypeUrl::get().ClusterLoadAssignment, "", {eds_service_name}, {eds_service_name},
970+
{}, false, Grpc::Status::WellKnownGrpcStatus::Ok, "", authority1_xds_stream_.get()));
971+
sendDiscoveryResponse<envoy::config::endpoint::v3::ClusterLoadAssignment>(
972+
Config::TestTypeUrl::get().ClusterLoadAssignment,
973+
{buildClusterLoadAssignment(eds_service_name, new_cluster_upstream_idx_)},
974+
{buildClusterLoadAssignment(eds_service_name, new_cluster_upstream_idx_)}, {}, "2", {},
975+
authority1_xds_stream_.get());
976+
// Now, Envoy should ACK the original CDS response.
977+
EXPECT_TRUE(compareDiscoveryRequest(Config::TestTypeUrl::get().Cluster, "1", {cds_cluster_name},
978+
{}, {}, false, Grpc::Status::WellKnownGrpcStatus::Ok, "",
979+
authority1_xds_stream_.get()));
980+
// And finally, Envoy should ACK the EDS response.
981+
EXPECT_TRUE(compareDiscoveryRequest(
982+
Config::TestTypeUrl::get().ClusterLoadAssignment, "2", {eds_service_name}, {}, {}, false,
983+
Grpc::Status::WellKnownGrpcStatus::Ok, "", authority1_xds_stream_.get()));
984+
985+
waitForNextUpstreamRequest(new_cluster_upstream_idx_);
986+
// Send response headers, and end_stream if there is no response body.
987+
upstream_request_->encodeHeaders(default_response_headers_, true);
988+
989+
ASSERT_TRUE(response->waitForEndStream());
990+
verifyResponse(std::move(response), "200", {}, {});
991+
992+
cleanupUpstreamAndDownstream();
993+
}
994+
922995
class OdCdsScopedRdsIntegrationTestBase : public ScopedRdsIntegrationTest {
923996
public:
924997
void addOnDemandConfig(OdCdsIntegrationHelper::OnDemandConfig config) {

0 commit comments

Comments
 (0)