Skip to content

Commit b534773

Browse files
Merge branch 'release-v1.53.0' into main
2 parents d39650f + ee3f28f commit b534773

File tree

38 files changed

+697
-50
lines changed

38 files changed

+697
-50
lines changed

integration/combination/test_api_with_authorizer_apikey.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,7 @@ def test_authorizer_apikey(self):
7171
# ApiKeySourceType is AUTHORIZER. Passing api key via x-api-key will not get authorized
7272
self.verify_authorized_request(base_url + "lambda-token-api-key", 401, "x-api-key", key["value"])
7373

74-
@retry(StatusCodeError, 10)
74+
@retry(StatusCodeError, 10, 0.25)
7575
def verify_authorized_request(
7676
self,
7777
url,

integration/combination/test_api_with_authorizers.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -427,7 +427,7 @@ def test_authorizers_with_invoke_function_set_none(self):
427427
auth_type_for_api_event_without_auth = api_event_with_out_auth["authorizationType"]
428428
self.assertEqual(auth_type_for_api_event_without_auth, "NONE")
429429

430-
@retry(StatusCodeError, 10)
430+
@retry(StatusCodeError, 10, 0.25)
431431
def verify_authorized_request(
432432
self,
433433
url,

integration/combination/test_connectors.py

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,17 @@
11
from time import sleep
2+
from unittest import SkipTest
23
from parameterized import parameterized
4+
from tenacity import retry, stop_after_attempt, retry_if_exception
35
from integration.conftest import clean_bucket
46
from integration.helpers.base_test import S3_BUCKET_PREFIX, BaseTest
57
from integration.helpers.resource import generate_suffix
68

9+
retry_once = retry(
10+
stop=stop_after_attempt(2),
11+
# unittest raises SkipTest for skipping tests
12+
retry=retry_if_exception(lambda e: not isinstance(e, SkipTest)),
13+
)
14+
715

816
class TestConnectors(BaseTest):
917
def tearDown(self):
@@ -41,6 +49,7 @@ def tearDown(self):
4149
("combination/connector_table_to_function_read",),
4250
]
4351
)
52+
@retry_once
4453
def test_connector_by_invoking_a_function(self, template_file_path):
4554
self.skip_using_service_detector(template_file_path)
4655
self.create_and_verify_stack(template_file_path)
@@ -72,6 +81,7 @@ def test_connector_by_invoking_a_function(self, template_file_path):
7281
("combination/connector_sfn_to_eb_custom_write",),
7382
]
7483
)
84+
@retry_once
7585
def test_connector_by_sync_execute_an_state_machine(self, template_file_path):
7686
self.skip_using_service_detector(template_file_path)
7787
self.create_and_verify_stack(template_file_path)
@@ -91,6 +101,7 @@ def test_connector_by_sync_execute_an_state_machine(self, template_file_path):
91101
("combination/connector_sfn_to_sfn_sync",),
92102
]
93103
)
104+
@retry_once
94105
def test_connector_by_async_execute_an_state_machine(self, template_file_path):
95106
self.skip_using_service_detector(template_file_path)
96107
self.create_and_verify_stack(template_file_path)
@@ -123,6 +134,7 @@ def test_connector_by_async_execute_an_state_machine(self, template_file_path):
123134
("combination/connector_bucket_to_function_write",),
124135
]
125136
)
137+
@retry_once
126138
def test_connector_by_execute_a_s3_bucket(self, template_file_path):
127139
self.skip_using_service_detector(template_file_path)
128140
bucket_name = S3_BUCKET_PREFIX + "connector" + generate_suffix()

integration/combination/test_custom_http_api_domains_test.py

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,10 @@ def test_custom_http_api_domains_regional(self):
2121
api_gateway_client = self.client_provider.api_v2_client
2222
result = api_gateway_client.get_domain_name(DomainName=domain_name_id)
2323

24-
self.assertEqual("httpapi.sam-gamma-regional.com", result["DomainName"])
24+
if "FeatureToggle" in self.pipeline_prefix:
25+
self.assertEqual("httpapi.ftl.sam-gamma-regional.com", result["DomainName"])
26+
else:
27+
self.assertEqual("httpapi.sam-gamma-regional.com", result["DomainName"])
2528

2629
mtls_auth_config = result["MutualTlsAuthentication"]
2730
self.assertEqual(self.file_to_s3_uri_map["MTLSCert.pem"]["uri"], mtls_auth_config["TruststoreUri"])

integration/combination/test_custom_rest_api_domains.py

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,14 +12,18 @@
1212
class TestCustomRestApiDomains(BaseInternalTest):
1313
def test_custom_rest_api_domains_edge(self):
1414
self.create_and_verify_stack("combination/api_with_custom_domains_edge")
15+
1516
domain_name_list = self.get_stack_resources("AWS::ApiGateway::DomainName")
1617
self.assertEqual(1, len(domain_name_list))
1718

1819
domain_name_id = self.get_physical_id_by_type("AWS::ApiGateway::DomainName")
1920
api_gateway_client = self.client_provider.api_client
2021
result = api_gateway_client.get_domain_name(domainName=domain_name_id)
2122

22-
self.assertEqual("sam-gamma-edge.com", result["domainName"])
23+
if "FeatureToggle" in self.pipeline_prefix:
24+
self.assertEqual("ftl.sam-gamma-edge.com", result["domainName"])
25+
else:
26+
self.assertEqual("sam-gamma-edge.com", result["domainName"])
2327

2428
end_point_config = result["endpointConfiguration"]
2529
end_point_types = end_point_config["types"]
@@ -37,7 +41,11 @@ def test_custom_rest_api_domains_regional(self):
3741
api_gateway_client = self.client_provider.api_client
3842
result = api_gateway_client.get_domain_name(domainName=domain_name_id)
3943

40-
self.assertEqual("sam-gamma-regional.com", result["domainName"])
44+
if "FeatureToggle" in self.pipeline_prefix:
45+
self.assertEqual("ftl.sam-gamma-regional.com", result["domainName"])
46+
else:
47+
self.assertEqual("sam-gamma-regional.com", result["domainName"])
48+
4149
self.assertEqual("TLS_1_2", result["securityPolicy"])
4250

4351
end_point_config = result["endpointConfiguration"]

integration/conftest.py

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
import time
12
import boto3
23
import botocore
34
import pytest
@@ -63,6 +64,26 @@ def clean_all_integ_buckets():
6364
clean_bucket(bucket.name, s3_client)
6465

6566

67+
def _delete_unused_network_interface_by_subnet(ec2_client, subnet_id):
68+
"""Deletes unused network interface under the provided subnet"""
69+
paginator = ec2_client.get_paginator("describe_network_interfaces")
70+
response_iterator = paginator.paginate(
71+
Filters=[
72+
{"Name": "subnet-id", "Values": [subnet_id]},
73+
{"Name": "status", "Values": ["available"]},
74+
]
75+
)
76+
network_interface_ids = []
77+
for page in response_iterator:
78+
network_interface_ids += [ni["NetworkInterfaceId"] for ni in page["NetworkInterfaces"]]
79+
80+
for ni_id in network_interface_ids:
81+
ec2_client.delete_network_interface(NetworkInterfaceId=ni_id)
82+
time.sleep(0.5)
83+
84+
LOG.info("Deleted %s unused network interfaces under subnet %s", len(network_interface_ids), subnet_id)
85+
86+
6687
@pytest.fixture()
6788
def setup_companion_stack_once(tmpdir_factory, get_prefix):
6889
tests_integ_dir = Path(__file__).resolve().parents[1]
@@ -74,6 +95,15 @@ def setup_companion_stack_once(tmpdir_factory, get_prefix):
7495
companion_stack = Stack(stack_name, companion_stack_tempalte_path, cfn_client, output_dir)
7596
companion_stack.create_or_update(_stack_exists(stack_name))
7697

98+
ec2_client = ClientProvider().ec2_client
99+
precreated_subnet_ids = [
100+
resource["PhysicalResourceId"]
101+
for resource in companion_stack.stack_resources["StackResourceSummaries"]
102+
if resource["LogicalResourceId"].startswith("PreCreatedSubnet")
103+
]
104+
for subnet_id in precreated_subnet_ids:
105+
_delete_unused_network_interface_by_subnet(ec2_client, subnet_id)
106+
77107

78108
@pytest.fixture()
79109
def get_serverless_application_repository_app():

integration/helpers/base_test.py

Lines changed: 16 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,13 @@
5151

5252
STACK_NAME_PREFIX = "sam-integ-stack-"
5353
S3_BUCKET_PREFIX = "sam-integ-bucket-"
54+
FEATURE_TOGGLE_JSON_FILES = [
55+
"http_api_with_custom_domains_regional",
56+
"http_api_with_custom_domains_regional_ownership_verification",
57+
"api_with_custom_domains_edge",
58+
"api_with_custom_domains_regional",
59+
"api_with_custom_domains_regional_ownership_verification",
60+
]
5461

5562

5663
class BaseTest(TestCase):
@@ -154,13 +161,20 @@ def create_and_verify_stack(self, file_path, parameters=None, s3_uploader=None):
154161
s3_uploader: S3Uploader object
155162
Object for uploading files to s3
156163
"""
157-
folder, file_name = file_path.split("/")
158164

159165
# If template is too large, calling the method with self.s3_uploader to send the template to s3 then deploy
160166
self.create_stack(file_path, parameters, s3_uploader)
161-
self.expected_resource_path = str(Path(self.expected_dir, folder, file_name + ".json"))
167+
self.get_expected_json_file_name(file_path)
162168
self.verify_stack()
163169

170+
def get_expected_json_file_name(self, file_path):
171+
folder, file_name = file_path.split("/")
172+
173+
if "FeatureToggle" in self.pipeline_prefix and file_name in FEATURE_TOGGLE_JSON_FILES:
174+
self.expected_resource_path = str(Path(self.expected_dir, folder, file_name + "_feature_toggle.json"))
175+
else:
176+
self.expected_resource_path = str(Path(self.expected_dir, folder, file_name + ".json"))
177+
164178
def skip_using_service_detector(self, file_path):
165179
"""
166180
Skips the test if it cannot pass the test of

integration/helpers/client_provider.py

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ def __init__(self):
2525
self._kafka_client = None
2626
self._code_deploy_client = None
2727
self._sar_client = None
28+
self._ec2_client = None
2829

2930
@property
3031
def cfn_client(self):
@@ -216,3 +217,13 @@ def sar_client(self):
216217
if not self._sar_client:
217218
self._sar_client = boto3.client("serverlessrepo")
218219
return self._sar_client
220+
221+
@property
222+
def ec2_client(self):
223+
"""
224+
EC2 Client
225+
"""
226+
with self._lock:
227+
if not self._ec2_client:
228+
self._ec2_client = boto3.client("ec2")
229+
return self._ec2_client
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
[
2+
{ "LogicalResourceId":"RecordSetGroupc911be5759", "ResourceType":"AWS::Route53::RecordSetGroup" },
3+
{ "LogicalResourceId":"MyApiDeployment", "ResourceType":"AWS::ApiGateway::Deployment" },
4+
{ "LogicalResourceId":"ApiGatewayDomainName299fac327d", "ResourceType":"AWS::ApiGateway::DomainName" },
5+
{ "LogicalResourceId":"MyApi", "ResourceType":"AWS::ApiGateway::RestApi" },
6+
{ "LogicalResourceId":"MyApiProdStage", "ResourceType":"AWS::ApiGateway::Stage" },
7+
{ "LogicalResourceId":"MyFunction", "ResourceType":"AWS::Lambda::Function" },
8+
{ "LogicalResourceId":"MyFunctionRole", "ResourceType":"AWS::IAM::Role" },
9+
{ "LogicalResourceId":"MyApigetBasePathMapping", "ResourceType":"AWS::ApiGateway::BasePathMapping" },
10+
{ "LogicalResourceId":"MyFunctionFetchPermissionProd", "ResourceType":"AWS::Lambda::Permission" }
11+
]
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
[
2+
{ "LogicalResourceId":"MyFunctionImplicitGetPermissionProd", "ResourceType":"AWS::Lambda::Permission" },
3+
{ "LogicalResourceId":"ServerlessRestApiDeployment", "ResourceType":"AWS::ApiGateway::Deployment" },
4+
{ "LogicalResourceId":"ServerlessRestApipostBasePathMapping", "ResourceType":"AWS::ApiGateway::BasePathMapping" },
5+
{ "LogicalResourceId":"ServerlessRestApi", "ResourceType":"AWS::ApiGateway::RestApi" },
6+
{ "LogicalResourceId":"RecordSetGroupd17dced08c", "ResourceType":"AWS::Route53::RecordSetGroup" },
7+
{ "LogicalResourceId":"ServerlessRestApiProdStage", "ResourceType":"AWS::ApiGateway::Stage" },
8+
{ "LogicalResourceId":"ServerlessRestApigetBasePathMapping", "ResourceType":"AWS::ApiGateway::BasePathMapping" },
9+
{ "LogicalResourceId":"ApiGatewayDomainName98c928338d", "ResourceType":"AWS::ApiGateway::DomainName" },
10+
{ "LogicalResourceId":"MyFunction", "ResourceType":"AWS::Lambda::Function" },
11+
{ "LogicalResourceId":"MyFunctionImplicitPostPermissionProd", "ResourceType":"AWS::Lambda::Permission" },
12+
{ "LogicalResourceId":"MyFunctionRole", "ResourceType":"AWS::IAM::Role" }
13+
]

0 commit comments

Comments
 (0)