From 6ac4996bc9ae3c6a5b45d6ade2faf5a526b252de Mon Sep 17 00:00:00 2001 From: Yuchen Dai Date: Tue, 16 Feb 2021 15:17:33 -0800 Subject: [PATCH 1/5] split tcp_proxy test into config test and data test Signed-off-by: Yuchen Dai --- test/common/tcp_proxy/BUILD | 36 +- test/common/tcp_proxy/config_test.cc | 1059 +++++++++++++++++ test/common/tcp_proxy/tcp_proxy_test.cc | 1182 +------------------ test/common/tcp_proxy/tcp_proxy_test_base.h | 185 +++ 4 files changed, 1283 insertions(+), 1179 deletions(-) create mode 100644 test/common/tcp_proxy/config_test.cc create mode 100644 test/common/tcp_proxy/tcp_proxy_test_base.h diff --git a/test/common/tcp_proxy/BUILD b/test/common/tcp_proxy/BUILD index 769badd15355..f274aa3d0d81 100644 --- a/test/common/tcp_proxy/BUILD +++ b/test/common/tcp_proxy/BUILD @@ -1,6 +1,7 @@ load( "//bazel:envoy_build_system.bzl", "envoy_cc_test", + "envoy_cc_test_library", "envoy_package", ) @@ -8,9 +9,11 @@ licenses(["notice"]) # Apache 2 envoy_package() -envoy_cc_test( - name = "tcp_proxy_test", - srcs = ["tcp_proxy_test.cc"], +envoy_cc_test_library( + name = "tcp_proxy_test_base", + srcs = [ + "tcp_proxy_test_base.h", + ], deps = [ "//source/common/buffer:buffer_lib", "//source/common/event:dispatcher_lib", @@ -33,6 +36,7 @@ envoy_cc_test( "//test/mocks/server:instance_mocks", "//test/mocks/ssl:ssl_mocks", "//test/mocks/stream_info:stream_info_mocks", + "//test/mocks/upstream:cluster_manager_mocks", "//test/mocks/upstream:host_mocks", "//test/test_common:test_runtime_lib", "@envoy_api//envoy/config/accesslog/v3:pkg_cc_proto", @@ -43,6 +47,31 @@ envoy_cc_test( ], ) +envoy_cc_test( + name = "config_test", + srcs = [ + "config_test.cc", + ], + deps = [ + ":tcp_proxy_test_base", + ], +) + +envoy_cc_test( + name = "tcp_proxy_test", + srcs = [ + "tcp_proxy_test.cc", + ], + deps = [ + ":tcp_proxy_test_base", + "@envoy_api//envoy/config/accesslog/v3:pkg_cc_proto", + "@envoy_api//envoy/extensions/access_loggers/file/v3:pkg_cc_proto", + "@envoy_api//envoy/extensions/filters/network/tcp_proxy/v3:pkg_cc_proto", + "@envoy_api//envoy/extensions/upstreams/http/generic/v3:pkg_cc_proto", + "@envoy_api//envoy/extensions/upstreams/tcp/generic/v3:pkg_cc_proto", + ], +) + envoy_cc_test( name = "upstream_test", srcs = ["upstream_test.cc"], @@ -50,5 +79,6 @@ envoy_cc_test( "//source/common/tcp_proxy", "//test/mocks/http:http_mocks", "//test/mocks/tcp:tcp_mocks", + "//test/mocks/upstream:cluster_manager_mocks", ], ) diff --git a/test/common/tcp_proxy/config_test.cc b/test/common/tcp_proxy/config_test.cc new file mode 100644 index 000000000000..ffebeb1bacbb --- /dev/null +++ b/test/common/tcp_proxy/config_test.cc @@ -0,0 +1,1059 @@ +#include "test/common/tcp_proxy/tcp_proxy_test_base.h" + +namespace Envoy { +namespace TcpProxy { + +namespace { +TEST(ConfigTest, DefaultTimeout) { + const std::string yaml = R"EOF( +stat_prefix: name +cluster: foo +)EOF"; + + NiceMock factory_context; + Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); + EXPECT_EQ(std::chrono::hours(1), config_obj.sharedConfig()->idleTimeout().value()); +} + +TEST(ConfigTest, DisabledTimeout) { + const std::string yaml = R"EOF( +stat_prefix: name +cluster: foo +idle_timeout: 0s +)EOF"; + + NiceMock factory_context; + Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); + EXPECT_FALSE(config_obj.sharedConfig()->idleTimeout().has_value()); +} + +TEST(ConfigTest, CustomTimeout) { + const std::string yaml = R"EOF( +stat_prefix: name +cluster: foo +idle_timeout: 1s +)EOF"; + + NiceMock factory_context; + Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); + EXPECT_EQ(std::chrono::seconds(1), config_obj.sharedConfig()->idleTimeout().value()); +} + +TEST(ConfigTest, MaxDownstreamConnectionDuration) { + const std::string yaml = R"EOF( +stat_prefix: name +cluster: foo +max_downstream_connection_duration: 10s +)EOF"; + + NiceMock factory_context; + Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); + EXPECT_EQ(std::chrono::seconds(10), config_obj.maxDownstreamConnectionDuration().value()); +} + +TEST(ConfigTest, NoRouteConfig) { + const std::string yaml = R"EOF( + stat_prefix: name + )EOF"; + + NiceMock factory_context; + EXPECT_THROW(constructConfigFromYaml(yaml, factory_context), EnvoyException); +} + +TEST(ConfigTest, DEPRECATED_FEATURE_TEST(BadConfig)) { + const std::string yaml_string = R"EOF( + stat_prefix: 1 + cluster: cluster + deprecated_v1: + routes: + - cluster: fake_cluster + )EOF"; + + NiceMock factory_context; + EXPECT_THROW(constructConfigFromYaml(yaml_string, factory_context, false), EnvoyException); +} + +TEST(ConfigTest, DEPRECATED_FEATURE_TEST(EmptyRouteConfig)) { + const std::string yaml = R"EOF( + stat_prefix: name + cluster: cluster + deprecated_v1: + routes: [] + )EOF"; + + NiceMock factory_context_; + EXPECT_THROW(constructConfigFromYaml(yaml, factory_context_, false), EnvoyException); +} + +TEST(ConfigTest, DEPRECATED_FEATURE_TEST(Routes)) { + TestDeprecatedV2Api _deprecated_v2_api; + const std::string yaml = R"EOF( + stat_prefix: name + cluster: cluster + deprecated_v1: + routes: + - destination_ip_list: + - address_prefix: 10.10.10.10 + prefix_len: 32 + - address_prefix: 10.10.11.0 + prefix_len: 24 + - address_prefix: 10.11.0.0 + prefix_len: 16 + - address_prefix: 11.0.0.0 + prefix_len: 8 + - address_prefix: 128.0.0.0 + prefix_len: 1 + cluster: with_destination_ip_list + - destination_ip_list: + - address_prefix: "::1" + prefix_len: 128 + - address_prefix: "2001:abcd::" + prefix_len: 64 + cluster: with_v6_destination + - destination_ports: 1-1024,2048-4096,12345 + cluster: with_destination_ports + - source_ports: '23457,23459' + cluster: with_source_ports + - destination_ip_list: + - address_prefix: "2002::" + prefix_len: 32 + source_ip_list: + - address_prefix: "2003::" + prefix_len: 64 + cluster: with_v6_source_and_destination + - destination_ip_list: + - address_prefix: 10.0.0.0 + prefix_len: 24 + source_ip_list: + - address_prefix: 20.0.0.0 + prefix_len: 24 + destination_ports: '10000' + source_ports: '20000' + cluster: with_everything + - cluster: catch_all + )EOF"; + + NiceMock factory_context_; + Config config_obj(constructConfigFromYaml(yaml, factory_context_, false)); + + { + // hit route with destination_ip (10.10.10.10/32) + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("10.10.10.10")); + EXPECT_EQ(std::string("with_destination_ip_list"), + config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // fall-through + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("10.10.10.11")); + connection.stream_info_.downstream_address_provider_->setRemoteAddress( + std::make_shared("0.0.0.0")); + EXPECT_EQ(std::string("catch_all"), config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // hit route with destination_ip (10.10.11.0/24) + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("10.10.11.11")); + EXPECT_EQ(std::string("with_destination_ip_list"), + config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // fall-through + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("10.10.12.12")); + connection.stream_info_.downstream_address_provider_->setRemoteAddress( + std::make_shared("0.0.0.0")); + EXPECT_EQ(std::string("catch_all"), config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // hit route with destination_ip (10.11.0.0/16) + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("10.11.11.11")); + EXPECT_EQ(std::string("with_destination_ip_list"), + config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // fall-through + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("10.12.12.12")); + connection.stream_info_.downstream_address_provider_->setRemoteAddress( + std::make_shared("0.0.0.0")); + EXPECT_EQ(std::string("catch_all"), config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // hit route with destination_ip (11.0.0.0/8) + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("11.11.11.11")); + EXPECT_EQ(std::string("with_destination_ip_list"), + config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // fall-through + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("12.12.12.12")); + connection.stream_info_.downstream_address_provider_->setRemoteAddress( + std::make_shared("0.0.0.0")); + EXPECT_EQ(std::string("catch_all"), config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // hit route with destination_ip (128.0.0.0/8) + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("128.255.255.255")); + EXPECT_EQ(std::string("with_destination_ip_list"), + config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // hit route with destination port range + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("1.2.3.4", 12345)); + EXPECT_EQ(std::string("with_destination_ports"), + config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // fall through + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("1.2.3.4", 23456)); + connection.stream_info_.downstream_address_provider_->setRemoteAddress( + std::make_shared("0.0.0.0")); + EXPECT_EQ(std::string("catch_all"), config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // hit route with source port range + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("1.2.3.4", 23456)); + connection.stream_info_.downstream_address_provider_->setRemoteAddress( + std::make_shared("0.0.0.0", 23459)); + EXPECT_EQ(std::string("with_source_ports"), + config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // fall through + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("1.2.3.4", 23456)); + connection.stream_info_.downstream_address_provider_->setRemoteAddress( + std::make_shared("0.0.0.0", 23458)); + EXPECT_EQ(std::string("catch_all"), config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // hit the route with all criteria present + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("10.0.0.0", 10000)); + connection.stream_info_.downstream_address_provider_->setRemoteAddress( + std::make_shared("20.0.0.0", 20000)); + EXPECT_EQ(std::string("with_everything"), + config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // fall through + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("10.0.0.0", 10000)); + connection.stream_info_.downstream_address_provider_->setRemoteAddress( + std::make_shared("30.0.0.0", 20000)); + EXPECT_EQ(std::string("catch_all"), config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // hit route with destination_ip (::1/128) + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("::1")); + EXPECT_EQ(std::string("with_v6_destination"), + config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // hit route with destination_ip ("2001:abcd/64") + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("2001:abcd:0:0:1::")); + EXPECT_EQ(std::string("with_v6_destination"), + config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // hit route with destination_ip ("2002::/32") and source_ip ("2003::/64") + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("2002:0:0:0:0:0::1")); + connection.stream_info_.downstream_address_provider_->setRemoteAddress( + std::make_shared("2003:0:0:0:0::5")); + EXPECT_EQ(std::string("with_v6_source_and_destination"), + config_obj.getRouteFromEntries(connection)->clusterName()); + } + + { + // fall through + NiceMock connection; + connection.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("2004::")); + connection.stream_info_.downstream_address_provider_->setRemoteAddress( + std::make_shared("::")); + EXPECT_EQ(std::string("catch_all"), config_obj.getRouteFromEntries(connection)->clusterName()); + } +} + +// Tests that a deprecated_v1 route gets the top-level endpoint selector. +TEST(ConfigTest, DEPRECATED_FEATURE_TEST(RouteWithTopLevelMetadataMatchConfig)) { + TestDeprecatedV2Api _deprecated_v2_api; + const std::string yaml = R"EOF( + stat_prefix: name + cluster: cluster + deprecated_v1: + routes: + - cluster: catch_all + metadata_match: + filter_metadata: + envoy.lb: + k1: v1 + k2: v2 +)EOF"; + + NiceMock factory_context_; + Config config_obj(constructConfigFromYaml(yaml, factory_context_, false)); + + ProtobufWkt::Value v1, v2; + v1.set_string_value("v1"); + v2.set_string_value("v2"); + HashedValue hv1(v1), hv2(v2); + + NiceMock connection; + const auto route = config_obj.getRouteFromEntries(connection); + EXPECT_NE(nullptr, route); + + EXPECT_EQ("catch_all", route->clusterName()); + + const auto* criteria = route->metadataMatchCriteria(); + EXPECT_NE(nullptr, criteria); + + const auto& criterions = criteria->metadataMatchCriteria(); + EXPECT_EQ(2, criterions.size()); + + EXPECT_EQ("k1", criterions[0]->name()); + EXPECT_EQ(hv1, criterions[0]->value()); + + EXPECT_EQ("k2", criterions[1]->name()); + EXPECT_EQ(hv2, criterions[1]->value()); +} + +// Tests that it's not possible to define a weighted cluster with 0 weight. +TEST(ConfigTest, WeightedClusterWithZeroWeightConfig) { + const std::string yaml = R"EOF( + stat_prefix: name + weighted_clusters: + clusters: + - name: cluster1 + weight: 1 + - name: cluster2 +)EOF"; + + NiceMock factory_context; + EXPECT_THROW(constructConfigFromV3Yaml(yaml, factory_context), EnvoyException); +} + +// Tests that it is possible to define a list of weighted clusters. +TEST(ConfigTest, WeightedClustersConfig) { + const std::string yaml = R"EOF( + stat_prefix: name + weighted_clusters: + clusters: + - name: cluster1 + weight: 1 + - name: cluster2 + weight: 2 +)EOF"; + + NiceMock factory_context; + Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); + + NiceMock connection; + EXPECT_CALL(factory_context.api_.random_, random()).WillOnce(Return(0)); + EXPECT_EQ(std::string("cluster1"), config_obj.getRouteFromEntries(connection)->clusterName()); + + EXPECT_CALL(factory_context.api_.random_, random()).WillOnce(Return(2)); + EXPECT_EQ(std::string("cluster2"), config_obj.getRouteFromEntries(connection)->clusterName()); +} + +// Tests that it is possible to define a list of weighted clusters with independent endpoint +// selectors. +TEST(ConfigTest, WeightedClustersWithMetadataMatchConfig) { + const std::string yaml = R"EOF( + stat_prefix: name + weighted_clusters: + clusters: + - name: cluster1 + weight: 1 + metadata_match: + filter_metadata: + envoy.lb: + k1: v1 + k2: v2 + - name: cluster2 + weight: 2 + metadata_match: + filter_metadata: + envoy.lb: + k3: v3 + k4: v4 +)EOF"; + + NiceMock factory_context; + Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); + + { + ProtobufWkt::Value v1, v2; + v1.set_string_value("v1"); + v2.set_string_value("v2"); + HashedValue hv1(v1), hv2(v2); + + NiceMock connection; + EXPECT_CALL(factory_context.api_.random_, random()).WillOnce(Return(0)); + + const auto route = config_obj.getRouteFromEntries(connection); + EXPECT_NE(nullptr, route); + + EXPECT_EQ("cluster1", route->clusterName()); + + const auto* criteria = route->metadataMatchCriteria(); + EXPECT_NE(nullptr, criteria); + + const auto& criterions = criteria->metadataMatchCriteria(); + EXPECT_EQ(2, criterions.size()); + + EXPECT_EQ("k1", criterions[0]->name()); + EXPECT_EQ(hv1, criterions[0]->value()); + + EXPECT_EQ("k2", criterions[1]->name()); + EXPECT_EQ(hv2, criterions[1]->value()); + } + + { + ProtobufWkt::Value v3, v4; + v3.set_string_value("v3"); + v4.set_string_value("v4"); + HashedValue hv3(v3), hv4(v4); + + NiceMock connection; + EXPECT_CALL(factory_context.api_.random_, random()).WillOnce(Return(2)); + + const auto route = config_obj.getRouteFromEntries(connection); + EXPECT_NE(nullptr, route); + + EXPECT_EQ("cluster2", route->clusterName()); + + const auto* criteria = route->metadataMatchCriteria(); + EXPECT_NE(nullptr, criteria); + + const auto& criterions = criteria->metadataMatchCriteria(); + EXPECT_EQ(2, criterions.size()); + + EXPECT_EQ("k3", criterions[0]->name()); + EXPECT_EQ(hv3, criterions[0]->value()); + + EXPECT_EQ("k4", criterions[1]->name()); + EXPECT_EQ(hv4, criterions[1]->value()); + } +} + +// Tests that an individual endpoint selector of a weighted cluster gets merged with the top-level +// endpoint selector. +TEST(ConfigTest, WeightedClustersWithMetadataMatchAndTopLevelMetadataMatchConfig) { + const std::string yaml = R"EOF( + stat_prefix: name + weighted_clusters: + clusters: + - name: cluster1 + weight: 1 + metadata_match: + filter_metadata: + envoy.lb: + k1: v1 + k2: v2 + - name: cluster2 + weight: 2 + metadata_match: + filter_metadata: + envoy.lb: + k3: v3 + k4: v4 + metadata_match: + filter_metadata: + envoy.lb: + k0: v00 + k1: v01 + k4: v04 +)EOF"; + + NiceMock factory_context; + Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); + + ProtobufWkt::Value v00, v01, v04; + v00.set_string_value("v00"); + v01.set_string_value("v01"); + v04.set_string_value("v04"); + HashedValue hv00(v00), hv01(v01), hv04(v04); + + { + ProtobufWkt::Value v1, v2; + v1.set_string_value("v1"); + v2.set_string_value("v2"); + HashedValue hv1(v1), hv2(v2); + + NiceMock connection; + EXPECT_CALL(factory_context.api_.random_, random()).WillOnce(Return(0)); + + const auto route = config_obj.getRouteFromEntries(connection); + EXPECT_NE(nullptr, route); + + EXPECT_EQ("cluster1", route->clusterName()); + + const auto* criteria = route->metadataMatchCriteria(); + EXPECT_NE(nullptr, criteria); + + const auto& criterions = criteria->metadataMatchCriteria(); + EXPECT_EQ(4, criterions.size()); + + EXPECT_EQ("k0", criterions[0]->name()); + EXPECT_EQ(hv00, criterions[0]->value()); + + EXPECT_EQ("k1", criterions[1]->name()); + EXPECT_EQ(hv1, criterions[1]->value()); + + EXPECT_EQ("k2", criterions[2]->name()); + EXPECT_EQ(hv2, criterions[2]->value()); + + EXPECT_EQ("k4", criterions[3]->name()); + EXPECT_EQ(hv04, criterions[3]->value()); + } + + { + ProtobufWkt::Value v3, v4; + v3.set_string_value("v3"); + v4.set_string_value("v4"); + HashedValue hv3(v3), hv4(v4); + + NiceMock connection; + EXPECT_CALL(factory_context.api_.random_, random()).WillOnce(Return(2)); + + const auto route = config_obj.getRouteFromEntries(connection); + EXPECT_NE(nullptr, route); + + EXPECT_EQ("cluster2", route->clusterName()); + + const auto* criteria = route->metadataMatchCriteria(); + EXPECT_NE(nullptr, criteria); + + const auto& criterions = criteria->metadataMatchCriteria(); + EXPECT_EQ(4, criterions.size()); + + EXPECT_EQ("k0", criterions[0]->name()); + EXPECT_EQ(hv00, criterions[0]->value()); + + EXPECT_EQ("k1", criterions[1]->name()); + EXPECT_EQ(hv01, criterions[1]->value()); + + EXPECT_EQ("k3", criterions[2]->name()); + EXPECT_EQ(hv3, criterions[2]->value()); + + EXPECT_EQ("k4", criterions[3]->name()); + EXPECT_EQ(hv4, criterions[3]->value()); + } +} + +// Tests that a weighted cluster gets the top-level endpoint selector. +TEST(ConfigTest, WeightedClustersWithTopLevelMetadataMatchConfig) { + const std::string yaml = R"EOF( + stat_prefix: name + weighted_clusters: + clusters: + - name: cluster1 + weight: 1 + metadata_match: + filter_metadata: + envoy.lb: + k1: v1 + k2: v2 +)EOF"; + + NiceMock factory_context; + Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); + + ProtobufWkt::Value v1, v2; + v1.set_string_value("v1"); + v2.set_string_value("v2"); + HashedValue hv1(v1), hv2(v2); + + NiceMock connection; + const auto route = config_obj.getRouteFromEntries(connection); + EXPECT_NE(nullptr, route); + + EXPECT_EQ("cluster1", route->clusterName()); + + const auto* criteria = route->metadataMatchCriteria(); + EXPECT_NE(nullptr, criteria); + + const auto& criterions = criteria->metadataMatchCriteria(); + EXPECT_EQ(2, criterions.size()); + + EXPECT_EQ("k1", criterions[0]->name()); + EXPECT_EQ(hv1, criterions[0]->value()); + + EXPECT_EQ("k2", criterions[1]->name()); + EXPECT_EQ(hv2, criterions[1]->value()); +} + +// Tests that it is possible to define the top-level endpoint selector. +TEST(ConfigTest, TopLevelMetadataMatchConfig) { + const std::string yaml = R"EOF( + stat_prefix: name + cluster: foo + metadata_match: + filter_metadata: + envoy.lb: + k1: v1 + k2: v2 +)EOF"; + + NiceMock factory_context; + Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); + + ProtobufWkt::Value v1, v2; + v1.set_string_value("v1"); + v2.set_string_value("v2"); + HashedValue hv1(v1), hv2(v2); + + const auto* criteria = config_obj.metadataMatchCriteria(); + EXPECT_NE(nullptr, criteria); + + const auto& criterions = criteria->metadataMatchCriteria(); + EXPECT_EQ(2, criterions.size()); + + EXPECT_EQ("k1", criterions[0]->name()); + EXPECT_EQ(hv1, criterions[0]->value()); + + EXPECT_EQ("k2", criterions[1]->name()); + EXPECT_EQ(hv2, criterions[1]->value()); +} + +// Tests that a regular cluster gets the top-level endpoint selector. +TEST(ConfigTest, ClusterWithTopLevelMetadataMatchConfig) { + const std::string yaml = R"EOF( + stat_prefix: name + cluster: foo + metadata_match: + filter_metadata: + envoy.lb: + k1: v1 + k2: v2 +)EOF"; + + NiceMock factory_context; + Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); + + ProtobufWkt::Value v1, v2; + v1.set_string_value("v1"); + v2.set_string_value("v2"); + HashedValue hv1(v1), hv2(v2); + + NiceMock connection; + const auto route = config_obj.getRouteFromEntries(connection); + EXPECT_NE(nullptr, route); + + EXPECT_EQ("foo", route->clusterName()); + + const auto* criteria = route->metadataMatchCriteria(); + EXPECT_NE(nullptr, criteria); + + const auto& criterions = criteria->metadataMatchCriteria(); + EXPECT_EQ(2, criterions.size()); + + EXPECT_EQ("k1", criterions[0]->name()); + EXPECT_EQ(hv1, criterions[0]->value()); + + EXPECT_EQ("k2", criterions[1]->name()); + EXPECT_EQ(hv2, criterions[1]->value()); +} + +// Tests that a per connection cluster gets the top-level endpoint selector. +TEST(ConfigTest, PerConnectionClusterWithTopLevelMetadataMatchConfig) { + const std::string yaml = R"EOF( + stat_prefix: name + cluster: foo + metadata_match: + filter_metadata: + envoy.lb: + k1: v1 + k2: v2 +)EOF"; + + NiceMock factory_context; + Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); + + ProtobufWkt::Value v1, v2; + v1.set_string_value("v1"); + v2.set_string_value("v2"); + HashedValue hv1(v1), hv2(v2); + + NiceMock connection; + connection.stream_info_.filterState()->setData( + "envoy.tcp_proxy.cluster", std::make_unique("filter_state_cluster"), + StreamInfo::FilterState::StateType::Mutable, StreamInfo::FilterState::LifeSpan::Connection); + + const auto route = config_obj.getRouteFromEntries(connection); + EXPECT_NE(nullptr, route); + + EXPECT_EQ("filter_state_cluster", route->clusterName()); + + const auto* criteria = route->metadataMatchCriteria(); + EXPECT_NE(nullptr, criteria); + + const auto& criterions = criteria->metadataMatchCriteria(); + EXPECT_EQ(2, criterions.size()); + + EXPECT_EQ("k1", criterions[0]->name()); + EXPECT_EQ(hv1, criterions[0]->value()); + + EXPECT_EQ("k2", criterions[1]->name()); + EXPECT_EQ(hv2, criterions[1]->value()); +} + +TEST(ConfigTest, HashWithSourceIpConfig) { + const std::string yaml = R"EOF( + stat_prefix: name + cluster: foo + hash_policy: + - source_ip: {} +)EOF"; + + NiceMock factory_context; + Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); + EXPECT_NE(nullptr, config_obj.hashPolicy()); +} + +TEST(ConfigTest, HashWithSourceIpDefaultConfig) { + const std::string yaml = R"EOF( + stat_prefix: name + cluster: foo +)EOF"; + + NiceMock factory_context; + Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); + EXPECT_EQ(nullptr, config_obj.hashPolicy()); +} + +TEST(ConfigTest, AccessLogConfig) { + envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy config; + envoy::config::accesslog::v3::AccessLog* log = config.mutable_access_log()->Add(); + log->set_name(Extensions::AccessLoggers::AccessLogNames::get().File); + { + envoy::extensions::access_loggers::file::v3::FileAccessLog file_access_log; + file_access_log.set_path("some_path"); + file_access_log.mutable_log_format()->mutable_text_format_source()->set_inline_string( + "the format specifier"); + log->mutable_typed_config()->PackFrom(file_access_log); + } + + log = config.mutable_access_log()->Add(); + log->set_name(Extensions::AccessLoggers::AccessLogNames::get().File); + { + envoy::extensions::access_loggers::file::v3::FileAccessLog file_access_log; + file_access_log.set_path("another path"); + log->mutable_typed_config()->PackFrom(file_access_log); + } + + NiceMock factory_context_; + Config config_obj(config, factory_context_); + + EXPECT_EQ(2, config_obj.accessLogs().size()); +} + +class TcpProxyRoutingTest : public testing::Test { +public: + TcpProxyRoutingTest() = default; + + void setup(bool avoid_boosting = true) { + const std::string yaml = R"EOF( + stat_prefix: name + cluster: fallback_cluster + deprecated_v1: + routes: + - destination_ports: 1-9999 + cluster: fake_cluster + )EOF"; + + factory_context_.cluster_manager_.initializeThreadLocalClusters( + {"fallback_cluster", "fake_cluster"}); + config_ = + std::make_shared(constructConfigFromYaml(yaml, factory_context_, avoid_boosting)); + } + + void initializeFilter() { + EXPECT_CALL(filter_callbacks_, connection()).WillRepeatedly(ReturnRef(connection_)); + + filter_ = std::make_unique(config_, factory_context_.cluster_manager_); + filter_->initializeReadFilterCallbacks(filter_callbacks_); + } + + Event::TestTimeSystem& timeSystem() { return factory_context_.timeSystem(); } + + NiceMock factory_context_; + ConfigSharedPtr config_; + NiceMock connection_; + NiceMock filter_callbacks_; + std::unique_ptr filter_; +}; + +TEST_F(TcpProxyRoutingTest, DEPRECATED_FEATURE_TEST(NonRoutableConnection)) { + TestDeprecatedV2Api _deprecated_v2_api; + setup(false); + + const uint32_t total_cx = config_->stats().downstream_cx_total_.value(); + const uint32_t non_routable_cx = config_->stats().downstream_cx_no_route_.value(); + + initializeFilter(); + + // Port 10000 is outside the specified destination port range. + connection_.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("1.2.3.4", 10000)); + + // Expect filter to try to open a connection to the fallback cluster. + EXPECT_CALL(factory_context_.cluster_manager_.thread_local_cluster_, tcpConnPool(_, _)) + .WillOnce(Return(nullptr)); + + filter_->onNewConnection(); + + EXPECT_EQ(total_cx + 1, config_->stats().downstream_cx_total_.value()); + EXPECT_EQ(non_routable_cx, config_->stats().downstream_cx_no_route_.value()); +} + +TEST_F(TcpProxyRoutingTest, DEPRECATED_FEATURE_TEST(RoutableConnection)) { + TestDeprecatedV2Api _deprecated_v2_api; + setup(false); + + const uint32_t total_cx = config_->stats().downstream_cx_total_.value(); + const uint32_t non_routable_cx = config_->stats().downstream_cx_no_route_.value(); + + initializeFilter(); + + // Port 9999 is within the specified destination port range. + connection_.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("1.2.3.4", 9999)); + + // Expect filter to try to open a connection to specified cluster. + EXPECT_CALL(factory_context_.cluster_manager_.thread_local_cluster_, tcpConnPool(_, _)) + .WillOnce(Return(nullptr)); + + filter_->onNewConnection(); + + EXPECT_EQ(total_cx + 1, config_->stats().downstream_cx_total_.value()); + EXPECT_EQ(non_routable_cx, config_->stats().downstream_cx_no_route_.value()); +} + +// Test that the tcp proxy uses the cluster from FilterState if set +TEST_F(TcpProxyRoutingTest, DEPRECATED_FEATURE_TEST(UseClusterFromPerConnectionCluster)) { + TestDeprecatedV2Api _deprecated_v2_api; + setup(false); + initializeFilter(); + + factory_context_.cluster_manager_.initializeThreadLocalClusters({"filter_state_cluster"}); + connection_.streamInfo().filterState()->setData( + "envoy.tcp_proxy.cluster", std::make_unique("filter_state_cluster"), + StreamInfo::FilterState::StateType::Mutable, StreamInfo::FilterState::LifeSpan::Connection); + + // Expect filter to try to open a connection to specified cluster. + EXPECT_CALL(factory_context_.cluster_manager_.thread_local_cluster_, tcpConnPool(_, _)) + .WillOnce(Return(nullptr)); + + filter_->onNewConnection(); +} + +// Test that the tcp proxy forwards the requested server name from FilterState if set +TEST_F(TcpProxyRoutingTest, DEPRECATED_FEATURE_TEST(UpstreamServerName)) { + TestDeprecatedV2Api _deprecated_v2_api; + setup(false); + initializeFilter(); + + connection_.streamInfo().filterState()->setData( + "envoy.network.upstream_server_name", std::make_unique("www.example.com"), + StreamInfo::FilterState::StateType::ReadOnly, StreamInfo::FilterState::LifeSpan::Connection); + + // Expect filter to try to open a connection to a cluster with the transport socket options with + // override-server-name + EXPECT_CALL(factory_context_.cluster_manager_.thread_local_cluster_, tcpConnPool(_, _)) + .WillOnce( + Invoke([](Upstream::ResourcePriority, + Upstream::LoadBalancerContext* context) -> Tcp::ConnectionPool::Instance* { + Network::TransportSocketOptionsSharedPtr transport_socket_options = + context->upstreamTransportSocketOptions(); + EXPECT_NE(transport_socket_options, nullptr); + EXPECT_TRUE(transport_socket_options->serverNameOverride().has_value()); + EXPECT_EQ(transport_socket_options->serverNameOverride().value(), "www.example.com"); + return nullptr; + })); + + // Port 9999 is within the specified destination port range. + connection_.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("1.2.3.4", 9999)); + + filter_->onNewConnection(); +} + +// Test that the tcp proxy override ALPN from FilterState if set +TEST_F(TcpProxyRoutingTest, DEPRECATED_FEATURE_TEST(ApplicationProtocols)) { + TestDeprecatedV2Api _deprecated_v2_api; + setup(false); + initializeFilter(); + + connection_.streamInfo().filterState()->setData( + Network::ApplicationProtocols::key(), + std::make_unique(std::vector{"foo", "bar"}), + StreamInfo::FilterState::StateType::ReadOnly, StreamInfo::FilterState::LifeSpan::Connection); + + // Expect filter to try to open a connection to a cluster with the transport socket options with + // override-application-protocol + EXPECT_CALL(factory_context_.cluster_manager_.thread_local_cluster_, tcpConnPool(_, _)) + .WillOnce( + Invoke([](Upstream::ResourcePriority, + Upstream::LoadBalancerContext* context) -> Tcp::ConnectionPool::Instance* { + Network::TransportSocketOptionsSharedPtr transport_socket_options = + context->upstreamTransportSocketOptions(); + EXPECT_NE(transport_socket_options, nullptr); + EXPECT_FALSE(transport_socket_options->applicationProtocolListOverride().empty()); + EXPECT_EQ(transport_socket_options->applicationProtocolListOverride().size(), 2); + EXPECT_EQ(transport_socket_options->applicationProtocolListOverride()[0], "foo"); + EXPECT_EQ(transport_socket_options->applicationProtocolListOverride()[1], "bar"); + return nullptr; + })); + + // Port 9999 is within the specified destination port range. + connection_.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("1.2.3.4", 9999)); + + filter_->onNewConnection(); +} + +class TcpProxyNonDeprecatedConfigRoutingTest : public TcpProxyRoutingTest { +public: + TcpProxyNonDeprecatedConfigRoutingTest() = default; + + void setup() { + const std::string yaml = R"EOF( + stat_prefix: name + cluster: fake_cluster + )EOF"; + + factory_context_.cluster_manager_.initializeThreadLocalClusters({"fake_cluster"}); + config_ = std::make_shared(constructConfigFromYaml(yaml, factory_context_)); + } +}; + +TEST_F(TcpProxyNonDeprecatedConfigRoutingTest, ClusterNameSet) { + setup(); + + initializeFilter(); + + // Port 9999 is within the specified destination port range. + connection_.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("1.2.3.4", 9999)); + + // Expect filter to try to open a connection to specified cluster. + EXPECT_CALL(factory_context_.cluster_manager_.thread_local_cluster_, tcpConnPool(_, _)) + .WillOnce(Return(nullptr)); + absl::optional cluster_info; + EXPECT_CALL(connection_.stream_info_, setUpstreamClusterInfo(_)) + .WillOnce( + Invoke([&cluster_info](const Upstream::ClusterInfoConstSharedPtr& upstream_cluster_info) { + cluster_info = upstream_cluster_info; + })); + EXPECT_CALL(connection_.stream_info_, upstreamClusterInfo()) + .WillOnce(ReturnPointee(&cluster_info)); + + filter_->onNewConnection(); + + EXPECT_EQ(connection_.stream_info_.upstreamClusterInfo().value()->name(), "fake_cluster"); +} + +class TcpProxyHashingTest : public testing::Test { +public: + TcpProxyHashingTest() = default; + + void setup() { + const std::string yaml = R"EOF( + stat_prefix: name + cluster: fake_cluster + hash_policy: + - source_ip: {} + )EOF"; + + factory_context_.cluster_manager_.initializeThreadLocalClusters({"fake_cluster"}); + config_ = std::make_shared(constructConfigFromYaml(yaml, factory_context_)); + } + + void initializeFilter() { + EXPECT_CALL(filter_callbacks_, connection()).WillRepeatedly(ReturnRef(connection_)); + + filter_ = std::make_unique(config_, factory_context_.cluster_manager_); + filter_->initializeReadFilterCallbacks(filter_callbacks_); + } + + Event::TestTimeSystem& timeSystem() { return factory_context_.timeSystem(); } + + NiceMock factory_context_; + ConfigSharedPtr config_; + NiceMock connection_; + NiceMock filter_callbacks_; + std::unique_ptr filter_; +}; + +// Test TCP proxy use source IP to hash. +TEST_F(TcpProxyHashingTest, HashWithSourceIp) { + setup(); + initializeFilter(); + EXPECT_CALL(factory_context_.cluster_manager_.thread_local_cluster_, tcpConnPool(_, _)) + .WillOnce( + Invoke([](Upstream::ResourcePriority, + Upstream::LoadBalancerContext* context) -> Tcp::ConnectionPool::Instance* { + EXPECT_TRUE(context->computeHashKey().has_value()); + return nullptr; + })); + + connection_.stream_info_.downstream_address_provider_->setRemoteAddress( + std::make_shared("1.2.3.4", 1111)); + connection_.stream_info_.downstream_address_provider_->setLocalAddress( + std::make_shared("2.3.4.5", 2222)); + + filter_->onNewConnection(); +} + +} // namespace +} // namespace TcpProxy +} // namespace Envoy \ No newline at end of file diff --git a/test/common/tcp_proxy/tcp_proxy_test.cc b/test/common/tcp_proxy/tcp_proxy_test.cc index 93284d71df4b..d0c1d5f7c8d1 100644 --- a/test/common/tcp_proxy/tcp_proxy_test.cc +++ b/test/common/tcp_proxy/tcp_proxy_test.cc @@ -23,6 +23,7 @@ #include "extensions/access_loggers/well_known_names.h" +#include "test/common/tcp_proxy/tcp_proxy_test_base.h" #include "test/common/upstream/utility.h" #include "test/mocks/buffer/mocks.h" #include "test/mocks/network/mocks.h" @@ -41,6 +42,7 @@ namespace Envoy { namespace TcpProxy { + namespace { using ::Envoy::Network::UpstreamServerName; @@ -54,870 +56,11 @@ using ::testing::ReturnPointee; using ::testing::ReturnRef; using ::testing::SaveArg; -namespace { -Config constructConfigFromYaml(const std::string& yaml, - Server::Configuration::FactoryContext& context, - bool avoid_boosting = true) { - envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy tcp_proxy; - TestUtility::loadFromYamlAndValidate(yaml, tcp_proxy, false, avoid_boosting); - return Config(tcp_proxy, context); -} - -Config constructConfigFromV3Yaml(const std::string& yaml, - Server::Configuration::FactoryContext& context, - bool avoid_boosting = true) { - envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy tcp_proxy; - TestUtility::loadFromYamlAndValidate(yaml, tcp_proxy, false, avoid_boosting); - return Config(tcp_proxy, context); -} - -} // namespace - -TEST(ConfigTest, DefaultTimeout) { - const std::string yaml = R"EOF( -stat_prefix: name -cluster: foo -)EOF"; - - NiceMock factory_context; - Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); - EXPECT_EQ(std::chrono::hours(1), config_obj.sharedConfig()->idleTimeout().value()); -} - -TEST(ConfigTest, DisabledTimeout) { - const std::string yaml = R"EOF( -stat_prefix: name -cluster: foo -idle_timeout: 0s -)EOF"; - - NiceMock factory_context; - Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); - EXPECT_FALSE(config_obj.sharedConfig()->idleTimeout().has_value()); -} - -TEST(ConfigTest, CustomTimeout) { - const std::string yaml = R"EOF( -stat_prefix: name -cluster: foo -idle_timeout: 1s -)EOF"; - - NiceMock factory_context; - Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); - EXPECT_EQ(std::chrono::seconds(1), config_obj.sharedConfig()->idleTimeout().value()); -} - -TEST(ConfigTest, MaxDownstreamConnectionDuration) { - const std::string yaml = R"EOF( -stat_prefix: name -cluster: foo -max_downstream_connection_duration: 10s -)EOF"; - - NiceMock factory_context; - Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); - EXPECT_EQ(std::chrono::seconds(10), config_obj.maxDownstreamConnectionDuration().value()); -} - -TEST(ConfigTest, NoRouteConfig) { - const std::string yaml = R"EOF( - stat_prefix: name - )EOF"; - - NiceMock factory_context; - EXPECT_THROW(constructConfigFromYaml(yaml, factory_context), EnvoyException); -} - -TEST(ConfigTest, DEPRECATED_FEATURE_TEST(BadConfig)) { - const std::string yaml_string = R"EOF( - stat_prefix: 1 - cluster: cluster - deprecated_v1: - routes: - - cluster: fake_cluster - )EOF"; - - NiceMock factory_context; - EXPECT_THROW(constructConfigFromYaml(yaml_string, factory_context, false), EnvoyException); -} - -TEST(ConfigTest, DEPRECATED_FEATURE_TEST(EmptyRouteConfig)) { - const std::string yaml = R"EOF( - stat_prefix: name - cluster: cluster - deprecated_v1: - routes: [] - )EOF"; - - NiceMock factory_context_; - EXPECT_THROW(constructConfigFromYaml(yaml, factory_context_, false), EnvoyException); -} - -TEST(ConfigTest, DEPRECATED_FEATURE_TEST(Routes)) { - TestDeprecatedV2Api _deprecated_v2_api; - const std::string yaml = R"EOF( - stat_prefix: name - cluster: cluster - deprecated_v1: - routes: - - destination_ip_list: - - address_prefix: 10.10.10.10 - prefix_len: 32 - - address_prefix: 10.10.11.0 - prefix_len: 24 - - address_prefix: 10.11.0.0 - prefix_len: 16 - - address_prefix: 11.0.0.0 - prefix_len: 8 - - address_prefix: 128.0.0.0 - prefix_len: 1 - cluster: with_destination_ip_list - - destination_ip_list: - - address_prefix: "::1" - prefix_len: 128 - - address_prefix: "2001:abcd::" - prefix_len: 64 - cluster: with_v6_destination - - destination_ports: 1-1024,2048-4096,12345 - cluster: with_destination_ports - - source_ports: '23457,23459' - cluster: with_source_ports - - destination_ip_list: - - address_prefix: "2002::" - prefix_len: 32 - source_ip_list: - - address_prefix: "2003::" - prefix_len: 64 - cluster: with_v6_source_and_destination - - destination_ip_list: - - address_prefix: 10.0.0.0 - prefix_len: 24 - source_ip_list: - - address_prefix: 20.0.0.0 - prefix_len: 24 - destination_ports: '10000' - source_ports: '20000' - cluster: with_everything - - cluster: catch_all - )EOF"; - - NiceMock factory_context_; - Config config_obj(constructConfigFromYaml(yaml, factory_context_, false)); - - { - // hit route with destination_ip (10.10.10.10/32) - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("10.10.10.10")); - EXPECT_EQ(std::string("with_destination_ip_list"), - config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // fall-through - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("10.10.10.11")); - connection.stream_info_.downstream_address_provider_->setRemoteAddress( - std::make_shared("0.0.0.0")); - EXPECT_EQ(std::string("catch_all"), config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // hit route with destination_ip (10.10.11.0/24) - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("10.10.11.11")); - EXPECT_EQ(std::string("with_destination_ip_list"), - config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // fall-through - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("10.10.12.12")); - connection.stream_info_.downstream_address_provider_->setRemoteAddress( - std::make_shared("0.0.0.0")); - EXPECT_EQ(std::string("catch_all"), config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // hit route with destination_ip (10.11.0.0/16) - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("10.11.11.11")); - EXPECT_EQ(std::string("with_destination_ip_list"), - config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // fall-through - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("10.12.12.12")); - connection.stream_info_.downstream_address_provider_->setRemoteAddress( - std::make_shared("0.0.0.0")); - EXPECT_EQ(std::string("catch_all"), config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // hit route with destination_ip (11.0.0.0/8) - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("11.11.11.11")); - EXPECT_EQ(std::string("with_destination_ip_list"), - config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // fall-through - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("12.12.12.12")); - connection.stream_info_.downstream_address_provider_->setRemoteAddress( - std::make_shared("0.0.0.0")); - EXPECT_EQ(std::string("catch_all"), config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // hit route with destination_ip (128.0.0.0/8) - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("128.255.255.255")); - EXPECT_EQ(std::string("with_destination_ip_list"), - config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // hit route with destination port range - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("1.2.3.4", 12345)); - EXPECT_EQ(std::string("with_destination_ports"), - config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // fall through - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("1.2.3.4", 23456)); - connection.stream_info_.downstream_address_provider_->setRemoteAddress( - std::make_shared("0.0.0.0")); - EXPECT_EQ(std::string("catch_all"), config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // hit route with source port range - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("1.2.3.4", 23456)); - connection.stream_info_.downstream_address_provider_->setRemoteAddress( - std::make_shared("0.0.0.0", 23459)); - EXPECT_EQ(std::string("with_source_ports"), - config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // fall through - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("1.2.3.4", 23456)); - connection.stream_info_.downstream_address_provider_->setRemoteAddress( - std::make_shared("0.0.0.0", 23458)); - EXPECT_EQ(std::string("catch_all"), config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // hit the route with all criteria present - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("10.0.0.0", 10000)); - connection.stream_info_.downstream_address_provider_->setRemoteAddress( - std::make_shared("20.0.0.0", 20000)); - EXPECT_EQ(std::string("with_everything"), - config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // fall through - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("10.0.0.0", 10000)); - connection.stream_info_.downstream_address_provider_->setRemoteAddress( - std::make_shared("30.0.0.0", 20000)); - EXPECT_EQ(std::string("catch_all"), config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // hit route with destination_ip (::1/128) - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("::1")); - EXPECT_EQ(std::string("with_v6_destination"), - config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // hit route with destination_ip ("2001:abcd/64") - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("2001:abcd:0:0:1::")); - EXPECT_EQ(std::string("with_v6_destination"), - config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // hit route with destination_ip ("2002::/32") and source_ip ("2003::/64") - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("2002:0:0:0:0:0::1")); - connection.stream_info_.downstream_address_provider_->setRemoteAddress( - std::make_shared("2003:0:0:0:0::5")); - EXPECT_EQ(std::string("with_v6_source_and_destination"), - config_obj.getRouteFromEntries(connection)->clusterName()); - } - - { - // fall through - NiceMock connection; - connection.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("2004::")); - connection.stream_info_.downstream_address_provider_->setRemoteAddress( - std::make_shared("::")); - EXPECT_EQ(std::string("catch_all"), config_obj.getRouteFromEntries(connection)->clusterName()); - } -} - -// Tests that a deprecated_v1 route gets the top-level endpoint selector. -TEST(ConfigTest, DEPRECATED_FEATURE_TEST(RouteWithTopLevelMetadataMatchConfig)) { - TestDeprecatedV2Api _deprecated_v2_api; - const std::string yaml = R"EOF( - stat_prefix: name - cluster: cluster - deprecated_v1: - routes: - - cluster: catch_all - metadata_match: - filter_metadata: - envoy.lb: - k1: v1 - k2: v2 -)EOF"; - - NiceMock factory_context_; - Config config_obj(constructConfigFromYaml(yaml, factory_context_, false)); - - ProtobufWkt::Value v1, v2; - v1.set_string_value("v1"); - v2.set_string_value("v2"); - HashedValue hv1(v1), hv2(v2); - - NiceMock connection; - const auto route = config_obj.getRouteFromEntries(connection); - EXPECT_NE(nullptr, route); - - EXPECT_EQ("catch_all", route->clusterName()); - - const auto* criteria = route->metadataMatchCriteria(); - EXPECT_NE(nullptr, criteria); - - const auto& criterions = criteria->metadataMatchCriteria(); - EXPECT_EQ(2, criterions.size()); - - EXPECT_EQ("k1", criterions[0]->name()); - EXPECT_EQ(hv1, criterions[0]->value()); - - EXPECT_EQ("k2", criterions[1]->name()); - EXPECT_EQ(hv2, criterions[1]->value()); -} - -// Tests that it's not possible to define a weighted cluster with 0 weight. -TEST(ConfigTest, WeightedClusterWithZeroWeightConfig) { - const std::string yaml = R"EOF( - stat_prefix: name - weighted_clusters: - clusters: - - name: cluster1 - weight: 1 - - name: cluster2 -)EOF"; - - NiceMock factory_context; - EXPECT_THROW(constructConfigFromV3Yaml(yaml, factory_context), EnvoyException); -} - -// Tests that it is possible to define a list of weighted clusters. -TEST(ConfigTest, WeightedClustersConfig) { - const std::string yaml = R"EOF( - stat_prefix: name - weighted_clusters: - clusters: - - name: cluster1 - weight: 1 - - name: cluster2 - weight: 2 -)EOF"; - - NiceMock factory_context; - Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); - - NiceMock connection; - EXPECT_CALL(factory_context.api_.random_, random()).WillOnce(Return(0)); - EXPECT_EQ(std::string("cluster1"), config_obj.getRouteFromEntries(connection)->clusterName()); - - EXPECT_CALL(factory_context.api_.random_, random()).WillOnce(Return(2)); - EXPECT_EQ(std::string("cluster2"), config_obj.getRouteFromEntries(connection)->clusterName()); -} - -// Tests that it is possible to define a list of weighted clusters with independent endpoint -// selectors. -TEST(ConfigTest, WeightedClustersWithMetadataMatchConfig) { - const std::string yaml = R"EOF( - stat_prefix: name - weighted_clusters: - clusters: - - name: cluster1 - weight: 1 - metadata_match: - filter_metadata: - envoy.lb: - k1: v1 - k2: v2 - - name: cluster2 - weight: 2 - metadata_match: - filter_metadata: - envoy.lb: - k3: v3 - k4: v4 -)EOF"; - - NiceMock factory_context; - Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); - - { - ProtobufWkt::Value v1, v2; - v1.set_string_value("v1"); - v2.set_string_value("v2"); - HashedValue hv1(v1), hv2(v2); - - NiceMock connection; - EXPECT_CALL(factory_context.api_.random_, random()).WillOnce(Return(0)); - - const auto route = config_obj.getRouteFromEntries(connection); - EXPECT_NE(nullptr, route); - - EXPECT_EQ("cluster1", route->clusterName()); - - const auto* criteria = route->metadataMatchCriteria(); - EXPECT_NE(nullptr, criteria); - - const auto& criterions = criteria->metadataMatchCriteria(); - EXPECT_EQ(2, criterions.size()); - - EXPECT_EQ("k1", criterions[0]->name()); - EXPECT_EQ(hv1, criterions[0]->value()); - - EXPECT_EQ("k2", criterions[1]->name()); - EXPECT_EQ(hv2, criterions[1]->value()); - } - - { - ProtobufWkt::Value v3, v4; - v3.set_string_value("v3"); - v4.set_string_value("v4"); - HashedValue hv3(v3), hv4(v4); - - NiceMock connection; - EXPECT_CALL(factory_context.api_.random_, random()).WillOnce(Return(2)); - - const auto route = config_obj.getRouteFromEntries(connection); - EXPECT_NE(nullptr, route); - - EXPECT_EQ("cluster2", route->clusterName()); - - const auto* criteria = route->metadataMatchCriteria(); - EXPECT_NE(nullptr, criteria); - - const auto& criterions = criteria->metadataMatchCriteria(); - EXPECT_EQ(2, criterions.size()); - - EXPECT_EQ("k3", criterions[0]->name()); - EXPECT_EQ(hv3, criterions[0]->value()); - - EXPECT_EQ("k4", criterions[1]->name()); - EXPECT_EQ(hv4, criterions[1]->value()); - } -} - -// Tests that an individual endpoint selector of a weighted cluster gets merged with the top-level -// endpoint selector. -TEST(ConfigTest, WeightedClustersWithMetadataMatchAndTopLevelMetadataMatchConfig) { - const std::string yaml = R"EOF( - stat_prefix: name - weighted_clusters: - clusters: - - name: cluster1 - weight: 1 - metadata_match: - filter_metadata: - envoy.lb: - k1: v1 - k2: v2 - - name: cluster2 - weight: 2 - metadata_match: - filter_metadata: - envoy.lb: - k3: v3 - k4: v4 - metadata_match: - filter_metadata: - envoy.lb: - k0: v00 - k1: v01 - k4: v04 -)EOF"; - - NiceMock factory_context; - Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); - - ProtobufWkt::Value v00, v01, v04; - v00.set_string_value("v00"); - v01.set_string_value("v01"); - v04.set_string_value("v04"); - HashedValue hv00(v00), hv01(v01), hv04(v04); - - { - ProtobufWkt::Value v1, v2; - v1.set_string_value("v1"); - v2.set_string_value("v2"); - HashedValue hv1(v1), hv2(v2); - - NiceMock connection; - EXPECT_CALL(factory_context.api_.random_, random()).WillOnce(Return(0)); - - const auto route = config_obj.getRouteFromEntries(connection); - EXPECT_NE(nullptr, route); - - EXPECT_EQ("cluster1", route->clusterName()); - - const auto* criteria = route->metadataMatchCriteria(); - EXPECT_NE(nullptr, criteria); - - const auto& criterions = criteria->metadataMatchCriteria(); - EXPECT_EQ(4, criterions.size()); - - EXPECT_EQ("k0", criterions[0]->name()); - EXPECT_EQ(hv00, criterions[0]->value()); - - EXPECT_EQ("k1", criterions[1]->name()); - EXPECT_EQ(hv1, criterions[1]->value()); - - EXPECT_EQ("k2", criterions[2]->name()); - EXPECT_EQ(hv2, criterions[2]->value()); - - EXPECT_EQ("k4", criterions[3]->name()); - EXPECT_EQ(hv04, criterions[3]->value()); - } - - { - ProtobufWkt::Value v3, v4; - v3.set_string_value("v3"); - v4.set_string_value("v4"); - HashedValue hv3(v3), hv4(v4); - - NiceMock connection; - EXPECT_CALL(factory_context.api_.random_, random()).WillOnce(Return(2)); - - const auto route = config_obj.getRouteFromEntries(connection); - EXPECT_NE(nullptr, route); - - EXPECT_EQ("cluster2", route->clusterName()); - - const auto* criteria = route->metadataMatchCriteria(); - EXPECT_NE(nullptr, criteria); - - const auto& criterions = criteria->metadataMatchCriteria(); - EXPECT_EQ(4, criterions.size()); - - EXPECT_EQ("k0", criterions[0]->name()); - EXPECT_EQ(hv00, criterions[0]->value()); - - EXPECT_EQ("k1", criterions[1]->name()); - EXPECT_EQ(hv01, criterions[1]->value()); - - EXPECT_EQ("k3", criterions[2]->name()); - EXPECT_EQ(hv3, criterions[2]->value()); - - EXPECT_EQ("k4", criterions[3]->name()); - EXPECT_EQ(hv4, criterions[3]->value()); - } -} - -// Tests that a weighted cluster gets the top-level endpoint selector. -TEST(ConfigTest, WeightedClustersWithTopLevelMetadataMatchConfig) { - const std::string yaml = R"EOF( - stat_prefix: name - weighted_clusters: - clusters: - - name: cluster1 - weight: 1 - metadata_match: - filter_metadata: - envoy.lb: - k1: v1 - k2: v2 -)EOF"; - - NiceMock factory_context; - Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); - - ProtobufWkt::Value v1, v2; - v1.set_string_value("v1"); - v2.set_string_value("v2"); - HashedValue hv1(v1), hv2(v2); - - NiceMock connection; - const auto route = config_obj.getRouteFromEntries(connection); - EXPECT_NE(nullptr, route); - - EXPECT_EQ("cluster1", route->clusterName()); - - const auto* criteria = route->metadataMatchCriteria(); - EXPECT_NE(nullptr, criteria); - - const auto& criterions = criteria->metadataMatchCriteria(); - EXPECT_EQ(2, criterions.size()); - - EXPECT_EQ("k1", criterions[0]->name()); - EXPECT_EQ(hv1, criterions[0]->value()); - - EXPECT_EQ("k2", criterions[1]->name()); - EXPECT_EQ(hv2, criterions[1]->value()); -} - -// Tests that it is possible to define the top-level endpoint selector. -TEST(ConfigTest, TopLevelMetadataMatchConfig) { - const std::string yaml = R"EOF( - stat_prefix: name - cluster: foo - metadata_match: - filter_metadata: - envoy.lb: - k1: v1 - k2: v2 -)EOF"; - - NiceMock factory_context; - Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); - - ProtobufWkt::Value v1, v2; - v1.set_string_value("v1"); - v2.set_string_value("v2"); - HashedValue hv1(v1), hv2(v2); - - const auto* criteria = config_obj.metadataMatchCriteria(); - EXPECT_NE(nullptr, criteria); - - const auto& criterions = criteria->metadataMatchCriteria(); - EXPECT_EQ(2, criterions.size()); - - EXPECT_EQ("k1", criterions[0]->name()); - EXPECT_EQ(hv1, criterions[0]->value()); - - EXPECT_EQ("k2", criterions[1]->name()); - EXPECT_EQ(hv2, criterions[1]->value()); -} - -// Tests that a regular cluster gets the top-level endpoint selector. -TEST(ConfigTest, ClusterWithTopLevelMetadataMatchConfig) { - const std::string yaml = R"EOF( - stat_prefix: name - cluster: foo - metadata_match: - filter_metadata: - envoy.lb: - k1: v1 - k2: v2 -)EOF"; - - NiceMock factory_context; - Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); - - ProtobufWkt::Value v1, v2; - v1.set_string_value("v1"); - v2.set_string_value("v2"); - HashedValue hv1(v1), hv2(v2); - - NiceMock connection; - const auto route = config_obj.getRouteFromEntries(connection); - EXPECT_NE(nullptr, route); - - EXPECT_EQ("foo", route->clusterName()); - - const auto* criteria = route->metadataMatchCriteria(); - EXPECT_NE(nullptr, criteria); - - const auto& criterions = criteria->metadataMatchCriteria(); - EXPECT_EQ(2, criterions.size()); - - EXPECT_EQ("k1", criterions[0]->name()); - EXPECT_EQ(hv1, criterions[0]->value()); - - EXPECT_EQ("k2", criterions[1]->name()); - EXPECT_EQ(hv2, criterions[1]->value()); -} - -// Tests that a per connection cluster gets the top-level endpoint selector. -TEST(ConfigTest, PerConnectionClusterWithTopLevelMetadataMatchConfig) { - const std::string yaml = R"EOF( - stat_prefix: name - cluster: foo - metadata_match: - filter_metadata: - envoy.lb: - k1: v1 - k2: v2 -)EOF"; - - NiceMock factory_context; - Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); - - ProtobufWkt::Value v1, v2; - v1.set_string_value("v1"); - v2.set_string_value("v2"); - HashedValue hv1(v1), hv2(v2); - - NiceMock connection; - connection.stream_info_.filterState()->setData( - "envoy.tcp_proxy.cluster", std::make_unique("filter_state_cluster"), - StreamInfo::FilterState::StateType::Mutable, StreamInfo::FilterState::LifeSpan::Connection); - - const auto route = config_obj.getRouteFromEntries(connection); - EXPECT_NE(nullptr, route); - - EXPECT_EQ("filter_state_cluster", route->clusterName()); - - const auto* criteria = route->metadataMatchCriteria(); - EXPECT_NE(nullptr, criteria); - - const auto& criterions = criteria->metadataMatchCriteria(); - EXPECT_EQ(2, criterions.size()); - - EXPECT_EQ("k1", criterions[0]->name()); - EXPECT_EQ(hv1, criterions[0]->value()); - - EXPECT_EQ("k2", criterions[1]->name()); - EXPECT_EQ(hv2, criterions[1]->value()); -} - -TEST(ConfigTest, HashWithSourceIpConfig) { - const std::string yaml = R"EOF( - stat_prefix: name - cluster: foo - hash_policy: - - source_ip: {} -)EOF"; - - NiceMock factory_context; - Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); - EXPECT_NE(nullptr, config_obj.hashPolicy()); -} - -TEST(ConfigTest, HashWithSourceIpDefaultConfig) { - const std::string yaml = R"EOF( - stat_prefix: name - cluster: foo -)EOF"; - - NiceMock factory_context; - Config config_obj(constructConfigFromV3Yaml(yaml, factory_context)); - EXPECT_EQ(nullptr, config_obj.hashPolicy()); -} - -TEST(ConfigTest, AccessLogConfig) { - envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy config; - envoy::config::accesslog::v3::AccessLog* log = config.mutable_access_log()->Add(); - log->set_name(Extensions::AccessLoggers::AccessLogNames::get().File); - { - envoy::extensions::access_loggers::file::v3::FileAccessLog file_access_log; - file_access_log.set_path("some_path"); - file_access_log.mutable_log_format()->mutable_text_format_source()->set_inline_string( - "the format specifier"); - log->mutable_typed_config()->PackFrom(file_access_log); - } - - log = config.mutable_access_log()->Add(); - log->set_name(Extensions::AccessLoggers::AccessLogNames::get().File); - { - envoy::extensions::access_loggers::file::v3::FileAccessLog file_access_log; - file_access_log.set_path("another path"); - log->mutable_typed_config()->PackFrom(file_access_log); - } - - NiceMock factory_context_; - Config config_obj(config, factory_context_); - - EXPECT_EQ(2, config_obj.accessLogs().size()); -} - -class TcpProxyTest : public testing::Test { +class TcpProxyTest : public TcpProxyTestBase { public: - TcpProxyTest() { - ON_CALL(*factory_context_.access_log_manager_.file_, write(_)) - .WillByDefault(SaveArg<0>(&access_log_data_)); - ON_CALL(filter_callbacks_.connection_.stream_info_, onUpstreamHostSelected(_)) - .WillByDefault(Invoke( - [this](Upstream::HostDescriptionConstSharedPtr host) { upstream_host_ = host; })); - ON_CALL(filter_callbacks_.connection_.stream_info_, upstreamHost()) - .WillByDefault(ReturnPointee(&upstream_host_)); - ON_CALL(filter_callbacks_.connection_.stream_info_, setUpstreamClusterInfo(_)) - .WillByDefault(Invoke([this](const Upstream::ClusterInfoConstSharedPtr& cluster_info) { - upstream_cluster_ = cluster_info; - })); - ON_CALL(filter_callbacks_.connection_.stream_info_, upstreamClusterInfo()) - .WillByDefault(ReturnPointee(&upstream_cluster_)); - factory_context_.cluster_manager_.initializeThreadLocalClusters({"fake_cluster"}); - } - - ~TcpProxyTest() override { - if (filter_ != nullptr) { - filter_callbacks_.connection_.raiseEvent(Network::ConnectionEvent::RemoteClose); - } - } - - void configure(const envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy& config) { - config_ = std::make_shared(config, factory_context_); - } - - envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy defaultConfig() { - envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy config; - config.set_stat_prefix("name"); - auto* route = config.mutable_hidden_envoy_deprecated_deprecated_v1()->mutable_routes()->Add(); - route->set_cluster("fake_cluster"); - return config; - } - - // Return the default config, plus one file access log with the specified format - envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy - accessLogConfig(const std::string& access_log_format) { - envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy config = defaultConfig(); - envoy::config::accesslog::v3::AccessLog* access_log = config.mutable_access_log()->Add(); - access_log->set_name(Extensions::AccessLoggers::AccessLogNames::get().File); - envoy::extensions::access_loggers::file::v3::FileAccessLog file_access_log; - file_access_log.set_path("unused"); - file_access_log.mutable_log_format()->mutable_text_format_source()->set_inline_string( - access_log_format); - access_log->mutable_typed_config()->PackFrom(file_access_log); - return config; - } - + using TcpProxyTestBase::setup; void setup(uint32_t connections, - const envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy& config) { + const envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy& config) override { configure(config); upstream_local_address_ = Network::Utility::resolveUrl("tcp://2.2.2.2:50000"); upstream_remote_address_ = Network::Utility::resolveUrl("tcp://127.0.0.1:80"); @@ -970,60 +113,6 @@ class TcpProxyTest : public testing::Test { EXPECT_EQ(nullptr, filter_->metadataMatchCriteria()); } } - - void setup(uint32_t connections) { setup(connections, defaultConfig()); } - - void raiseEventUpstreamConnected(uint32_t conn_index) { - EXPECT_CALL(filter_callbacks_.connection_, readDisable(false)); - EXPECT_CALL(*upstream_connection_data_.at(conn_index), addUpstreamCallbacks(_)) - .WillOnce(Invoke([=](Tcp::ConnectionPool::UpstreamCallbacks& cb) -> void { - upstream_callbacks_ = &cb; - - // Simulate TCP conn pool upstream callbacks. This is safe because the TCP proxy never - // releases a connection so all events go to the same UpstreamCallbacks instance. - upstream_connections_.at(conn_index)->addConnectionCallbacks(cb); - })); - EXPECT_CALL(*upstream_connections_.at(conn_index), enableHalfClose(true)); - conn_pool_callbacks_.at(conn_index) - ->onPoolReady(std::move(upstream_connection_data_.at(conn_index)), - upstream_hosts_.at(conn_index)); - } - - void raiseEventUpstreamConnectFailed(uint32_t conn_index, - ConnectionPool::PoolFailureReason reason) { - conn_pool_callbacks_.at(conn_index)->onPoolFailure(reason, upstream_hosts_.at(conn_index)); - } - - Tcp::ConnectionPool::Cancellable* onNewConnection(Tcp::ConnectionPool::Cancellable* connection) { - if (!new_connection_functions_.empty()) { - auto fn = new_connection_functions_.front(); - new_connection_functions_.pop_front(); - return fn(connection); - } - return connection; - } - - Event::TestTimeSystem& timeSystem() { return factory_context_.timeSystem(); } - - NiceMock factory_context_; - ConfigSharedPtr config_; - NiceMock filter_callbacks_; - std::unique_ptr filter_; - std::vector>> upstream_hosts_{}; - std::vector>> upstream_connections_{}; - std::vector>> - upstream_connection_data_{}; - std::vector conn_pool_callbacks_; - std::vector>> conn_pool_handles_; - NiceMock conn_pool_; - Tcp::ConnectionPool::UpstreamCallbacks* upstream_callbacks_; - StringViewSaver access_log_data_; - Network::Address::InstanceConstSharedPtr upstream_local_address_; - Network::Address::InstanceConstSharedPtr upstream_remote_address_; - std::list> - new_connection_functions_; - Upstream::HostDescriptionConstSharedPtr upstream_host_{}; - Upstream::ClusterInfoConstSharedPtr upstream_cluster_{}; }; TEST_F(TcpProxyTest, DefaultRoutes) { @@ -1585,7 +674,7 @@ TEST_F(TcpProxyTest, RemoteClosedBeforeUpstreamConnected) { // Test that if the downstream connection is closed before the upstream connection // is established, the upstream connection is cancelled. -TEST_F(TcpProxyTest, LocalClosetBeforeUpstreamConnected) { +TEST_F(TcpProxyTest, LocalClosedBeforeUpstreamConnected) { setup(1); EXPECT_CALL(*conn_pool_handles_.at(0), cancel(Tcp::ConnectionPool::CancelPolicy::CloseExcess)); filter_callbacks_.connection_.raiseEvent(Network::ConnectionEvent::LocalClose); @@ -1942,265 +1031,6 @@ TEST_F(TcpProxyTest, AccessDownstreamAndUpstreamProperties) { EXPECT_EQ(filter_callbacks_.connection().streamInfo().upstreamSslConnection(), upstream_connections_.at(0)->streamInfo().downstreamSslConnection()); } - -class TcpProxyRoutingTest : public testing::Test { -public: - TcpProxyRoutingTest() = default; - - void setup(bool avoid_boosting = true) { - const std::string yaml = R"EOF( - stat_prefix: name - cluster: fallback_cluster - deprecated_v1: - routes: - - destination_ports: 1-9999 - cluster: fake_cluster - )EOF"; - - factory_context_.cluster_manager_.initializeThreadLocalClusters( - {"fallback_cluster", "fake_cluster"}); - config_ = - std::make_shared(constructConfigFromYaml(yaml, factory_context_, avoid_boosting)); - } - - void initializeFilter() { - EXPECT_CALL(filter_callbacks_, connection()).WillRepeatedly(ReturnRef(connection_)); - - filter_ = std::make_unique(config_, factory_context_.cluster_manager_); - filter_->initializeReadFilterCallbacks(filter_callbacks_); - } - - Event::TestTimeSystem& timeSystem() { return factory_context_.timeSystem(); } - - NiceMock factory_context_; - ConfigSharedPtr config_; - NiceMock connection_; - NiceMock filter_callbacks_; - std::unique_ptr filter_; -}; - -TEST_F(TcpProxyRoutingTest, DEPRECATED_FEATURE_TEST(NonRoutableConnection)) { - TestDeprecatedV2Api _deprecated_v2_api; - setup(false); - - const uint32_t total_cx = config_->stats().downstream_cx_total_.value(); - const uint32_t non_routable_cx = config_->stats().downstream_cx_no_route_.value(); - - initializeFilter(); - - // Port 10000 is outside the specified destination port range. - connection_.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("1.2.3.4", 10000)); - - // Expect filter to try to open a connection to the fallback cluster. - EXPECT_CALL(factory_context_.cluster_manager_.thread_local_cluster_, tcpConnPool(_, _)) - .WillOnce(Return(nullptr)); - - filter_->onNewConnection(); - - EXPECT_EQ(total_cx + 1, config_->stats().downstream_cx_total_.value()); - EXPECT_EQ(non_routable_cx, config_->stats().downstream_cx_no_route_.value()); -} - -TEST_F(TcpProxyRoutingTest, DEPRECATED_FEATURE_TEST(RoutableConnection)) { - TestDeprecatedV2Api _deprecated_v2_api; - setup(false); - - const uint32_t total_cx = config_->stats().downstream_cx_total_.value(); - const uint32_t non_routable_cx = config_->stats().downstream_cx_no_route_.value(); - - initializeFilter(); - - // Port 9999 is within the specified destination port range. - connection_.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("1.2.3.4", 9999)); - - // Expect filter to try to open a connection to specified cluster. - EXPECT_CALL(factory_context_.cluster_manager_.thread_local_cluster_, tcpConnPool(_, _)) - .WillOnce(Return(nullptr)); - - filter_->onNewConnection(); - - EXPECT_EQ(total_cx + 1, config_->stats().downstream_cx_total_.value()); - EXPECT_EQ(non_routable_cx, config_->stats().downstream_cx_no_route_.value()); -} - -// Test that the tcp proxy uses the cluster from FilterState if set -TEST_F(TcpProxyRoutingTest, DEPRECATED_FEATURE_TEST(UseClusterFromPerConnectionCluster)) { - TestDeprecatedV2Api _deprecated_v2_api; - setup(false); - initializeFilter(); - - factory_context_.cluster_manager_.initializeThreadLocalClusters({"filter_state_cluster"}); - connection_.streamInfo().filterState()->setData( - "envoy.tcp_proxy.cluster", std::make_unique("filter_state_cluster"), - StreamInfo::FilterState::StateType::Mutable, StreamInfo::FilterState::LifeSpan::Connection); - - // Expect filter to try to open a connection to specified cluster. - EXPECT_CALL(factory_context_.cluster_manager_.thread_local_cluster_, tcpConnPool(_, _)) - .WillOnce(Return(nullptr)); - - filter_->onNewConnection(); -} - -// Test that the tcp proxy forwards the requested server name from FilterState if set -TEST_F(TcpProxyRoutingTest, DEPRECATED_FEATURE_TEST(UpstreamServerName)) { - TestDeprecatedV2Api _deprecated_v2_api; - setup(false); - initializeFilter(); - - connection_.streamInfo().filterState()->setData( - "envoy.network.upstream_server_name", std::make_unique("www.example.com"), - StreamInfo::FilterState::StateType::ReadOnly, StreamInfo::FilterState::LifeSpan::Connection); - - // Expect filter to try to open a connection to a cluster with the transport socket options with - // override-server-name - EXPECT_CALL(factory_context_.cluster_manager_.thread_local_cluster_, tcpConnPool(_, _)) - .WillOnce( - Invoke([](Upstream::ResourcePriority, - Upstream::LoadBalancerContext* context) -> Tcp::ConnectionPool::Instance* { - Network::TransportSocketOptionsSharedPtr transport_socket_options = - context->upstreamTransportSocketOptions(); - EXPECT_NE(transport_socket_options, nullptr); - EXPECT_TRUE(transport_socket_options->serverNameOverride().has_value()); - EXPECT_EQ(transport_socket_options->serverNameOverride().value(), "www.example.com"); - return nullptr; - })); - - // Port 9999 is within the specified destination port range. - connection_.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("1.2.3.4", 9999)); - - filter_->onNewConnection(); -} - -// Test that the tcp proxy override ALPN from FilterState if set -TEST_F(TcpProxyRoutingTest, DEPRECATED_FEATURE_TEST(ApplicationProtocols)) { - TestDeprecatedV2Api _deprecated_v2_api; - setup(false); - initializeFilter(); - - connection_.streamInfo().filterState()->setData( - Network::ApplicationProtocols::key(), - std::make_unique(std::vector{"foo", "bar"}), - StreamInfo::FilterState::StateType::ReadOnly, StreamInfo::FilterState::LifeSpan::Connection); - - // Expect filter to try to open a connection to a cluster with the transport socket options with - // override-application-protocol - EXPECT_CALL(factory_context_.cluster_manager_.thread_local_cluster_, tcpConnPool(_, _)) - .WillOnce( - Invoke([](Upstream::ResourcePriority, - Upstream::LoadBalancerContext* context) -> Tcp::ConnectionPool::Instance* { - Network::TransportSocketOptionsSharedPtr transport_socket_options = - context->upstreamTransportSocketOptions(); - EXPECT_NE(transport_socket_options, nullptr); - EXPECT_FALSE(transport_socket_options->applicationProtocolListOverride().empty()); - EXPECT_EQ(transport_socket_options->applicationProtocolListOverride().size(), 2); - EXPECT_EQ(transport_socket_options->applicationProtocolListOverride()[0], "foo"); - EXPECT_EQ(transport_socket_options->applicationProtocolListOverride()[1], "bar"); - return nullptr; - })); - - // Port 9999 is within the specified destination port range. - connection_.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("1.2.3.4", 9999)); - - filter_->onNewConnection(); -} - -class TcpProxyNonDeprecatedConfigRoutingTest : public TcpProxyRoutingTest { -public: - TcpProxyNonDeprecatedConfigRoutingTest() = default; - - void setup() { - const std::string yaml = R"EOF( - stat_prefix: name - cluster: fake_cluster - )EOF"; - - factory_context_.cluster_manager_.initializeThreadLocalClusters({"fake_cluster"}); - config_ = std::make_shared(constructConfigFromYaml(yaml, factory_context_)); - } -}; - -TEST_F(TcpProxyNonDeprecatedConfigRoutingTest, ClusterNameSet) { - setup(); - - initializeFilter(); - - // Port 9999 is within the specified destination port range. - connection_.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("1.2.3.4", 9999)); - - // Expect filter to try to open a connection to specified cluster. - EXPECT_CALL(factory_context_.cluster_manager_.thread_local_cluster_, tcpConnPool(_, _)) - .WillOnce(Return(nullptr)); - absl::optional cluster_info; - EXPECT_CALL(connection_.stream_info_, setUpstreamClusterInfo(_)) - .WillOnce( - Invoke([&cluster_info](const Upstream::ClusterInfoConstSharedPtr& upstream_cluster_info) { - cluster_info = upstream_cluster_info; - })); - EXPECT_CALL(connection_.stream_info_, upstreamClusterInfo()) - .WillOnce(ReturnPointee(&cluster_info)); - - filter_->onNewConnection(); - - EXPECT_EQ(connection_.stream_info_.upstreamClusterInfo().value()->name(), "fake_cluster"); -} - -class TcpProxyHashingTest : public testing::Test { -public: - TcpProxyHashingTest() = default; - - void setup() { - const std::string yaml = R"EOF( - stat_prefix: name - cluster: fake_cluster - hash_policy: - - source_ip: {} - )EOF"; - - factory_context_.cluster_manager_.initializeThreadLocalClusters({"fake_cluster"}); - config_ = std::make_shared(constructConfigFromYaml(yaml, factory_context_)); - } - - void initializeFilter() { - EXPECT_CALL(filter_callbacks_, connection()).WillRepeatedly(ReturnRef(connection_)); - - filter_ = std::make_unique(config_, factory_context_.cluster_manager_); - filter_->initializeReadFilterCallbacks(filter_callbacks_); - } - - Event::TestTimeSystem& timeSystem() { return factory_context_.timeSystem(); } - - NiceMock factory_context_; - ConfigSharedPtr config_; - NiceMock connection_; - NiceMock filter_callbacks_; - std::unique_ptr filter_; -}; - -// Test TCP proxy use source IP to hash. -TEST_F(TcpProxyHashingTest, HashWithSourceIp) { - setup(); - initializeFilter(); - EXPECT_CALL(factory_context_.cluster_manager_.thread_local_cluster_, tcpConnPool(_, _)) - .WillOnce( - Invoke([](Upstream::ResourcePriority, - Upstream::LoadBalancerContext* context) -> Tcp::ConnectionPool::Instance* { - EXPECT_TRUE(context->computeHashKey().has_value()); - return nullptr; - })); - - connection_.stream_info_.downstream_address_provider_->setRemoteAddress( - std::make_shared("1.2.3.4", 1111)); - connection_.stream_info_.downstream_address_provider_->setLocalAddress( - std::make_shared("2.3.4.5", 2222)); - - filter_->onNewConnection(); -} - } // namespace } // namespace TcpProxy } // namespace Envoy diff --git a/test/common/tcp_proxy/tcp_proxy_test_base.h b/test/common/tcp_proxy/tcp_proxy_test_base.h new file mode 100644 index 000000000000..96338e7e72fb --- /dev/null +++ b/test/common/tcp_proxy/tcp_proxy_test_base.h @@ -0,0 +1,185 @@ +#include +#include +#include +#include +#include +#include + +#include "envoy/config/accesslog/v3/accesslog.pb.h" +#include "envoy/extensions/access_loggers/file/v3/file.pb.h" +#include "envoy/extensions/filters/network/tcp_proxy/v3/tcp_proxy.pb.h" +#include "envoy/extensions/filters/network/tcp_proxy/v3/tcp_proxy.pb.validate.h" +#include "envoy/extensions/upstreams/http/generic/v3/generic_connection_pool.pb.h" +#include "envoy/extensions/upstreams/tcp/generic/v3/generic_connection_pool.pb.h" + +#include "common/buffer/buffer_impl.h" +#include "common/network/address_impl.h" +#include "common/network/application_protocol.h" +#include "common/network/transport_socket_options_impl.h" +#include "common/network/upstream_server_name.h" +#include "common/router/metadatamatchcriteria_impl.h" +#include "common/tcp_proxy/tcp_proxy.h" +#include "common/upstream/upstream_impl.h" + +#include "extensions/access_loggers/well_known_names.h" + +#include "test/common/upstream/utility.h" +#include "test/mocks/buffer/mocks.h" +#include "test/mocks/network/mocks.h" +#include "test/mocks/runtime/mocks.h" +#include "test/mocks/server/factory_context.h" +#include "test/mocks/server/instance.h" +#include "test/mocks/ssl/mocks.h" +#include "test/mocks/stream_info/mocks.h" +#include "test/mocks/tcp/mocks.h" +#include "test/mocks/upstream/host.h" +#include "test/test_common/test_runtime.h" +#include "test/test_common/utility.h" + +#include "gmock/gmock.h" +#include "gtest/gtest.h" + +namespace Envoy { +namespace TcpProxy { + +namespace { +using ::Envoy::Network::UpstreamServerName; +using ::testing::_; +using ::testing::DoAll; +using ::testing::Invoke; +using ::testing::InvokeWithoutArgs; +using ::testing::NiceMock; +using ::testing::Return; +using ::testing::ReturnPointee; +using ::testing::ReturnRef; +using ::testing::SaveArg; + +} // namespace +inline Config constructConfigFromYaml(const std::string& yaml, + Server::Configuration::FactoryContext& context, + bool avoid_boosting = true) { + envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy tcp_proxy; + TestUtility::loadFromYamlAndValidate(yaml, tcp_proxy, false, avoid_boosting); + return Config(tcp_proxy, context); +} + +inline Config constructConfigFromV3Yaml(const std::string& yaml, + Server::Configuration::FactoryContext& context, + bool avoid_boosting = true) { + envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy tcp_proxy; + TestUtility::loadFromYamlAndValidate(yaml, tcp_proxy, false, avoid_boosting); + return Config(tcp_proxy, context); +} + +class TcpProxyTestBase : public testing::Test { +public: + TcpProxyTestBase() { + ON_CALL(*factory_context_.access_log_manager_.file_, write(_)) + .WillByDefault(SaveArg<0>(&access_log_data_)); + ON_CALL(filter_callbacks_.connection_.stream_info_, onUpstreamHostSelected(_)) + .WillByDefault(Invoke( + [this](Upstream::HostDescriptionConstSharedPtr host) { upstream_host_ = host; })); + ON_CALL(filter_callbacks_.connection_.stream_info_, upstreamHost()) + .WillByDefault(ReturnPointee(&upstream_host_)); + ON_CALL(filter_callbacks_.connection_.stream_info_, setUpstreamClusterInfo(_)) + .WillByDefault(Invoke([this](const Upstream::ClusterInfoConstSharedPtr& cluster_info) { + upstream_cluster_ = cluster_info; + })); + ON_CALL(filter_callbacks_.connection_.stream_info_, upstreamClusterInfo()) + .WillByDefault(ReturnPointee(&upstream_cluster_)); + factory_context_.cluster_manager_.initializeThreadLocalClusters({"fake_cluster"}); + } + + ~TcpProxyTestBase() override { + if (filter_ != nullptr) { + filter_callbacks_.connection_.raiseEvent(Network::ConnectionEvent::RemoteClose); + } + } + + void configure(const envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy& config) { + config_ = std::make_shared(config, factory_context_); + } + + envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy defaultConfig() { + envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy config; + config.set_stat_prefix("name"); + auto* route = config.mutable_hidden_envoy_deprecated_deprecated_v1()->mutable_routes()->Add(); + route->set_cluster("fake_cluster"); + return config; + } + + // Return the default config, plus one file access log with the specified format + envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy + accessLogConfig(const std::string& access_log_format) { + envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy config = defaultConfig(); + envoy::config::accesslog::v3::AccessLog* access_log = config.mutable_access_log()->Add(); + access_log->set_name(Extensions::AccessLoggers::AccessLogNames::get().File); + envoy::extensions::access_loggers::file::v3::FileAccessLog file_access_log; + file_access_log.set_path("unused"); + file_access_log.mutable_log_format()->mutable_text_format_source()->set_inline_string( + access_log_format); + access_log->mutable_typed_config()->PackFrom(file_access_log); + return config; + } + + virtual void + setup(uint32_t connections, + const envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy& config) PURE; + + void setup(uint32_t connections) { setup(connections, defaultConfig()); } + + void raiseEventUpstreamConnected(uint32_t conn_index) { + EXPECT_CALL(filter_callbacks_.connection_, readDisable(false)); + EXPECT_CALL(*upstream_connection_data_.at(conn_index), addUpstreamCallbacks(_)) + .WillOnce(Invoke([=](Tcp::ConnectionPool::UpstreamCallbacks& cb) -> void { + upstream_callbacks_ = &cb; + + // Simulate TCP conn pool upstream callbacks. This is safe because the TCP proxy never + // releases a connection so all events go to the same UpstreamCallbacks instance. + upstream_connections_.at(conn_index)->addConnectionCallbacks(cb); + })); + EXPECT_CALL(*upstream_connections_.at(conn_index), enableHalfClose(true)); + conn_pool_callbacks_.at(conn_index) + ->onPoolReady(std::move(upstream_connection_data_.at(conn_index)), + upstream_hosts_.at(conn_index)); + } + + void raiseEventUpstreamConnectFailed(uint32_t conn_index, + ConnectionPool::PoolFailureReason reason) { + conn_pool_callbacks_.at(conn_index)->onPoolFailure(reason, upstream_hosts_.at(conn_index)); + } + + Tcp::ConnectionPool::Cancellable* onNewConnection(Tcp::ConnectionPool::Cancellable* connection) { + if (!new_connection_functions_.empty()) { + auto fn = new_connection_functions_.front(); + new_connection_functions_.pop_front(); + return fn(connection); + } + return connection; + } + + Event::TestTimeSystem& timeSystem() { return factory_context_.timeSystem(); } + + NiceMock factory_context_; + ConfigSharedPtr config_; + NiceMock filter_callbacks_; + std::unique_ptr filter_; + std::vector>> upstream_hosts_{}; + std::vector>> upstream_connections_{}; + std::vector>> + upstream_connection_data_{}; + std::vector conn_pool_callbacks_; + std::vector>> conn_pool_handles_; + NiceMock conn_pool_; + Tcp::ConnectionPool::UpstreamCallbacks* upstream_callbacks_; + StringViewSaver access_log_data_; + Network::Address::InstanceConstSharedPtr upstream_local_address_; + Network::Address::InstanceConstSharedPtr upstream_remote_address_; + std::list> + new_connection_functions_; + Upstream::HostDescriptionConstSharedPtr upstream_host_{}; + Upstream::ClusterInfoConstSharedPtr upstream_cluster_{}; +}; + +} // namespace TcpProxy +} // namespace Envoy From 24687408b68a11e83b6cd1658d6be13d8862fe8f Mon Sep 17 00:00:00 2001 From: Yuchen Dai Date: Wed, 17 Feb 2021 03:14:38 -0800 Subject: [PATCH 2/5] clang-tidy Signed-off-by: Yuchen Dai --- test/common/tcp_proxy/BUILD | 15 ++++++++++----- test/common/tcp_proxy/config_test.cc | 4 ---- test/common/tcp_proxy/tcp_proxy_test.cc | 1 - test/common/tcp_proxy/tcp_proxy_test_base.h | 7 +------ 4 files changed, 11 insertions(+), 16 deletions(-) diff --git a/test/common/tcp_proxy/BUILD b/test/common/tcp_proxy/BUILD index f274aa3d0d81..74bbd82bd8ae 100644 --- a/test/common/tcp_proxy/BUILD +++ b/test/common/tcp_proxy/BUILD @@ -64,11 +64,16 @@ envoy_cc_test( ], deps = [ ":tcp_proxy_test_base", - "@envoy_api//envoy/config/accesslog/v3:pkg_cc_proto", - "@envoy_api//envoy/extensions/access_loggers/file/v3:pkg_cc_proto", - "@envoy_api//envoy/extensions/filters/network/tcp_proxy/v3:pkg_cc_proto", - "@envoy_api//envoy/extensions/upstreams/http/generic/v3:pkg_cc_proto", - "@envoy_api//envoy/extensions/upstreams/tcp/generic/v3:pkg_cc_proto", + ], +) + +envoy_cc_test( + name = "tcp_proxy_cluster_test", + srcs = [ + "tcp_proxy_cluster_test.cc", + ], + deps = [ + ":tcp_proxy_test_base", ], ) diff --git a/test/common/tcp_proxy/config_test.cc b/test/common/tcp_proxy/config_test.cc index ffebeb1bacbb..f9649ad7bf2d 100644 --- a/test/common/tcp_proxy/config_test.cc +++ b/test/common/tcp_proxy/config_test.cc @@ -963,8 +963,6 @@ TEST_F(TcpProxyRoutingTest, DEPRECATED_FEATURE_TEST(ApplicationProtocols)) { class TcpProxyNonDeprecatedConfigRoutingTest : public TcpProxyRoutingTest { public: - TcpProxyNonDeprecatedConfigRoutingTest() = default; - void setup() { const std::string yaml = R"EOF( stat_prefix: name @@ -1004,8 +1002,6 @@ TEST_F(TcpProxyNonDeprecatedConfigRoutingTest, ClusterNameSet) { class TcpProxyHashingTest : public testing::Test { public: - TcpProxyHashingTest() = default; - void setup() { const std::string yaml = R"EOF( stat_prefix: name diff --git a/test/common/tcp_proxy/tcp_proxy_test.cc b/test/common/tcp_proxy/tcp_proxy_test.cc index d0c1d5f7c8d1..6917b4fe6fe3 100644 --- a/test/common/tcp_proxy/tcp_proxy_test.cc +++ b/test/common/tcp_proxy/tcp_proxy_test.cc @@ -45,7 +45,6 @@ namespace TcpProxy { namespace { -using ::Envoy::Network::UpstreamServerName; using ::testing::_; using ::testing::DoAll; using ::testing::Invoke; diff --git a/test/common/tcp_proxy/tcp_proxy_test_base.h b/test/common/tcp_proxy/tcp_proxy_test_base.h index 96338e7e72fb..f3d5c93c1613 100644 --- a/test/common/tcp_proxy/tcp_proxy_test_base.h +++ b/test/common/tcp_proxy/tcp_proxy_test_base.h @@ -43,18 +43,13 @@ namespace Envoy { namespace TcpProxy { namespace { -using ::Envoy::Network::UpstreamServerName; using ::testing::_; -using ::testing::DoAll; using ::testing::Invoke; -using ::testing::InvokeWithoutArgs; using ::testing::NiceMock; -using ::testing::Return; using ::testing::ReturnPointee; -using ::testing::ReturnRef; using ::testing::SaveArg; - } // namespace + inline Config constructConfigFromYaml(const std::string& yaml, Server::Configuration::FactoryContext& context, bool avoid_boosting = true) { From 03dddf56f0a9c667d317955f5c4aaa9a9e7a635e Mon Sep 17 00:00:00 2001 From: Yuchen Dai Date: Wed, 17 Feb 2021 03:49:17 -0800 Subject: [PATCH 3/5] format and clangtidy Signed-off-by: Yuchen Dai --- test/common/tcp_proxy/BUILD | 10 ++++++++++ test/common/tcp_proxy/config_test.cc | 3 ++- 2 files changed, 12 insertions(+), 1 deletion(-) diff --git a/test/common/tcp_proxy/BUILD b/test/common/tcp_proxy/BUILD index 74bbd82bd8ae..0ba41bf6b418 100644 --- a/test/common/tcp_proxy/BUILD +++ b/test/common/tcp_proxy/BUILD @@ -64,6 +64,11 @@ envoy_cc_test( ], deps = [ ":tcp_proxy_test_base", + "@envoy_api//envoy/config/accesslog/v3:pkg_cc_proto", + "@envoy_api//envoy/extensions/access_loggers/file/v3:pkg_cc_proto", + "@envoy_api//envoy/extensions/filters/network/tcp_proxy/v3:pkg_cc_proto", + "@envoy_api//envoy/extensions/upstreams/http/generic/v3:pkg_cc_proto", + "@envoy_api//envoy/extensions/upstreams/tcp/generic/v3:pkg_cc_proto", ], ) @@ -74,6 +79,11 @@ envoy_cc_test( ], deps = [ ":tcp_proxy_test_base", + "@envoy_api//envoy/config/accesslog/v3:pkg_cc_proto", + "@envoy_api//envoy/extensions/access_loggers/file/v3:pkg_cc_proto", + "@envoy_api//envoy/extensions/filters/network/tcp_proxy/v3:pkg_cc_proto", + "@envoy_api//envoy/extensions/upstreams/http/generic/v3:pkg_cc_proto", + "@envoy_api//envoy/extensions/upstreams/tcp/generic/v3:pkg_cc_proto", ], ) diff --git a/test/common/tcp_proxy/config_test.cc b/test/common/tcp_proxy/config_test.cc index f9649ad7bf2d..7365a5749668 100644 --- a/test/common/tcp_proxy/config_test.cc +++ b/test/common/tcp_proxy/config_test.cc @@ -903,7 +903,8 @@ TEST_F(TcpProxyRoutingTest, DEPRECATED_FEATURE_TEST(UpstreamServerName)) { initializeFilter(); connection_.streamInfo().filterState()->setData( - "envoy.network.upstream_server_name", std::make_unique("www.example.com"), + "envoy.network.upstream_server_name", + std::make_unique("www.example.com"), StreamInfo::FilterState::StateType::ReadOnly, StreamInfo::FilterState::LifeSpan::Connection); // Expect filter to try to open a connection to a cluster with the transport socket options with From 347c6fc9dfe46350d0a845b7d12471e4ce57e5f8 Mon Sep 17 00:00:00 2001 From: Yuchen Dai Date: Wed, 17 Feb 2021 21:26:26 -0800 Subject: [PATCH 4/5] remove tcp proxy cluster test from future Signed-off-by: Yuchen Dai --- test/common/tcp_proxy/BUILD | 15 --------------- 1 file changed, 15 deletions(-) diff --git a/test/common/tcp_proxy/BUILD b/test/common/tcp_proxy/BUILD index 0ba41bf6b418..f274aa3d0d81 100644 --- a/test/common/tcp_proxy/BUILD +++ b/test/common/tcp_proxy/BUILD @@ -72,21 +72,6 @@ envoy_cc_test( ], ) -envoy_cc_test( - name = "tcp_proxy_cluster_test", - srcs = [ - "tcp_proxy_cluster_test.cc", - ], - deps = [ - ":tcp_proxy_test_base", - "@envoy_api//envoy/config/accesslog/v3:pkg_cc_proto", - "@envoy_api//envoy/extensions/access_loggers/file/v3:pkg_cc_proto", - "@envoy_api//envoy/extensions/filters/network/tcp_proxy/v3:pkg_cc_proto", - "@envoy_api//envoy/extensions/upstreams/http/generic/v3:pkg_cc_proto", - "@envoy_api//envoy/extensions/upstreams/tcp/generic/v3:pkg_cc_proto", - ], -) - envoy_cc_test( name = "upstream_test", srcs = ["upstream_test.cc"], From 9ae0fb258d2d70d788bbb85316a0f2a25340ac3b Mon Sep 17 00:00:00 2001 From: Yuchen Dai Date: Tue, 2 Mar 2021 11:05:22 -0800 Subject: [PATCH 5/5] header to hdrs Signed-off-by: Yuchen Dai --- include/envoy/server/overload/thread_local_overload_state.h | 1 - test/common/tcp_proxy/BUILD | 2 +- test/common/tcp_proxy/tcp_proxy_test_base.h | 2 ++ 3 files changed, 3 insertions(+), 2 deletions(-) diff --git a/include/envoy/server/overload/thread_local_overload_state.h b/include/envoy/server/overload/thread_local_overload_state.h index 23c5e7add043..ccee5b9ceb22 100644 --- a/include/envoy/server/overload/thread_local_overload_state.h +++ b/include/envoy/server/overload/thread_local_overload_state.h @@ -1,4 +1,3 @@ - #pragma once #include diff --git a/test/common/tcp_proxy/BUILD b/test/common/tcp_proxy/BUILD index b5ad6775dca2..b84cdb0c6d6a 100644 --- a/test/common/tcp_proxy/BUILD +++ b/test/common/tcp_proxy/BUILD @@ -11,7 +11,7 @@ envoy_package() envoy_cc_test_library( name = "tcp_proxy_test_base", - srcs = [ + hdrs = [ "tcp_proxy_test_base.h", ], deps = [ diff --git a/test/common/tcp_proxy/tcp_proxy_test_base.h b/test/common/tcp_proxy/tcp_proxy_test_base.h index 90b5dce23c89..7c3d5d717670 100644 --- a/test/common/tcp_proxy/tcp_proxy_test_base.h +++ b/test/common/tcp_proxy/tcp_proxy_test_base.h @@ -1,3 +1,5 @@ +#pragma once + #include #include #include