From: Jan Fajerski Date: Wed, 23 Jan 2019 14:04:29 +0000 (+0100) Subject: ceph-volume: add osd_ids argument X-Git-Tag: v14.1.0~243^2~2 X-Git-Url: http://git-server-git.apps.pok.os.sepia.ceph.com/?a=commitdiff_plain;h=73978ca0c7ac1e95e89fb3bac6384cd931cefc04;p=ceph.git ceph-volume: add osd_ids argument Signed-off-by: Jan Fajerski --- diff --git a/src/ceph-volume/ceph_volume/devices/lvm/batch.py b/src/ceph-volume/ceph_volume/devices/lvm/batch.py index 3fb6be677fab..a7d2cbea8496 100644 --- a/src/ceph-volume/ceph_volume/devices/lvm/batch.py +++ b/src/ceph-volume/ceph_volume/devices/lvm/batch.py @@ -245,6 +245,12 @@ class Batch(object): action='store_true', help='Only prepare all OSDs, do not activate', ) + parser.add_argument( + '--osd-ids', + nargs='*', + default=[], + help='Reuse existing OSD ids', + ) self.args = parser.parse_args(argv) self.parser = parser diff --git a/src/ceph-volume/ceph_volume/devices/lvm/strategies/bluestore.py b/src/ceph-volume/ceph_volume/devices/lvm/strategies/bluestore.py index e1af45ecf8fe..0024d4428c9a 100644 --- a/src/ceph-volume/ceph_volume/devices/lvm/strategies/bluestore.py +++ b/src/ceph-volume/ceph_volume/devices/lvm/strategies/bluestore.py @@ -7,6 +7,7 @@ from .strategies import MixedStrategy from ceph_volume.devices.lvm.create import Create from ceph_volume.devices.lvm.prepare import Prepare from ceph_volume.util import templates +from ceph_volume.util.prepare import osd_id_available from ceph_volume.exceptions import SizeAllocationError @@ -39,6 +40,9 @@ class SingleType(Strategy): for osd in self.computed['osds']: string += templates.osd_header + if 'osd_id' in osd: + string += templates.osd_reused_id.format( + id_=osd['osd_id']) string += templates.osd_component.format( _type='[data]', path=osd['data']['path'], @@ -61,6 +65,9 @@ class SingleType(Strategy): # make sure that data devices do not have any LVs validators.no_lvm_membership(self.data_devs) + if self.osd_ids: + self._validate_osd_ids() + def compute(self): """ Go through the rules needed to properly size the lvs, return @@ -109,6 +116,9 @@ class SingleType(Strategy): if self.args.crush_device_class: command.extend(['--crush-device-class', self.args.crush_device_class]) + if self.osd_ids: + command.extend(['--osd-id', self.osd_ids.pop(0)]) + if self.args.prepare: Prepare(command).main() else: @@ -189,6 +199,9 @@ class MixedType(MixedStrategy): string += templates.osd_component_titles for osd in self.computed['osds']: string += templates.osd_header + if 'osd_id' in osd: + string += templates.osd_reused_id.format( + id_=osd['osd_id']) string += templates.osd_component.format( _type='[data]', path=osd['data']['path'], @@ -271,6 +284,9 @@ class MixedType(MixedStrategy): osd['block.wal']['human_readable_size'] = str(self.block_wal_size) osd['block.wal']['percentage'] = self.wal_vg_extents['percentages'] + if self.osd_ids: + osd['osd_id'] = self.osd_ids.pop(0) + osds.append(osd) self.computed['changed'] = len(osds) > 0 @@ -365,6 +381,8 @@ class MixedType(MixedStrategy): command.append('--no-systemd') if self.args.crush_device_class: command.extend(['--crush-device-class', self.args.crush_device_class]) + if 'osd_id' in osd: + command.extend(['--osd-id', osd['osd_id']]) if self.args.prepare: Prepare(command).main() @@ -389,6 +407,9 @@ class MixedType(MixedStrategy): if self.wal_devs: self._validate_wal_devs() + if self.osd_ids: + self._validate_osd_ids() + def _validate_db_devs(self): # do not allow non-common VG to continue validators.has_common_vg(self.db_or_journal_devs) @@ -510,3 +531,4 @@ class MixedType(MixedStrategy): self.block_wal_size, ) raise RuntimeError(msg) + diff --git a/src/ceph-volume/ceph_volume/devices/lvm/strategies/filestore.py b/src/ceph-volume/ceph_volume/devices/lvm/strategies/filestore.py index 3e21f766f3e3..42f9179faa34 100644 --- a/src/ceph-volume/ceph_volume/devices/lvm/strategies/filestore.py +++ b/src/ceph-volume/ceph_volume/devices/lvm/strategies/filestore.py @@ -52,6 +52,9 @@ class SingleType(Strategy): for osd in self.computed['osds']: string += templates.osd_header + if 'osd_id' in osd: + string += templates.osd_reused_id.format( + id_=osd['osd_id']) string += templates.osd_component.format( _type='[data]', path=osd['data']['path'], @@ -83,6 +86,9 @@ class SingleType(Strategy): # make sure that data devices do not have any LVs validators.no_lvm_membership(self.data_devs) + if self.osd_ids: + self._validate_osd_ids() + def compute(self): """ Go through the rules needed to properly size the lvs, return @@ -107,6 +113,10 @@ class SingleType(Strategy): osd['journal']['size'] = journal_size.b.as_int() osd['journal']['percentage'] = int(100 - data_percentage) osd['journal']['human_readable_size'] = str(journal_size) + + if self.osd_ids: + osd['osd_id'] = self.osd_ids.pop() + osds.append(osd) self.computed['changed'] = len(osds) > 0 @@ -150,6 +160,8 @@ class SingleType(Strategy): command.append('--no-systemd') if self.args.crush_device_class: command.extend(['--crush-device-class', self.args.crush_device_class]) + if 'osd_id' in osd: + command.extend(['--osd-id', osd['osd_id']]) if self.args.prepare: Prepare(command).main() @@ -205,6 +217,9 @@ class MixedType(MixedStrategy): for osd in self.computed['osds']: string += templates.osd_header + if 'osd_id' in osd: + string += templates.osd_reused_id.format( + id_=osd['osd_id']) string += templates.osd_component.format( _type='[data]', path=osd['data']['path'], @@ -271,6 +286,9 @@ class MixedType(MixedStrategy): ) raise RuntimeError(msg) + if self.osd_ids: + self._validate_osd_ids() + def compute(self): """ Go through the rules needed to properly size the lvs, return @@ -308,6 +326,10 @@ class MixedType(MixedStrategy): osd['journal']['size'] = self.journal_size.b.as_int() osd['journal']['percentage'] = int(self.journal_size.gb * 100 / vg_free) osd['journal']['human_readable_size'] = str(self.journal_size) + + if self.osd_ids: + osd['osd_id'] = self.osd_ids.pop(0) + osds.append(osd) self.computed['changed'] = len(osds) > 0 @@ -361,6 +383,8 @@ class MixedType(MixedStrategy): command.append('--no-systemd') if self.args.crush_device_class: command.extend(['--crush-device-class', self.args.crush_device_class]) + if 'osd_id' in osd: + command.extend(['--osd-id', osd['osd_id']]) if self.args.prepare: Prepare(command).main() diff --git a/src/ceph-volume/ceph_volume/devices/lvm/strategies/strategies.py b/src/ceph-volume/ceph_volume/devices/lvm/strategies/strategies.py index be13d30b0919..ccd0d955901c 100644 --- a/src/ceph-volume/ceph_volume/devices/lvm/strategies/strategies.py +++ b/src/ceph-volume/ceph_volume/devices/lvm/strategies/strategies.py @@ -1,4 +1,5 @@ import json +from ceph_volume.util.prepare import osd_id_available class Strategy(object): @@ -9,6 +10,7 @@ class Strategy(object): empty list for wal_devs. ''' self.args = args + self.osd_ids = args.osd_ids self.osds_per_device = args.osds_per_device self.devices = data_devs + wal_devs + db_or_journal_devs self.data_devs = data_devs @@ -36,6 +38,14 @@ class Strategy(object): report['filtered_devices'] = filtered_devices print(json.dumps(self.computed, indent=4, sort_keys=True)) + def _validate_osd_ids(self): + unavailable_ids = [id_ for id_ in self.osd_ids if + not osd_id_available(id_)] + if unavailable_ids: + msg = ("Not all specfied OSD ids are available: {}" + "unavailable").format(",".join(unavailable_ids)) + raise RuntimeError(msg) + @property def total_osds(self): return len(self.data_devs) * self.osds_per_device diff --git a/src/ceph-volume/ceph_volume/tests/devices/lvm/strategies/test_bluestore.py b/src/ceph-volume/ceph_volume/tests/devices/lvm/strategies/test_bluestore.py index b92b498a307a..1af580c631ad 100644 --- a/src/ceph-volume/ceph_volume/tests/devices/lvm/strategies/test_bluestore.py +++ b/src/ceph-volume/ceph_volume/tests/devices/lvm/strategies/test_bluestore.py @@ -5,7 +5,8 @@ from ceph_volume.devices.lvm.strategies import bluestore class TestSingleType(object): def test_hdd_device_is_large_enough(self, fakedevice, factory): - args = factory(filtered_devices=[], osds_per_device=1, block_db_size=None) + args = factory(filtered_devices=[], osds_per_device=1, + block_db_size=None, osd_ids=[]) devices = [ fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='1', size=6073740000)) ] @@ -16,7 +17,8 @@ class TestSingleType(object): assert computed_osd['data']['path'] == '/dev/sda' def test_sdd_device_is_large_enough(self, fakedevice, factory): - args = factory(filtered_devices=[], osds_per_device=1, block_db_size=None) + args = factory(filtered_devices=[], osds_per_device=1, + block_db_size=None, osd_ids=[]) devices = [ fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='0', size=6073740000)) ] @@ -27,7 +29,8 @@ class TestSingleType(object): assert computed_osd['data']['path'] == '/dev/sda' def test_device_cannot_have_many_osds_per_device(self, fakedevice, factory): - args = factory(filtered_devices=[], osds_per_device=3, block_db_size=None) + args = factory(filtered_devices=[], osds_per_device=3, + block_db_size=None, osd_ids=[]) devices = [ fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='1', size=6073740000)) ] @@ -36,7 +39,8 @@ class TestSingleType(object): assert 'Unable to use device 5.66 GB /dev/sda' in str(error) def test_device_is_lvm_member_fails(self, fakedevice, factory): - args = factory(filtered_devices=[], osds_per_device=1, block_db_size=None) + args = factory(filtered_devices=[], osds_per_device=1, + block_db_size=None, osd_ids=[]) devices = [ fakedevice(used_by_ceph=False, is_lvm_member=True, sys_api=dict(rotational='1', size=6073740000)) ] @@ -53,7 +57,8 @@ class TestMixedTypeConfiguredSize(object): # 3GB block.db in ceph.conf conf_ceph(get_safe=lambda *a: 3147483640) args = factory(filtered_devices=[], osds_per_device=1, - block_db_size=None, block_wal_size=None) + block_db_size=None, block_wal_size=None, + osd_ids=[]) ssd = fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='0', size=6073740000)) hdd = fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='1', size=6073740000)) devices = [ssd, hdd] @@ -70,7 +75,8 @@ class TestMixedTypeConfiguredSize(object): # 7GB block.db in ceph.conf conf_ceph(get_safe=lambda *a: 7747483640) args = factory(filtered_devices=[], osds_per_device=1, - block_db_size=None, block_wal_size=None) + block_db_size=None, block_wal_size=None, + osd_ids=[]) ssd = fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='0', size=6073740000)) hdd = fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='1', size=6073740000)) devices = [ssd, hdd] @@ -84,7 +90,8 @@ class TestMixedTypeConfiguredSize(object): # 3GB block.db in ceph.conf conf_ceph(get_safe=lambda *a: 3147483640) args = factory(filtered_devices=[], osds_per_device=2, - block_db_size=None, block_wal_size=None) + block_db_size=None, block_wal_size=None, + osd_ids=[]) ssd = fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='0', size=60737400000)) hdd = fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='1', size=6073740000)) devices = [ssd, hdd] @@ -100,7 +107,8 @@ class TestMixedTypeLargeAsPossible(object): def test_hdd_device_is_large_enough(self, stub_vgs, fakedevice, factory, conf_ceph): conf_ceph(get_safe=lambda *a: None) args = factory(filtered_devices=[], osds_per_device=1, - block_db_size=None, block_wal_size=None) + block_db_size=None, block_wal_size=None, + osd_ids=[]) ssd = fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='0', size=6073740000)) hdd = fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='1', size=6073740000)) devices = [ssd, hdd] @@ -117,7 +125,8 @@ class TestMixedTypeLargeAsPossible(object): def test_multi_hdd_device_is_large_enough(self, stub_vgs, fakedevice, factory, conf_ceph): conf_ceph(get_safe=lambda *a: None) args = factory(filtered_devices=[], osds_per_device=2, - block_db_size=None, block_wal_size=None) + block_db_size=None, block_wal_size=None, + osd_ids=[]) ssd = fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='0', size=60073740000)) hdd = fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='1', size=60073740000)) devices = [ssd, hdd] @@ -134,7 +143,8 @@ class TestMixedTypeLargeAsPossible(object): def test_multi_hdd_device_is_not_large_enough(self, stub_vgs, fakedevice, factory, conf_ceph): conf_ceph(get_safe=lambda *a: None) args = factory(filtered_devices=[], osds_per_device=2, - block_db_size=None, block_wal_size=None) + block_db_size=None, block_wal_size=None, + osd_ids=[]) ssd = fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='0', size=60737400000)) hdd = fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='1', size=6073740000)) devices = [ssd, hdd] diff --git a/src/ceph-volume/ceph_volume/tests/devices/lvm/strategies/test_filestore.py b/src/ceph-volume/ceph_volume/tests/devices/lvm/strategies/test_filestore.py index f1be2328c90a..02891cc607a7 100644 --- a/src/ceph-volume/ceph_volume/tests/devices/lvm/strategies/test_filestore.py +++ b/src/ceph-volume/ceph_volume/tests/devices/lvm/strategies/test_filestore.py @@ -7,7 +7,8 @@ class TestSingleType(object): def test_hdd_device_is_large_enough(self, fakedevice, factory, conf_ceph): conf_ceph(get_safe=lambda *a: '5120') - args = factory(filtered_devices=[], osds_per_device=1, journal_size=None) + args = factory(filtered_devices=[], osds_per_device=1, + journal_size=None, osd_ids=[]) devices = [ fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='1', size=12073740000)) ] @@ -19,7 +20,8 @@ class TestSingleType(object): def test_hdd_device_with_large_journal(self, fakedevice, factory, conf_ceph): conf_ceph(get_safe=lambda *a: '5120') - args = factory(filtered_devices=[], osds_per_device=1, journal_size=None) + args = factory(filtered_devices=[], osds_per_device=1, + journal_size=None, osd_ids=[]) devices = [ fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='1', size=6073740000)) ] @@ -30,7 +32,8 @@ class TestSingleType(object): def test_ssd_device_is_large_enough(self, fakedevice, factory, conf_ceph): conf_ceph(get_safe=lambda *a: '5120') - args = factory(filtered_devices=[], osds_per_device=1, journal_size=None) + args = factory(filtered_devices=[], osds_per_device=1, + journal_size=None, osd_ids=[]) devices = [ fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='0', size=12073740000)) ] @@ -42,7 +45,8 @@ class TestSingleType(object): def test_ssd_device_with_large_journal(self, fakedevice, factory, conf_ceph): conf_ceph(get_safe=lambda *a: '5120') - args = factory(filtered_devices=[], osds_per_device=1, journal_size=None) + args = factory(filtered_devices=[], osds_per_device=1, + journal_size=None, osd_ids=[]) devices = [ fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='0', size=6073740000)) ] @@ -53,7 +57,8 @@ class TestSingleType(object): def test_ssd_device_multi_osd(self, fakedevice, factory, conf_ceph): conf_ceph(get_safe=lambda *a: '5120') - args = factory(filtered_devices=[], osds_per_device=4, journal_size=None) + args = factory(filtered_devices=[], osds_per_device=4, + journal_size=None, osd_ids=[]) devices = [ fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='0', size=16073740000)) ] @@ -64,7 +69,8 @@ class TestSingleType(object): def test_hdd_device_multi_osd(self, fakedevice, factory, conf_ceph): conf_ceph(get_safe=lambda *a: '5120') - args = factory(filtered_devices=[], osds_per_device=4, journal_size=None) + args = factory(filtered_devices=[], osds_per_device=4, + journal_size=None, osd_ids=[]) devices = [ fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='1', size=16073740000)) ] @@ -75,7 +81,8 @@ class TestSingleType(object): def test_device_is_lvm_member_fails(self, fakedevice, factory, conf_ceph): conf_ceph(get_safe=lambda *a: '5120') - args = factory(filtered_devices=[], osds_per_device=1, journal_size=None) + args = factory(filtered_devices=[], osds_per_device=1, + journal_size=None, osd_ids=[]) devices = [ fakedevice(used_by_ceph=False, is_lvm_member=True, sys_api=dict(rotational='1', size=12073740000)) ] @@ -85,7 +92,8 @@ class TestSingleType(object): def test_hdd_device_with_small_configured_journal(self, fakedevice, factory, conf_ceph): conf_ceph(get_safe=lambda *a: '120') - args = factory(filtered_devices=[], osds_per_device=1, journal_size=None) + args = factory(filtered_devices=[], osds_per_device=1, + journal_size=None, osd_ids=[]) devices = [ fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='1', size=6073740000)) ] @@ -96,7 +104,8 @@ class TestSingleType(object): def test_ssd_device_with_small_configured_journal(self, fakedevice, factory, conf_ceph): conf_ceph(get_safe=lambda *a: '120') - args = factory(filtered_devices=[], osds_per_device=1, journal_size=None) + args = factory(filtered_devices=[], osds_per_device=1, + journal_size=None, osd_ids=[]) devices = [ fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='0', size=6073740000)) ] @@ -110,7 +119,8 @@ class TestMixedType(object): def test_minimum_size_is_not_met(self, stub_vgs, fakedevice, factory, conf_ceph): conf_ceph(get_safe=lambda *a: '120') - args = factory(filtered_devices=[], osds_per_device=1, journal_size=None) + args = factory(filtered_devices=[], osds_per_device=1, + journal_size=None, osd_ids=[]) devices = [ fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='0', size=6073740000)), fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='1', size=6073740000)) @@ -122,7 +132,8 @@ class TestMixedType(object): def test_ssd_device_is_not_large_enough(self, stub_vgs, fakedevice, factory, conf_ceph): conf_ceph(get_safe=lambda *a: '7120') - args = factory(filtered_devices=[], osds_per_device=1, journal_size=None) + args = factory(filtered_devices=[], osds_per_device=1, + journal_size=None, osd_ids=[]) devices = [ fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='0', size=6073740000)), fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='1', size=6073740000)) @@ -134,7 +145,8 @@ class TestMixedType(object): def test_hdd_device_is_lvm_member_fails(self, stub_vgs, fakedevice, factory, conf_ceph): conf_ceph(get_safe=lambda *a: '5120') - args = factory(filtered_devices=[], osds_per_device=1, journal_size=None) + args = factory(filtered_devices=[], osds_per_device=1, + journal_size=None, osd_ids=[]) devices = [ fakedevice(used_by_ceph=False, is_lvm_member=False, sys_api=dict(rotational='0', size=6073740000)), fakedevice(used_by_ceph=False, is_lvm_member=True, sys_api=dict(rotational='1', size=6073740000)) @@ -159,7 +171,8 @@ class TestMixedType(object): ]) conf_ceph(get_safe=lambda *a: '5120') - args = factory(filtered_devices=[], osds_per_device=1, journal_size=None) + args = factory(filtered_devices=[], osds_per_device=1, + journal_size=None, osd_ids=[]) devices = [ssd, hdd] result = filestore.MixedType.with_auto_devices(args, devices).computed['osds'][0] assert result['journal']['path'] == 'vg: fast' @@ -190,7 +203,8 @@ class TestMixedType(object): ]) conf_ceph(get_safe=lambda *a: '5120') - args = factory(filtered_devices=[], osds_per_device=1, journal_size=None) + args = factory(filtered_devices=[], osds_per_device=1, + journal_size=None, osd_ids=[]) devices = [ssd1, ssd2, hdd] with pytest.raises(RuntimeError) as error: filestore.MixedType.with_auto_devices(args, devices) @@ -199,7 +213,8 @@ class TestMixedType(object): def test_ssd_device_fails_multiple_osds(self, stub_vgs, fakedevice, factory, conf_ceph): conf_ceph(get_safe=lambda *a: '15120') - args = factory(filtered_devices=[], osds_per_device=2, journal_size=None) + args = factory(filtered_devices=[], osds_per_device=2, + journal_size=None, osd_ids=[]) devices = [ fakedevice(is_lvm_member=False, sys_api=dict(rotational='0', size=16073740000)), fakedevice(is_lvm_member=False, sys_api=dict(rotational='1', size=16073740000)) diff --git a/src/ceph-volume/ceph_volume/util/templates.py b/src/ceph-volume/ceph_volume/util/templates.py index 78edd63d702a..08d4756dec33 100644 --- a/src/ceph-volume/ceph_volume/util/templates.py +++ b/src/ceph-volume/ceph_volume/util/templates.py @@ -7,6 +7,10 @@ osd_component_titles = """ Type Path LV Size % of device""" +osd_reused_id = """ + OSD id {id_: <55}""" + + osd_component = """ {_type: <15} {path: <55} {size: <15} {percent}%"""