Skip to content

Commit

Permalink
Merge remote-tracking branch 'grpc/main' into go-docker-image
Browse files Browse the repository at this point in the history
  • Loading branch information
eugeneo committed Aug 1, 2024
2 parents 88fb135 + b3d0417 commit f656375
Show file tree
Hide file tree
Showing 27 changed files with 453 additions and 57 deletions.
1 change: 1 addition & 0 deletions .github/CODEOWNERS
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
* @grpc/grpc-psm-interop
52 changes: 50 additions & 2 deletions .kokoro/psm_interop_kokoro_lib.sh
Original file line number Diff line number Diff line change
Expand Up @@ -158,6 +158,50 @@ psm::security::run_test() {
psm::tools::run_verbose python -m "tests.${test_name}" "${PSM_TEST_FLAGS[@]}"
}

# --- DualStack TESTS ------------------

#######################################
# DualStack Test Suite setup.
# Outputs:
# Prints activated cluster names.
#######################################
psm::dualstack::setup() {
activate_gke_cluster GKE_CLUSTER_DUALSTACK
}

#######################################
# Prepares the list of tests in DualStack test suite.
# Globals:
# TESTS: Populated with tests in PSM DualStack test suite.
#######################################
psm::dualstack::get_tests() {
TESTS=(
"dualstack_test"
)
}

#######################################
# Executes DualStack test case
# Globals:
# PSM_TEST_FLAGS: The array with flags for the test
# GRPC_LANGUAGE: The name of gRPC languages under test
# Arguments:
# Test case name
# Outputs:
# Writes the output of test execution to stdout, stderr
# Test xUnit report to ${TEST_XML_OUTPUT_DIR}/${test_name}/sponge_log.xml
#######################################
psm::dualstack::run_test() {
local test_name="${1:?${FUNCNAME[0]} missing the test name argument}"

PSM_TEST_FLAGS+=(
"--flagfile=config/common-dualstack.cfg"
)

psm::run::finalize_test_flags "${test_name}"
psm::tools::run_verbose python -m "tests.${test_name}" "${PSM_TEST_FLAGS[@]}"
}

# --- URL Map TESTS ------------------

#######################################
Expand Down Expand Up @@ -257,7 +301,7 @@ psm::csm::run_test() {
# BUILD_SCRIPT_DIR: Absolute path to the directory with lang-specific buildscript
# in the source repo.
# Arguments:
# Test suite name, one of (lb, security, url_map, csm)
# Test suite name, one of (lb, security, dualstack, url_map, csm)
# Outputs:
# Writes the output of test execution to stdout, stderr
#######################################
Expand All @@ -272,7 +316,7 @@ psm::run() {
psm::setup::docker_image_names "${GRPC_LANGUAGE}" "${test_suite}"

case "${test_suite}" in
lb | security | url_map | csm)
lb | security | dualstack | url_map | csm)
psm::setup::generic_test_suite "${test_suite}"
;;
*)
Expand Down Expand Up @@ -694,6 +738,10 @@ activate_gke_cluster() {
GKE_CLUSTER_NAME="interop-test-psm-basic"
GKE_CLUSTER_ZONE="us-central1-c"
;;
GKE_CLUSTER_DUALSTACK)
GKE_CLUSTER_NAME="psm-interop-dualstack"
GKE_CLUSTER_ZONE="us-central1-a"
;;
*)
psm::tools::log "Unknown GKE cluster: ${1}"
exit 1
Expand Down
6 changes: 3 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -250,7 +250,7 @@ do this, navigate to this directory and run `./bin/freeze.sh`.

There are many arguments to be passed into the test run. You can save the
arguments to a config file ("flagfile") for your development environment.
Use [`config/local-dev.cfg.example`](https://github.com/grpc/grpc/blob/master/tools/run_tests/xds_k8s_test_driver/config/local-dev.cfg.example)
Use [`config/local-dev.cfg.example`](https://github.com/grpc/psm-interop/blob/main/config/local-dev.cfg.example)
as a starting point:

```shell
Expand All @@ -268,7 +268,7 @@ Learn more about flagfiles in [abseil documentation](https://abseil.io/docs/pyth

## Test suites

See the full list of available test suites in the [`tests/`](https://github.com/grpc/grpc/tree/master/tools/run_tests/xds_k8s_test_driver/tests) folder.
See the full list of available test suites in the [`tests/`](https://github.com/grpc/psm-interop/blob/main/tests) folder.

### xDS Baseline Tests

Expand Down Expand Up @@ -304,7 +304,7 @@ python -m tests.security_test --flagfile="config/local-dev.cfg"
```

## Helper scripts
You can use interop xds-k8s [`bin/`](https://github.com/grpc/grpc/tree/master/tools/run_tests/xds_k8s_test_driver/bin)
You can use interop xds-k8s [`bin/`](https://github.com/grpc/psm-interop/blob/main/bin)
scripts to configure TD, start k8s instances step-by-step, and keep them alive
for as long as you need.

Expand Down
8 changes: 8 additions & 0 deletions config/common-dualstack.cfg
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
# Common config file for PSM DualStack tests.
--resource_prefix=psm-ds
--enable_dualstack
--noenable_workload_identity
--network=dualstack

# TODO remove when ipAddressSelectionPolicy is available in compute v1
--compute_api_version=v1beta
2 changes: 1 addition & 1 deletion config/common.cfg
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
--resource_prefix=psm-interop
--td_bootstrap_image=us-docker.pkg.dev/grpc-testing/trafficdirector/td-grpc-bootstrap:2bf1b5ed00f852ffea8d24759c6fa673acc9ef10
--td_bootstrap_image=us-docker.pkg.dev/grpc-testing/trafficdirector/td-grpc-bootstrap:4ba99d77963c72d4973486ef2a3055913fdc2392

# The canonical implementation of the xDS test server.
# Can be used in tests where language-specific xDS test server does not exist,
Expand Down
2 changes: 2 additions & 0 deletions framework/infrastructure/gcp/api.py
Original file line number Diff line number Diff line change
Expand Up @@ -157,6 +157,8 @@ def compute(self, version: str):
return self._build_from_discovery_v1(api_name, version)
elif version == "v1alpha":
return self._build_from_discovery_v1(api_name, "alpha")
elif version == "v1beta":
return self._build_from_discovery_v1(api_name, "beta")

raise NotImplementedError(f"Compute {version} not supported")

Expand Down
5 changes: 5 additions & 0 deletions framework/infrastructure/gcp/compute.py
Original file line number Diff line number Diff line change
Expand Up @@ -151,6 +151,7 @@ def create_backend_service_traffic_director(
subset_size: Optional[int] = None,
locality_lb_policies: Optional[List[dict]] = None,
outlier_detection: Optional[dict] = None,
enable_dualstack: bool = False,
) -> "GcpResource":
if not isinstance(protocol, self.BackendServiceProtocol):
raise TypeError(f"Unexpected Backend Service protocol: {protocol}")
Expand All @@ -160,6 +161,10 @@ def create_backend_service_traffic_director(
"healthChecks": [health_check.url],
"protocol": protocol.name,
}
# If add dualstack support is specified True, config the backend service
# to support IPv6
if enable_dualstack:
body["ipAddressSelectionPolicy"] = "PREFER_IPV6"
# If affinity header is specified, config the backend service to support
# affinity, and set affinity header to the one given.
if affinity_header:
Expand Down
80 changes: 79 additions & 1 deletion framework/infrastructure/traffic_director.py
Original file line number Diff line number Diff line change
Expand Up @@ -65,9 +65,11 @@ class TrafficDirectorManager: # pylint: disable=too-many-public-methods
URL_MAP_PATH_MATCHER_NAME: Final[str] = "path-matcher"

TARGET_PROXY_NAME: Final[str] = "target-proxy"
TARGET_PROXY_NAME_IPV6: Final[str] = "target-proxy-ipv6"
ALTERNATIVE_TARGET_PROXY_NAME: Final[str] = "target-proxy-alt"

FORWARDING_RULE_NAME: Final[str] = "forwarding-rule"
FORWARDING_RULE_NAME_IPV6: Final[str] = "forwarding-rule-ipv6"
ALTERNATIVE_FORWARDING_RULE_NAME: Final[str] = "forwarding-rule-alt"

HEALTH_CHECK_NAME: Final[str] = "health-check"
Expand Down Expand Up @@ -107,6 +109,7 @@ def __init__(
resource_suffix: str,
network: str = "default",
compute_api_version: str = "v1",
enable_dualstack: bool = False,
):
# API
self.compute = _ComputeV1(
Expand All @@ -121,6 +124,7 @@ def __init__(
self.network: str = network
self.resource_prefix: str = resource_prefix
self.resource_suffix: str = resource_suffix
self.enable_dualstack: bool = enable_dualstack

# Managed resources
self.health_check: Optional[GcpResource] = None
Expand All @@ -129,10 +133,12 @@ def __init__(
self.firewall_rule: Optional[GcpResource] = None
self.firewall_rule_ipv6: Optional[GcpResource] = None
self.target_proxy: Optional[GcpResource] = None
self.target_proxy_ipv6: Optional[GcpResource] = None
# TODO(sergiitk): remove this flag once target proxy resource loaded
self.target_proxy_is_http: bool = False
self.alternative_target_proxy: Optional[GcpResource] = None
self.forwarding_rule: Optional[GcpResource] = None
self.forwarding_rule_ipv6: Optional[GcpResource] = None
self.alternative_forwarding_rule: Optional[GcpResource] = None

# Backends.
Expand Down Expand Up @@ -171,13 +177,20 @@ def setup_routing_rule_map_for_grpc(self, service_host, service_port):
self.create_target_proxy()
self.create_forwarding_rule(service_port)

if self.enable_dualstack:
self.create_target_proxy_ipv6()
self.create_forwarding_rule_ipv6(service_port)

def cleanup(self, *, force=False):
# Cleanup in the reverse order of creation
self.delete_firewall_rules(force=force)
self.delete_forwarding_rule(force=force)
self.delete_alternative_forwarding_rule(force=force)
self.delete_target_http_proxy(force=force)
self.delete_target_grpc_proxy(force=force)
if self.enable_dualstack:
self.delete_forwarding_rule_ipv6(force=force)
self.delete_target_proxy_ipv6(force=force)
self.delete_alternative_target_grpc_proxy(force=force)
self.delete_url_map(force=force)
self.delete_alternative_url_map(force=force)
Expand Down Expand Up @@ -246,6 +259,7 @@ def create_backend_service(
affinity_header=affinity_header,
locality_lb_policies=locality_lb_policies,
outlier_detection=outlier_detection,
enable_dualstack=self.enable_dualstack,
)
self.backend_service = resource
self.backend_service_protocol = protocol
Expand Down Expand Up @@ -337,7 +351,10 @@ def create_alternative_backend_service(
'Creating %s Alternative Backend Service "%s"', protocol.name, name
)
resource = self.compute.create_backend_service_traffic_director(
name, health_check=self.health_check, protocol=protocol
name,
health_check=self.health_check,
protocol=protocol,
enable_dualstack=self.enable_dualstack,
)
self.alternative_backend_service = resource
self.alternative_backend_service_protocol = protocol
Expand Down Expand Up @@ -418,6 +435,7 @@ def create_affinity_backend_service(
health_check=self.health_check,
protocol=protocol,
affinity_header=TEST_AFFINITY_METADATA_KEY,
enable_dualstack=self.enable_dualstack,
)
self.affinity_backend_service = resource
self.affinity_backend_service_protocol = protocol
Expand Down Expand Up @@ -614,6 +632,20 @@ def create_target_proxy(self):
)
self.target_proxy = create_proxy_fn(name, self.url_map)

def create_target_proxy_ipv6(self):
name = self.make_resource_name(self.TARGET_PROXY_NAME_IPV6)
# TODO(lsafran): Support GRPC target proxy as well
target_proxy_type = "HTTP"
create_proxy_fn = self.compute.create_target_http_proxy

logger.info(
'Creating IPv6 target %s proxy "%s" to URL map %s',
name,
target_proxy_type,
self.url_map.name,
)
self.target_proxy_ipv6 = create_proxy_fn(name, self.url_map)

def delete_target_grpc_proxy(self, force=False):
if force:
name = self.make_resource_name(self.TARGET_PROXY_NAME)
Expand All @@ -638,6 +670,18 @@ def delete_target_http_proxy(self, force=False):
self.target_proxy = None
self.target_proxy_is_http = False

def delete_target_proxy_ipv6(self, force=False):
if force:
name = self.make_resource_name(self.TARGET_PROXY_NAME_IPV6)
elif self.target_proxy_ipv6:
name = self.target_proxy_ipv6.name
else:
return
# TODO: Delete Target GRPC Proxy when added in create_target_proxy_ipv6.
logger.info('Deleting IPv6 Target HTTP proxy "%s"', name)
self.compute.delete_target_http_proxy(name)
self.target_proxy_ipv6 = None

def create_alternative_target_proxy(self):
name = self.make_resource_name(self.ALTERNATIVE_TARGET_PROXY_NAME)
if self.backend_service_protocol is BackendServiceProtocol.GRPC:
Expand Down Expand Up @@ -695,6 +739,25 @@ def create_forwarding_rule(self, src_port: int):
self.forwarding_rule = resource
return resource

def create_forwarding_rule_ipv6(self, src_port: int):
name = self.make_resource_name(self.FORWARDING_RULE_NAME_IPV6)
logging.info(
'Creating IPv6 forwarding rule "%s" in network "%s": [::]:%s -> %s',
name,
self.network,
src_port,
self.target_proxy_ipv6.url,
)
resource = self.compute.create_forwarding_rule(
name,
src_port,
self.target_proxy_ipv6,
self.network_url,
ip_address="::",
)
self.forwarding_rule_ipv6 = resource
return resource

def delete_forwarding_rule(self, force=False):
if force:
name = self.make_resource_name(self.FORWARDING_RULE_NAME)
Expand All @@ -706,6 +769,17 @@ def delete_forwarding_rule(self, force=False):
self.compute.delete_forwarding_rule(name)
self.forwarding_rule = None

def delete_forwarding_rule_ipv6(self, force=False):
if force:
name = self.make_resource_name(self.FORWARDING_RULE_NAME_IPV6)
elif self.forwarding_rule_ipv6:
name = self.forwarding_rule_ipv6.name
else:
return
logger.info('Deleting IPv6 Forwarding rule "%s"', name)
self.compute.delete_forwarding_rule(name)
self.forwarding_rule_ipv6 = None

def create_alternative_forwarding_rule(
self, src_port: int, ip_address="0.0.0.0"
):
Expand Down Expand Up @@ -845,6 +919,7 @@ def __init__(
resource_suffix: Optional[str] = None,
network: str = "default",
compute_api_version: str = "v1",
enable_dualstack: bool = False,
):
super().__init__(
gcp_api_manager,
Expand All @@ -853,6 +928,7 @@ def __init__(
resource_suffix=resource_suffix,
network=network,
compute_api_version=compute_api_version,
enable_dualstack=enable_dualstack,
)

# API
Expand Down Expand Up @@ -969,6 +1045,7 @@ def __init__(
resource_suffix: Optional[str] = None,
network: str = "default",
compute_api_version: str = "v1",
enable_dualstack: bool = False,
):
super().__init__(
gcp_api_manager,
Expand All @@ -977,6 +1054,7 @@ def __init__(
resource_suffix=resource_suffix,
network=network,
compute_api_version=compute_api_version,
enable_dualstack=enable_dualstack,
)

# API
Expand Down
5 changes: 4 additions & 1 deletion framework/test_app/runners/k8s/gamma_server_runner.py
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,7 @@ def __init__(
deployment_name: str,
image_name: str,
td_bootstrap_image: str,
app_label: str = "",
network: str = "default",
xds_server_uri: Optional[str] = None,
gcp_api_manager: gcp.api.GcpApiManager,
Expand All @@ -88,6 +89,7 @@ def __init__(
deployment_name=deployment_name,
image_name=image_name,
td_bootstrap_image=td_bootstrap_image,
app_label=app_label,
network=network,
xds_server_uri=xds_server_uri,
gcp_api_manager=gcp_api_manager,
Expand Down Expand Up @@ -154,7 +156,7 @@ def run( # pylint: disable=arguments-differ
self.service_template,
service_name=self.service_name,
namespace_name=self.k8s_namespace.name,
deployment_name=self.deployment_name,
app_label=self.app_label,
neg_name=self.gcp_neg_name,
test_port=test_port,
)
Expand Down Expand Up @@ -199,6 +201,7 @@ def run( # pylint: disable=arguments-differ
deployment_name=self.deployment_name,
image_name=self.image_name,
namespace_name=self.k8s_namespace.name,
app_label=self.app_label,
service_account_name=self.service_account_name,
td_bootstrap_image=self.td_bootstrap_image,
xds_server_uri=self.xds_server_uri,
Expand Down
Loading

0 comments on commit f656375

Please sign in to comment.