You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
138 lines
6.0 KiB
Python
138 lines
6.0 KiB
Python
"""
|
|
All or portions of this file Copyright (c) Amazon.com, Inc. or its affiliates or
|
|
its licensors.
|
|
|
|
For complete copyright and license terms please see the LICENSE at the root of this
|
|
distribution (the "License"). All use of this software is governed by the License,
|
|
or, if provided, by the license below or the license accompanying this file. Do not
|
|
remove or modify any license notices. This file is distributed on an "AS IS" BASIS,
|
|
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
"""
|
|
|
|
import os
|
|
import pytest
|
|
import json
|
|
|
|
AWS_RESOURCE_MAPPINGS_KEY = 'AWSResourceMappings'
|
|
AWS_RESOURCE_MAPPINGS_ACCOUNT_ID_KEY = 'AccountId'
|
|
AWS_RESOURCE_MAPPINGS_REGION_KEY = 'Region'
|
|
|
|
|
|
class ResourceMappings:
|
|
"""
|
|
ResourceMappings class that handles writing Cloud formation outputs to resource mappings json file in a project.
|
|
"""
|
|
|
|
def __init__(self, file_path: str, region: str, feature_name: str, account_id: str, workspace: pytest.fixture,
|
|
cloud_formation_client):
|
|
"""
|
|
:param file_path: Path for the resource mapping file.
|
|
:param region: Region value for the resource mapping file.
|
|
:param feature_name: Feature gem name to use to append name to mappings key.
|
|
:param account_id: AWS account id value for the resource mapping file.
|
|
:param workspace: ly_test_tools workspace fixture.
|
|
:param cloud_formation_client: AWS cloud formation client.
|
|
"""
|
|
self._cdk_env = os.environ.copy()
|
|
self._cdk_env['PATH'] = f'{workspace.paths.engine_root()}\\python;' + self._cdk_env['PATH']
|
|
self._resource_mapping_file_path = file_path
|
|
self._region = region
|
|
self._feature_name = feature_name
|
|
self._account_id = account_id
|
|
|
|
assert os.path.exists(self._resource_mapping_file_path), \
|
|
f'Invalid resource mapping file path {self._resource_mapping_file_path}'
|
|
self._client = cloud_formation_client
|
|
|
|
def populate_output_keys(self, stacks=[]) -> None:
|
|
"""
|
|
Calls describe stacks on cloud formation service and persists outputs to resource mappings file.
|
|
:param stacks List of stack arns to describe and populate resource mappings with.
|
|
"""
|
|
for stack_name in stacks:
|
|
response = self._client.describe_stacks(
|
|
StackName=stack_name
|
|
)
|
|
stacks = response.get('Stacks', [])
|
|
assert len(stacks) == 1, f'{stack_name} is invalid.'
|
|
|
|
self.__write_resource_mappings(stacks[0].get('Outputs', []))
|
|
|
|
def __write_resource_mappings(self, outputs, append_feature_name = True) -> None:
|
|
with open(self._resource_mapping_file_path) as file_content:
|
|
resource_mappings = json.load(file_content)
|
|
|
|
resource_mappings[AWS_RESOURCE_MAPPINGS_ACCOUNT_ID_KEY] = self._account_id
|
|
resource_mappings[AWS_RESOURCE_MAPPINGS_REGION_KEY] = self._region
|
|
|
|
# Append new mappings.
|
|
resource_mappings[AWS_RESOURCE_MAPPINGS_KEY] = resource_mappings.get(AWS_RESOURCE_MAPPINGS_KEY, {})
|
|
|
|
for output in outputs:
|
|
if append_feature_name:
|
|
resource_key = f'{self._feature_name}.{output.get("OutputKey", "InvalidKey")}'
|
|
else:
|
|
resource_key = output.get("OutputKey", "InvalidKey")
|
|
resource_mappings[AWS_RESOURCE_MAPPINGS_KEY][resource_key] = resource_mappings[
|
|
AWS_RESOURCE_MAPPINGS_KEY].get(resource_key, {})
|
|
resource_mappings[AWS_RESOURCE_MAPPINGS_KEY][resource_key]['Type'] = 'AutomationTestType'
|
|
resource_mappings[AWS_RESOURCE_MAPPINGS_KEY][resource_key]['Name/ID'] = output.get('OutputValue',
|
|
'InvalidId')
|
|
|
|
with open(self._resource_mapping_file_path, 'w') as file_content:
|
|
json.dump(resource_mappings, file_content, indent=4)
|
|
|
|
def clear_output_keys(self) -> None:
|
|
"""
|
|
Clears values of all resource mapping keys. Sets region to default to us-west-2
|
|
"""
|
|
with open(self._resource_mapping_file_path) as file_content:
|
|
resource_mappings = json.load(file_content)
|
|
|
|
resource_mappings[AWS_RESOURCE_MAPPINGS_ACCOUNT_ID_KEY] = ''
|
|
resource_mappings[AWS_RESOURCE_MAPPINGS_REGION_KEY] = 'us-west-2'
|
|
|
|
# Append new mappings.
|
|
resource_mappings[AWS_RESOURCE_MAPPINGS_KEY] = resource_mappings.get(AWS_RESOURCE_MAPPINGS_KEY, {})
|
|
resource_mappings[AWS_RESOURCE_MAPPINGS_KEY] = {}
|
|
|
|
with open(self._resource_mapping_file_path, 'w') as file_content:
|
|
json.dump(resource_mappings, file_content, indent=4)
|
|
|
|
self._resource_mapping_file_path = ''
|
|
self._region = ''
|
|
self._client = None
|
|
|
|
|
|
@pytest.fixture(scope='function')
|
|
def resource_mappings(
|
|
request: pytest.fixture,
|
|
project: str,
|
|
feature_name: str,
|
|
resource_mappings_filename: str,
|
|
workspace: pytest.fixture,
|
|
aws_utils: pytest.fixture) -> ResourceMappings:
|
|
"""
|
|
Fixture for setting up resource mappings file.
|
|
:param request: _pytest.fixtures.SubRequest class that handles getting
|
|
a pytest fixture from a pytest function/fixture.
|
|
:param project: Project to find resource mapping file.
|
|
:param feature_name: AWS Gem name that is prepended to resource mapping keys.
|
|
:param resource_mappings_filename: Name of resource mapping file.
|
|
:param workspace: ly_test_tools workspace fixture.
|
|
:param aws_utils: AWS utils fixture.
|
|
:return: ResourceMappings class object.
|
|
"""
|
|
|
|
path = f'{workspace.paths.engine_root()}\\{project}\\Config\\{resource_mappings_filename}'
|
|
resource_mappings_obj = ResourceMappings(path, aws_utils.assume_session().region_name, feature_name,
|
|
aws_utils.assume_account_id(), workspace,
|
|
aws_utils.client('cloudformation'))
|
|
|
|
def teardown():
|
|
resource_mappings_obj.clear_output_keys()
|
|
|
|
request.addfinalizer(teardown)
|
|
|
|
return resource_mappings_obj
|