Convert block device size into nailgun data driver

Now all partition related tools expect "size" in bytest(not in MiB) or
instances of SizeUnit object. Nailgun was last data driver that
represented "size" of block devices in MiBs.

Change-Id: I03170969407d33a8921fc0b4b32739d1865c10e0
This commit is contained in:
Dmitry Bogun 2016-12-29 17:37:53 +02:00 committed by Andrii Ostapenko
parent 3dc8f1c411
commit 328dd6cd0c
3 changed files with 137 additions and 46 deletions

View File

@ -193,7 +193,7 @@ class PartitioningAction(base.BaseAction):
# creating physical volumes # creating physical volumes
for pv in self.driver.partition_scheme.pvs: for pv in self.driver.partition_scheme.pvs:
lu.pvcreate(pv.name, metadatasize=pv.metadatasize, lu.pvcreate(pv.name, metadatasize=utils.B2MiB(pv.metadatasize),
metadatacopies=pv.metadatacopies) metadatacopies=pv.metadatacopies)
# creating volume groups # creating volume groups

View File

@ -12,6 +12,7 @@
# See the License for the specific language governing permissions and # See the License for the specific language governing permissions and
# limitations under the License. # limitations under the License.
import copy
import itertools import itertools
import math import math
import os import os
@ -24,6 +25,7 @@ from six.moves.urllib.parse import urlparse
from six.moves.urllib.parse import urlsplit from six.moves.urllib.parse import urlsplit
import yaml import yaml
from bareon.utils import block_device
from bareon.utils import hardware as hu from bareon.utils import hardware as hu
from bareon.utils import utils from bareon.utils import utils
@ -355,6 +357,10 @@ class Nailgun(BaseDataDriver,
and v.get("mount") != "/boot" and v.get("mount") != "/boot"
)): )):
continue continue
disk = copy.deepcopy(disk)
self._convert_size_unit(disk, 'size', 'min_size', 'free_space')
LOG.debug('Processing disk %s' % disk['name']) LOG.debug('Processing disk %s' % disk['name'])
LOG.debug('Adding gpt table on disk %s' % disk['name']) LOG.debug('Adding gpt table on disk %s' % disk['name'])
parted = partition_scheme.add_parted( parted = partition_scheme.add_parted(
@ -367,11 +373,13 @@ class Nailgun(BaseDataDriver,
# legacy boot partition # legacy boot partition
LOG.debug('Adding bios_grub partition on disk %s: size=24' % LOG.debug('Adding bios_grub partition on disk %s: size=24' %
disk['name']) disk['name'])
parted.add_partition(size=24, flags=['bios_grub']) size = block_device.SizeUnit(24, 'MiB').bytes
parted.add_partition(size=size, flags=['bios_grub'])
# uefi partition (for future use) # uefi partition (for future use)
LOG.debug('Adding UEFI partition on disk %s: size=200' % LOG.debug('Adding UEFI partition on disk %s: size=200' %
disk['name']) disk['name'])
parted.add_partition(size=200) size = block_device.SizeUnit(200, 'MiB').bytes
parted.add_partition(size=size)
LOG.debug('Looping over all volumes on disk %s' % disk['name']) LOG.debug('Looping over all volumes on disk %s' % disk['name'])
for volume in disk['volumes']: for volume in disk['volumes']:
@ -384,6 +392,8 @@ class Nailgun(BaseDataDriver,
LOG.debug('Volume size is zero. Skipping.') LOG.debug('Volume size is zero. Skipping.')
continue continue
self._convert_size_unit(volume, 'size', 'lvm_meta_size')
if volume.get('name') == 'cephjournal': if volume.get('name') == 'cephjournal':
LOG.debug('Volume seems to be a CEPH journal volume. ' LOG.debug('Volume seems to be a CEPH journal volume. '
'Special procedure is supposed to be applied.') 'Special procedure is supposed to be applied.')
@ -394,9 +404,10 @@ class Nailgun(BaseDataDriver,
# No more than 10GB will be allocated to a single journal # No more than 10GB will be allocated to a single journal
# partition # partition
size = volume["size"] / ratio size = block_device.SizeUnit(volume['size'], 'B')
if size > 10240: count = size.in_unit('MiB').value / ratio
size = 10240 if count > 10240:
size = block_device.SizeUnit(10, 'GiB')
# This will attempt to evenly spread partitions across # This will attempt to evenly spread partitions across
# multiple devices e.g. 5 osds with 2 journal devices will # multiple devices e.g. 5 osds with 2 journal devices will
@ -413,7 +424,7 @@ class Nailgun(BaseDataDriver,
LOG.debug('Adding CEPH journal partition on ' LOG.debug('Adding CEPH journal partition on '
'disk %s: size=%s' % 'disk %s: size=%s' %
(disk['name'], size)) (disk['name'], size))
prt = parted.add_partition(size=size) prt = parted.add_partition(size=size.bytes)
LOG.debug('Partition name: %s' % prt.name) LOG.debug('Partition name: %s' % prt.name)
if 'partition_guid' in volume: if 'partition_guid' in volume:
LOG.debug('Setting partition GUID: %s' % LOG.debug('Setting partition GUID: %s' %
@ -430,9 +441,10 @@ class Nailgun(BaseDataDriver,
keep_data=volume.get('keep_data', False)) keep_data=volume.get('keep_data', False))
LOG.debug('Partition name: %s' % prt.name) LOG.debug('Partition name: %s' % prt.name)
elif volume.get('mount') == '/boot' \ elif (volume.get('mount') == '/boot'
and not self._boot_partition_done \ and not self._boot_partition_done
and disk in self.boot_disks: and disk['name'] in
[d['name'] for d in self.boot_disks]):
LOG.debug('Adding /boot partition on disk %s: ' LOG.debug('Adding /boot partition on disk %s: '
'size=%s', disk['name'], volume['size']) 'size=%s', disk['name'], volume['size'])
prt = parted.add_partition( prt = parted.add_partition(
@ -466,7 +478,10 @@ class Nailgun(BaseDataDriver,
if volume['type'] == 'pv': if volume['type'] == 'pv':
LOG.debug('Creating pv on partition: pv=%s vg=%s' % LOG.debug('Creating pv on partition: pv=%s vg=%s' %
(prt.name, volume['vg'])) (prt.name, volume['vg']))
lvm_meta_size = volume.get('lvm_meta_size', 64) lvm_meta_size = block_device.SizeUnit(64, 'MiB').bytes
lvm_meta_size = volume.get('lvm_meta_size', lvm_meta_size)
lvm_meta_size = block_device.SizeUnit(lvm_meta_size, 'B')
lvm_meta_size = lvm_meta_size.in_unit('MiB')
# The reason for that is to make sure that # The reason for that is to make sure that
# there will be enough space for creating logical volumes. # there will be enough space for creating logical volumes.
# Default lvm extension size is 4M. Nailgun volume # Default lvm extension size is 4M. Nailgun volume
@ -479,15 +494,17 @@ class Nailgun(BaseDataDriver,
# logical volume. Besides, parted aligns partitions # logical volume. Besides, parted aligns partitions
# according to its own algorithm and actual partition might # according to its own algorithm and actual partition might
# be a bit smaller than integer number of mebibytes. # be a bit smaller than integer number of mebibytes.
if lvm_meta_size < 10: if lvm_meta_size.value < 10:
raise errors.WrongPartitionSchemeError( raise errors.WrongPartitionSchemeError(
'Error while creating physical volume: ' 'Error while creating physical volume: '
'lvm metadata size is too small') 'lvm metadata size is too small')
metadatasize = int(math.floor((lvm_meta_size - 8) / 2)) metadatasize = int(
math.floor((lvm_meta_size.value - 8) / 2))
metadatasize = block_device.SizeUnit(metadatasize, 'MiB')
metadatacopies = 2 metadatacopies = 2
partition_scheme.vg_attach_by_name( partition_scheme.vg_attach_by_name(
pvname=prt.name, vgname=volume['vg'], pvname=prt.name, vgname=volume['vg'],
metadatasize=metadatasize, metadatasize=metadatasize.bytes,
metadatacopies=metadatacopies) metadatacopies=metadatacopies)
if volume['type'] == 'raid': if volume['type'] == 'raid':
@ -526,7 +543,8 @@ class Nailgun(BaseDataDriver,
(self._is_root_disk(disk) or self._is_os_disk(disk))): (self._is_root_disk(disk) or self._is_os_disk(disk))):
LOG.debug('Adding configdrive partition on disk %s: size=20' % LOG.debug('Adding configdrive partition on disk %s: size=20' %
disk['name']) disk['name'])
parted.add_partition(size=20, configdrive=True) size = block_device.SizeUnit(20, 'MiB').bytes
parted.add_partition(size=size, configdrive=True)
# checking if /boot is expected to be created # checking if /boot is expected to be created
if self._have_boot_partition(self.ks_disks) and \ if self._have_boot_partition(self.ks_disks) and \
@ -544,12 +562,16 @@ class Nailgun(BaseDataDriver,
for vg in self.ks_vgs: for vg in self.ks_vgs:
LOG.debug('Processing vg %s' % vg['id']) LOG.debug('Processing vg %s' % vg['id'])
LOG.debug('Looping over all logical volumes in vg %s' % vg['id']) LOG.debug('Looping over all logical volumes in vg %s' % vg['id'])
vg = copy.deepcopy(vg)
self._convert_size_unit(vg, 'size', 'min_size', 'free_space')
for volume in vg['volumes']: for volume in vg['volumes']:
LOG.debug('Processing lv %s' % volume['name']) LOG.debug('Processing lv %s' % volume['name'])
if volume['size'] <= 0: if volume['size'] <= 0:
LOG.debug('LogicalVolume size is zero. Skipping.') LOG.debug('LogicalVolume size is zero. Skipping.')
continue continue
self._convert_size_unit(volume, 'size', 'lvm_meta_size')
if volume['type'] == 'lv': if volume['type'] == 'lv':
LOG.debug('Adding lv to vg %s: name=%s, size=%s' % LOG.debug('Adding lv to vg %s: name=%s, size=%s' %
(vg['id'], volume['name'], volume['size'])) (vg['id'], volume['name'], volume['size']))
@ -722,6 +744,15 @@ class Nailgun(BaseDataDriver,
'Invalid partition schema: You must specify at least one ' 'Invalid partition schema: You must specify at least one '
'disk.') 'disk.')
@staticmethod
def _convert_size_unit(record, *fields):
for key in fields:
try:
value = record[key]
except KeyError:
continue
record[key] = block_device.SizeUnit(value, 'MiB').bytes
class Ironic(Nailgun): class Ironic(Nailgun):
def __init__(self, data): def __init__(self, data):

View File

@ -22,6 +22,7 @@ from bareon.actions import partitioning
from bareon.drivers.data import nailgun from bareon.drivers.data import nailgun
from bareon import objects from bareon import objects
from bareon.tests import test_nailgun from bareon.tests import test_nailgun
from bareon.utils import block_device as bd
from bareon.utils import utils from bareon.utils import utils
if six.PY2: if six.PY2:
@ -116,21 +117,59 @@ class TestPartitioningAction(unittest2.TestCase):
mock_pu.make_label.call_args_list) mock_pu.make_label.call_args_list)
mock_pu_mp_expected_calls = [ mock_pu_mp_expected_calls = [
mock.call('/dev/sda', 1, 24, 'primary', alignment='optimal'), mock.call('/dev/sda',
mock.call('/dev/sda', 25, 224, 'primary', alignment='optimal'), 1,
mock.call('/dev/sda', 225, 424, 'primary', alignment='optimal'), bd.SizeUnit(24, 'MiB').bytes,
mock.call('/dev/sda', 425, 624, 'primary', alignment='optimal'), 'primary', alignment='optimal'),
mock.call('/dev/sda', 625, 20062, 'primary', alignment='optimal'), mock.call('/dev/sda',
mock.call('/dev/sda', 20063, 65659, 'primary', bd.SizeUnit(24, 'MiB').bytes + 1,
alignment='optimal'), bd.SizeUnit(224, 'MiB').bytes,
mock.call('/dev/sda', 65660, 65679, 'primary', 'primary', alignment='optimal'),
alignment='optimal'), mock.call('/dev/sda',
mock.call('/dev/sdb', 1, 24, 'primary', alignment='optimal'), bd.SizeUnit(224, 'MiB').bytes + 1,
mock.call('/dev/sdb', 25, 224, 'primary', alignment='optimal'), bd.SizeUnit(424, 'MiB').bytes,
mock.call('/dev/sdb', 225, 65195, 'primary', alignment='optimal'), 'primary', alignment='optimal'),
mock.call('/dev/sdc', 1, 24, 'primary', alignment='optimal'), mock.call('/dev/sda',
mock.call('/dev/sdc', 25, 224, 'primary', alignment='optimal'), bd.SizeUnit(424, 'MiB').bytes + 1,
mock.call('/dev/sdc', 225, 65195, 'primary', alignment='optimal')] bd.SizeUnit(624, 'MiB').bytes,
'primary', alignment='optimal'),
mock.call('/dev/sda',
bd.SizeUnit(624, 'MiB').bytes + 1,
bd.SizeUnit(20062, 'MiB').bytes,
'primary', alignment='optimal'),
mock.call('/dev/sda',
bd.SizeUnit(20062, 'MiB').bytes + 1,
bd.SizeUnit(65659, 'MiB').bytes,
'primary', alignment='optimal'),
mock.call('/dev/sda',
bd.SizeUnit(65659, 'MiB').bytes + 1,
bd.SizeUnit(65679, 'MiB').bytes,
'primary', alignment='optimal'),
mock.call('/dev/sdb',
1,
bd.SizeUnit(24, 'MiB').bytes,
'primary', alignment='optimal'),
mock.call('/dev/sdb',
bd.SizeUnit(24, 'MiB').bytes + 1,
bd.SizeUnit(224, 'MiB').bytes,
'primary', alignment='optimal'),
mock.call('/dev/sdb',
bd.SizeUnit(224, 'MiB').bytes + 1,
bd.SizeUnit(65195, 'MiB').bytes,
'primary', alignment='optimal'),
mock.call('/dev/sdc',
1,
bd.SizeUnit(24, 'MiB').bytes,
'primary', alignment='optimal'),
mock.call('/dev/sdc',
bd.SizeUnit(24, 'MiB').bytes + 1,
bd.SizeUnit(224, 'MiB').bytes,
'primary', alignment='optimal'),
mock.call('/dev/sdc',
bd.SizeUnit(224, 'MiB').bytes + 1,
bd.SizeUnit(65195, 'MiB').bytes,
'primary', alignment='optimal'),
]
self.assertEqual(mock_pu_mp_expected_calls, self.assertEqual(mock_pu_mp_expected_calls,
mock_pu.make_partition.call_args_list) mock_pu.make_partition.call_args_list)
@ -158,9 +197,9 @@ class TestPartitioningAction(unittest2.TestCase):
self.assertEqual(mock_lu_v_expected_calls, self.assertEqual(mock_lu_v_expected_calls,
mock_lu.vgcreate.call_args_list) mock_lu.vgcreate.call_args_list)
mock_lu_l_expected_calls = [mock.call('os', 'root', 1), mock_lu_l_expected_calls = [mock.call('os', 'root', 15360),
mock.call('os', 'swap', 1), mock.call('os', 'swap', 4014),
mock.call('image', 'glance', 1)] mock.call('image', 'glance', 175347)]
self.assertEqual(mock_lu_l_expected_calls, self.assertEqual(mock_lu_l_expected_calls,
mock_lu.lvcreate.call_args_list) mock_lu.lvcreate.call_args_list)
@ -253,19 +292,40 @@ class TestManagerMultipathPartition(unittest2.TestCase):
mock.call('/dev/sdc', 'gpt')]) mock.call('/dev/sdc', 'gpt')])
self.assertEqual(mock_pu.make_partition.mock_calls, [ self.assertEqual(mock_pu.make_partition.mock_calls, [
mock.call('/dev/mapper/12312', 1, 24, 'primary', mock.call('/dev/mapper/12312',
alignment='optimal'), 1,
mock.call('/dev/mapper/12312', 25, 224, 'primary', bd.SizeUnit(24, 'MiB').bytes,
alignment='optimal'), 'primary', alignment='optimal'),
mock.call('/dev/mapper/12312', 225, 424, 'primary', mock.call('/dev/mapper/12312',
alignment='optimal'), bd.SizeUnit(24, 'MiB').bytes + 1,
mock.call('/dev/mapper/12312', 425, 624, 'primary', bd.SizeUnit(224, 'MiB').bytes,
alignment='optimal'), 'primary', alignment='optimal'),
mock.call('/dev/mapper/12312', 625, 644, 'primary', mock.call('/dev/mapper/12312',
alignment='optimal'), bd.SizeUnit(224, 'MiB').bytes + 1,
mock.call('/dev/sdc', 1, 24, 'primary', alignment='optimal'), bd.SizeUnit(424, 'MiB').bytes,
mock.call('/dev/sdc', 25, 224, 'primary', alignment='optimal'), 'primary', alignment='optimal'),
mock.call('/dev/sdc', 225, 424, 'primary', alignment='optimal')]) mock.call('/dev/mapper/12312',
bd.SizeUnit(424, 'MiB').bytes + 1,
bd.SizeUnit(624, 'MiB').bytes,
'primary', alignment='optimal'),
mock.call('/dev/mapper/12312',
bd.SizeUnit(624, 'MiB').bytes + 1,
bd.SizeUnit(644, 'MiB').bytes,
'primary', alignment='optimal'),
mock.call('/dev/sdc',
1,
bd.SizeUnit(24, 'MiB').bytes,
'primary', alignment='optimal'),
mock.call('/dev/sdc',
bd.SizeUnit(24, 'MiB').bytes + 1,
bd.SizeUnit(224, 'MiB').bytes,
'primary', alignment='optimal'),
mock.call('/dev/sdc',
bd.SizeUnit(224, 'MiB').bytes + 1,
bd.SizeUnit(424, 'MiB').bytes,
'primary', alignment='optimal'),
])
self.assertEqual(mock_pu.set_partition_flag.mock_calls, [ self.assertEqual(mock_pu.set_partition_flag.mock_calls, [
mock.call('/dev/mapper/12312', 1, 'bios_grub'), mock.call('/dev/mapper/12312', 1, 'bios_grub'),