diff --git a/src/core/src/core_logic/ExecutionConfig.py b/src/core/src/core_logic/ExecutionConfig.py index cfff4d7d..04cec562 100644 --- a/src/core/src/core_logic/ExecutionConfig.py +++ b/src/core/src/core_logic/ExecutionConfig.py @@ -108,9 +108,9 @@ def __get_max_patch_publish_date(self, health_store_id): """ Obtains implicit date ceiling for published date - converts pub_off_sku_2024.04.01 to 20240401T000000Z """ max_patch_publish_date = str() if health_store_id is not None and health_store_id != "": - split = health_store_id.split("_") - if len(split) == 4 and len(split[3]) == 10: - max_patch_publish_date = "{0}T000000Z".format(split[3].replace(".", "")) + date_candidate = str(health_store_id)[-10:].replace(".", "") # last 10 characters and remove '.' + if len(date_candidate) == 8 and date_candidate.isdigit() and str(health_store_id)[-11:-10] == "_": + max_patch_publish_date = date_candidate + "T000000Z" self.composite_logger.log_debug("[EC] Getting max patch publish date. [MaxPatchPublishDate={0}][HealthStoreId={1}]".format(str(max_patch_publish_date), str(health_store_id))) return max_patch_publish_date diff --git a/src/core/src/package_managers/YumPackageManager.py b/src/core/src/package_managers/YumPackageManager.py index d66a0976..33a5cf91 100644 --- a/src/core/src/package_managers/YumPackageManager.py +++ b/src/core/src/package_managers/YumPackageManager.py @@ -84,7 +84,7 @@ def __init__(self, env_layer, execution_config, composite_logger, telemetry_writ # if an Auto Patching request comes in on a CentOS machine with Security and/or Critical classifications selected, we need to install all patches installation_included_classifications = [] if execution_config.included_classifications_list is None else execution_config.included_classifications_list - if execution_config.maintenance_run_id is not None and execution_config.operation.lower() == Constants.INSTALLATION.lower() \ + if execution_config.health_store_id is not str() and execution_config.operation.lower() == Constants.INSTALLATION.lower() \ and 'CentOS' in str(env_layer.platform.linux_distribution()) \ and 'Critical' in installation_included_classifications and 'Security' in installation_included_classifications: self.composite_logger.log_debug("Updating classifications list to install all patches for the Auto Patching request since classification based patching is not available on CentOS machines") diff --git a/src/core/tests/Test_CoreMain.py b/src/core/tests/Test_CoreMain.py index c815b420..682787d2 100644 --- a/src/core/tests/Test_CoreMain.py +++ b/src/core/tests/Test_CoreMain.py @@ -432,9 +432,7 @@ def test_install_all_packages_for_centos_autopatching(self): LegacyEnvLayerExtensions.LegacyPlatform.linux_distribution = self.mock_linux_distribution_to_return_centos argument_composer = ArgumentComposer() - maintenance_run_id = "9/28/2020 02:00:00 PM +00:00" classifications_to_include = ["Security", "Critical"] - argument_composer.maintenance_run_id = str(maintenance_run_id) argument_composer.health_store_id = str("pub_off_sku_2020.09.29") argument_composer.classifications_to_include = classifications_to_include argument_composer.reboot_setting = 'Always' @@ -449,6 +447,7 @@ def test_install_all_packages_for_centos_autopatching(self): with runtime.env_layer.file_system.open(runtime.execution_config.status_file_path, 'r') as file_handle: substatus_file_data = json.load(file_handle)[0]["status"]["substatus"] self.assertEqual(len(substatus_file_data), 4) + self.assertTrue(runtime.execution_config.max_patch_publish_date == "20200929T000000Z") self.assertTrue(substatus_file_data[0]["name"] == Constants.PATCH_ASSESSMENT_SUMMARY) self.assertTrue(substatus_file_data[0]["status"].lower() == Constants.STATUS_SUCCESS.lower()) self.assertTrue(substatus_file_data[1]["name"] == Constants.PATCH_INSTALLATION_SUMMARY) diff --git a/src/core/tests/Test_ExecutionConfig.py b/src/core/tests/Test_ExecutionConfig.py new file mode 100644 index 00000000..16756e2c --- /dev/null +++ b/src/core/tests/Test_ExecutionConfig.py @@ -0,0 +1,49 @@ +# Copyright 2025 Microsoft Corporation +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# +# Requires Python 2.7+ +import unittest + +from core.src.bootstrap.Constants import Constants +from core.tests.library.ArgumentComposer import ArgumentComposer +from core.tests.library.RuntimeCompositor import RuntimeCompositor + + +class TestExecutionConfig(unittest.TestCase): + def setUp(self): + pass + + def tearDown(self): + pass + + def test_get_max_patch_publish_date(self): + test_input_output_table = [ + ["pub_off_sku_2020.09.29", "20200929T000000Z"], + ["pu_b_off_sk_u_2020.09.29", "20200929T000000Z"], + [str(), str()], + ["pub_off_sku_20.09.29", str()], + ["pub_off_sku_2020.9.29", str()], + ["pub_off_sk_u2020.09.29", str()], + ["x_2020.09.29", "20200929T000000Z"] # theoretically okay + ] + + argument_composer = ArgumentComposer() + runtime = RuntimeCompositor(argument_composer.get_composed_arguments(), True, Constants.YUM) + for row in test_input_output_table: + self.assertEqual(runtime.execution_config._ExecutionConfig__get_max_patch_publish_date(row[0]), row[1]) + runtime.stop() + + +if __name__ == '__main__': + unittest.main()