diff --git a/kiwi/runtime_checker.py b/kiwi/runtime_checker.py index 1c89bc16..8b4a3054 100644 --- a/kiwi/runtime_checker.py +++ b/kiwi/runtime_checker.py @@ -20,6 +20,7 @@ import re from textwrap import dedent # project +from io import StringIO from kiwi.xml_description import XMLDescription from kiwi.firmware import FirmWare from kiwi.xml_state import XMLState @@ -791,3 +792,44 @@ class RuntimeChecker: if not self.xml_state.get_image_version(): raise KiwiRuntimeError(message_missing_version) + + def check_image_type_unique(self): + """ + Verify that the selected image type is unique within + the range of the configured types and profiles. + """ + message = dedent('''\n + Conflicting image type setup detected + + The selected image type '{0}' in the {1} profile + selection is not unique. There are the followng type + settings which overrides each other: + {2} + To solve this conflict please move the image type + setup into its own profile and select them using + the --profile option at call time. + ''') + image_type_sections = [] + type_dict = {} + for preferences in self.xml_state.get_preferences_sections(): + image_type_sections += preferences.get_type() + + for image_type in image_type_sections: + type_name = image_type.get_image() + if type_dict.get(type_name): + type_dict[type_name].append(image_type) + else: + type_dict[type_name] = [image_type] + + for type_name, type_list in list(type_dict.items()): + if len(type_list) > 1: + type_export = StringIO() + for image_type in type_list: + type_export.write(os.linesep) + image_type.export(type_export, 0) + raise KiwiRuntimeError( + message.format( + type_name, self.xml_state.profiles or ['Default'], + type_export.getvalue() + ) + ) diff --git a/kiwi/tasks/base.py b/kiwi/tasks/base.py index 177a30a3..6f5a4630 100644 --- a/kiwi/tasks/base.py +++ b/kiwi/tasks/base.py @@ -89,7 +89,8 @@ class CliTask: 'check_dracut_module_for_oem_install_in_package_list': [], 'check_architecture_supports_iso_firmware_setup': [], 'check_appx_naming_conventions_valid': [], - 'check_syslinux_installed_if_isolinux_is_used': [] + 'check_syslinux_installed_if_isolinux_is_used': [], + 'check_image_type_unique': [] } self.checks_after_command_args = { 'check_repositories_configured': [], diff --git a/test/data/example_runtime_checker_conflicting_types.xml b/test/data/example_runtime_checker_conflicting_types.xml new file mode 100644 index 00000000..d4dfbb46 --- /dev/null +++ b/test/data/example_runtime_checker_conflicting_types.xml @@ -0,0 +1,26 @@ + + + + + Marcus Schäfer + ms@suse.de + Test conflicting type setup + + + 1.1.0 + zypper + + + + + + + + + + + + + + + diff --git a/test/unit/runtime_checker_test.py b/test/unit/runtime_checker_test.py index 320f0e5a..8ddfbd00 100644 --- a/test/unit/runtime_checker_test.py +++ b/test/unit/runtime_checker_test.py @@ -350,5 +350,14 @@ class TestRuntimeChecker: with raises(KiwiRuntimeError): runtime_checker.check_syslinux_installed_if_isolinux_is_used() + def test_check_image_type_unique(self): + description = XMLDescription( + '../data/example_runtime_checker_conflicting_types.xml' + ) + xml_state = XMLState(description.load()) + runtime_checker = RuntimeChecker(xml_state) + with raises(KiwiRuntimeError): + runtime_checker.check_image_type_unique() + def teardown(self): sys.argv = argv_kiwi_tests