diff --git a/kiwi/builder/disk.py b/kiwi/builder/disk.py index d763af26..b8e4c94f 100644 --- a/kiwi/builder/disk.py +++ b/kiwi/builder/disk.py @@ -326,7 +326,7 @@ class DiskBuilder: 'resize_on_boot': self.disk_resize_requested } - self.volume_manager = VolumeManager( + self.volume_manager = VolumeManager.new( self.volume_manager_name, device_map, self.root_dir + '/', self.volumes, diff --git a/kiwi/volume_manager/__init__.py b/kiwi/volume_manager/__init__.py index 0ffcefbd..e0a6006a 100644 --- a/kiwi/volume_manager/__init__.py +++ b/kiwi/volume_manager/__init__.py @@ -15,16 +15,20 @@ # You should have received a copy of the GNU General Public License # along with kiwi. If not, see # -# project -from kiwi.volume_manager.lvm import VolumeManagerLVM -from kiwi.volume_manager.btrfs import VolumeManagerBtrfs - -from kiwi.exceptions import ( - KiwiVolumeManagerSetupError +import importlib +from typing import ( + Dict, List +) +from abc import ( + ABCMeta, + abstractmethod ) +# project +from kiwi.exceptions import KiwiVolumeManagerSetupError -class VolumeManager: + +class VolumeManager(metaclass=ABCMeta): """ **VolumeManager factory** @@ -35,18 +39,30 @@ class VolumeManager: :param list volumes: list of volumes from :class:`XMLState::get_volumes()` :param dict custom_args: dictionary of custom volume manager arguments """ - def __new__( - self, name, device_map, root_dir, volumes, custom_args=None + @abstractmethod + def __init__(self) -> None: + return None # pragma: no cover + + @staticmethod + def new( + name: str, device_map: object, root_dir: str, + volumes: List, custom_args: Dict = None ): - if name == 'lvm': - return VolumeManagerLVM( + name_map = { + 'lvm': 'LVM', + 'btrfs': 'Btrfs' + } + try: + volume_manager = importlib.import_module( + 'kiwi.volume_manager.{0}'.format(name) + ) + module_name = 'VolumeManager{0}'.format(name_map[name]) + return volume_manager.__dict__[module_name]( device_map, root_dir, volumes, custom_args ) - elif name == 'btrfs': - return VolumeManagerBtrfs( - device_map, root_dir, volumes, custom_args - ) - else: + except Exception as issue: raise KiwiVolumeManagerSetupError( - 'Support for %s volume manager not implemented' % name + 'Support for {0} volume manager not implemented: {1}'.format( + name, issue + ) ) diff --git a/test/unit/builder/disk_test.py b/test/unit/builder/disk_test.py index 9cb38dfa..85d370ec 100644 --- a/test/unit/builder/disk_test.py +++ b/test/unit/builder/disk_test.py @@ -716,7 +716,7 @@ class TestDiskBuilder: ) @patch('kiwi.builder.disk.FileSystem.new') - @patch('kiwi.builder.disk.VolumeManager') + @patch('kiwi.builder.disk.VolumeManager.new') @patch('kiwi.builder.disk.Command.run') @patch('kiwi.builder.disk.Defaults.get_grub_boot_directory_name') @patch('os.path.exists') diff --git a/test/unit/volume_manager/init_test.py b/test/unit/volume_manager/init_test.py index 3cfc0c50..9e55b87f 100644 --- a/test/unit/volume_manager/init_test.py +++ b/test/unit/volume_manager/init_test.py @@ -11,26 +11,22 @@ from kiwi.exceptions import KiwiVolumeManagerSetupError class TestVolumeManager: def test_volume_manager_not_implemented(self): with raises(KiwiVolumeManagerSetupError): - VolumeManager('foo', Mock(), 'root_dir', Mock()) + VolumeManager.new('foo', Mock(), 'root_dir', [Mock()]) - @patch('kiwi.volume_manager.VolumeManagerLVM') - @patch('os.path.exists') - def test_volume_manager_lvm(self, mock_path, mock_lvm): - mock_path.return_value = True + @patch('kiwi.volume_manager.lvm.VolumeManagerLVM') + def test_volume_manager_lvm(self, mock_lvm): device_map = Mock() - volumes = Mock() - VolumeManager('lvm', device_map, 'root_dir', volumes) + volumes = [Mock()] + VolumeManager.new('lvm', device_map, 'root_dir', volumes) mock_lvm.assert_called_once_with( device_map, 'root_dir', volumes, None ) - @patch('kiwi.volume_manager.VolumeManagerBtrfs') - @patch('os.path.exists') - def test_volume_manager_btrfs(self, mock_path, mock_btrfs): - mock_path.return_value = True + @patch('kiwi.volume_manager.btrfs.VolumeManagerBtrfs') + def test_volume_manager_btrfs(self, mock_btrfs): device_map = Mock() - volumes = Mock() - VolumeManager('btrfs', device_map, 'root_dir', volumes) + volumes = [Mock()] + VolumeManager.new('btrfs', device_map, 'root_dir', volumes) mock_btrfs.assert_called_once_with( device_map, 'root_dir', volumes, None )