diff --git a/src/rpdk/core/project.py b/src/rpdk/core/project.py index 37b8af90..81a85b68 100644 --- a/src/rpdk/core/project.py +++ b/src/rpdk/core/project.py @@ -292,25 +292,19 @@ def load_settings(self): f"Project file '{self.settings_path}' exceeds maximum length of 10 KiB." ) # validate protocol version, if specified - try: - settings = raw_settings["settings"] - if "protocolVersion" in settings: - protocol_version = settings["protocolVersion"] - if protocol_version not in PROTOCOL_VERSION_VALUES: - raise InvalidProjectError( - f"Invalid 'protocolVersion' settings in '{self.settings_path}" - ) - else: - LOG.warning( - "No protovolVersion found: this will default to version 1.0.0 during registration. " - "Please consider upgrading to CFN-CLI 2.0 following the guide: " - "https://docs.aws.amazon.com/cloudformation-cli/latest/userguide/what-is-cloudformation-cli.html" + if "settings" in raw_settings and "protocolVersion" in raw_settings["settings"]: + protocol_version = raw_settings["settings"]["protocolVersion"] + if protocol_version not in PROTOCOL_VERSION_VALUES: + raise InvalidProjectError( + f"Invalid 'protocolVersion' settings in '{self.settings_path}" ) - except KeyError as e: - self._raise_invalid_project( - f"Error extracting protocol version from '{self.settings_path}'", e + else: + LOG.warning( + "No protovolVersion found: this will default to version 1.0.0 during registration. " + "Please consider upgrading to CFN-CLI 2.0 following the guide: " + "https://docs.aws.amazon.com/cloudformation-cli/latest/userguide/what-is-cloudformation-cli.html" ) - + # backward compatible if "artifact_type" not in raw_settings: raw_settings["artifact_type"] = ARTIFACT_TYPE_RESOURCE diff --git a/tests/test_project.py b/tests/test_project.py index 90d5dfa5..68bfe681 100644 --- a/tests/test_project.py +++ b/tests/test_project.py @@ -173,6 +173,32 @@ def test_load_settings_invalid_hooks_settings(project): mock_open.assert_called_once_with("r", encoding="utf-8") +def test_load_settings_invalid_protocol_version(project): + with patch_settings(project, '{"settings": {"protocolVersion": "3.0.0"}}') as mock_open: + with pytest.raises(InvalidProjectError): + project.load_settings() + mock_open.assert_called_once_with("r", encoding="utf-8") + + +def test_load_settings_missing_protocol_version(project): + plugin = object() + data = json.dumps( + { + "artifact_type": "MODULE", + "typeName": MODULE_TYPE_NAME, + "settings": {} + } + ) + patch_load = patch( + "rpdk.core.project.load_plugin", autospec=True, return_value=plugin + ) + + with patch_settings(project, data) as mock_open, patch_load as mock_load: + project.load_settings() + + assert project.settings == {} + + def test_load_settings_valid_json_for_resource(project): plugin = object() data = json.dumps( @@ -292,6 +318,59 @@ def test_load_settings_valid_json_for_hook(project): assert project.settings == {} +def test_load_settings_valid_protocol_version(project): + plugin = object() + data = json.dumps( + { + "artifact_type": "MODULE", + "typeName": MODULE_TYPE_NAME, + "settings": { + "protocolVersion": "2.0.0" + } + } + ) + patch_load = patch( + "rpdk.core.project.load_plugin", autospec=True, return_value=plugin + ) + + with patch_settings(project, data) as mock_open, patch_load as mock_load: + project.load_settings() + + mock_open.assert_called_once_with("r", encoding="utf-8") + mock_load.assert_not_called() + assert project.type_info == ("AWS", "Color", "Red", "MODULE") + assert project.type_name == MODULE_TYPE_NAME + assert project.language is None + assert project.artifact_type == ARTIFACT_TYPE_MODULE + assert project._plugin is None + assert project.settings == {"protocolVersion": "2.0.0"} + + +def test_load_settings_missing_settings(project): + plugin = object() + data = json.dumps( + { + "artifact_type": "MODULE", + "typeName": MODULE_TYPE_NAME, + } + ) + patch_load = patch( + "rpdk.core.project.load_plugin", autospec=True, return_value=plugin + ) + + with patch_settings(project, data) as mock_open, patch_load as mock_load: + project.load_settings() + + mock_open.assert_called_once_with("r", encoding="utf-8") + mock_load.assert_not_called() + assert project.type_info == ("AWS", "Color", "Red", "MODULE") + assert project.type_name == MODULE_TYPE_NAME + assert project.language is None + assert project.artifact_type == ARTIFACT_TYPE_MODULE + assert project._plugin is None + assert project.settings == {} + + def test_load_schema_settings_not_loaded(project): with pytest.raises(InternalError): project.load_schema()