Exemple #1
0
 def test_multiple_pvs_is_matched_by_tags(self, pvolumes, monkeypatch):
     FooPVolume = api.PVolume(vg_name="vg1", pv_name='/dev/sdc', pv_uuid="1000", pv_tags="ceph.foo=bar", lv_uuid="0000000")
     BarPVolume = api.PVolume(vg_name="vg", pv_name='/dev/sda', pv_uuid="0000", pv_tags="ceph.foo=bar")
     pvolumes.append(FooPVolume)
     pvolumes.append(BarPVolume)
     monkeypatch.setattr(api, 'PVolumes', lambda: pvolumes)
     with pytest.raises(exceptions.MultiplePVsError):
         api.get_pv(pv_tags={"ceph.foo": "bar"})
Exemple #2
0
 def test_multiple_pvs_is_matched_by_tags(self, pvolumes, monkeypatch):
     FooPVolume = api.PVolume(vg_name="vg1", pv_name='/dev/sdc', pv_uuid="1000", pv_tags="ceph.foo=bar", lv_uuid="0000000")
     BarPVolume = api.PVolume(vg_name="vg", pv_name='/dev/sda', pv_uuid="0000", pv_tags="ceph.foo=bar")
     pvolumes.append(FooPVolume)
     pvolumes.append(BarPVolume)
     monkeypatch.setattr(api, 'PVolumes', lambda: pvolumes)
     with pytest.raises(exceptions.MultiplePVsError):
         api.get_pv(pv_tags={"ceph.foo": "bar"})
Exemple #3
0
 def test_single_pv_is_matched_by_uuid(self, pvolumes, monkeypatch):
     FooPVolume = api.PVolume(
         pv_name='/dev/vg/foo',
         pv_uuid='1111', pv_tags="ceph.type=data")
     pvolumes.append(FooPVolume)
     monkeypatch.setattr(api, 'PVolumes', lambda: pvolumes)
     assert api.get_pv(pv_uuid='1111') == FooPVolume
Exemple #4
0
 def test_single_pv_is_matched(self, pvolumes, monkeypatch):
     FooPVolume = api.PVolume(pv_name='/dev/sda',
                              pv_uuid="0000",
                              pv_tags={})
     pvolumes.append(FooPVolume)
     monkeypatch.setattr(api, 'PVolumes', lambda: pvolumes)
     assert api.get_pv(pv_uuid='0000') == FooPVolume
Exemple #5
0
 def test_single_pv_is_matched_by_uuid(self, pvolumes, monkeypatch):
     FooPVolume = api.PVolume(
         pv_name='/dev/vg/foo',
         pv_uuid='1111', pv_tags="ceph.type=data", vg_name="vg")
     pvolumes.append(FooPVolume)
     monkeypatch.setattr(api, 'PVolumes', lambda: pvolumes)
     assert api.get_pv(pv_uuid='1111') == FooPVolume
Exemple #6
0
 def test_multiple_pvs_is_matched_by_name(self, pvolumes, monkeypatch):
     FooPVolume = api.PVolume(vg_name="vg", pv_name='/dev/sda', pv_uuid="0000", pv_tags={}, lv_uuid="0000000")
     BarPVolume = api.PVolume(vg_name="vg", pv_name='/dev/sda', pv_uuid="0000", pv_tags={})
     pvolumes.append(FooPVolume)
     pvolumes.append(BarPVolume)
     monkeypatch.setattr(api, 'PVolumes', lambda: pvolumes)
     assert api.get_pv(pv_name='/dev/sda') == FooPVolume
Exemple #7
0
 def test_multiple_pvs_is_matched_by_name(self, pvolumes, monkeypatch):
     FooPVolume = api.PVolume(vg_name="vg", pv_name='/dev/sda', pv_uuid="0000", pv_tags={}, lv_uuid="0000000")
     BarPVolume = api.PVolume(vg_name="vg", pv_name='/dev/sda', pv_uuid="0000", pv_tags={})
     pvolumes.append(FooPVolume)
     pvolumes.append(BarPVolume)
     monkeypatch.setattr(api, 'PVolumes', lambda: pvolumes)
     assert api.get_pv(pv_name='/dev/sda') == FooPVolume
Exemple #8
0
    def zap(self, args):
        device = args.device
        lv = api.get_lv_from_argument(device)
        if lv:
            # we are zapping a logical volume
            path = lv.lv_path
        else:
            # we are zapping a partition
            #TODO: ensure device is a partition
            path = device

        mlogger.info("Zapping: %s", path)

        # check if there was a pv created with the
        # name of device
        pv = api.get_pv(pv_name=device)
        if pv:
            vg_name = pv.vg_name
            lv = api.get_lv(vg_name=vg_name)

        dmcrypt = False
        dmcrypt_uuid = None
        if lv:
            osd_path = "/var/lib/ceph/osd/{}-{}".format(lv.tags['ceph.cluster_name'], lv.tags['ceph.osd_id'])
            dmcrypt_uuid = lv.lv_uuid
            dmcrypt = lv.encrypted
            if system.path_is_mounted(osd_path):
                mlogger.info("Unmounting %s", osd_path)
                system.unmount(osd_path)
        else:
            # we're most likely dealing with a partition here, check to
            # see if it was encrypted
            partuuid = disk.get_partuuid(device)
            if encryption.status("/dev/mapper/{}".format(partuuid)):
                dmcrypt_uuid = partuuid
                dmcrypt = True

        if dmcrypt and dmcrypt_uuid:
            dmcrypt_path = "/dev/mapper/{}".format(dmcrypt_uuid)
            mlogger.info("Closing encrypted path %s", dmcrypt_path)
            encryption.dmcrypt_close(dmcrypt_path)

        if args.destroy and pv:
            logger.info("Found a physical volume created from %s, will destroy all it's vgs and lvs", device)
            vg_name = pv.vg_name
            mlogger.info("Destroying volume group %s because --destroy was given", vg_name)
            api.remove_vg(vg_name)
            mlogger.info("Destroying physical volume %s because --destroy was given", device)
            api.remove_pv(device)
        elif args.destroy and not pv:
            mlogger.info("Skipping --destroy because no associated physical volumes are found for %s", device)

        wipefs(path)
        zap_data(path)

        if lv and not pv:
            # remove all lvm metadata
            lv.clear_tags()

        terminal.success("Zapping successful for: %s" % path)
Exemple #9
0
 def test_vg_name_is_set(self, pvolumes, monkeypatch):
     FooPVolume = api.PVolume(
         pv_name='/dev/vg/foo',
         pv_uuid='1111', pv_tags="ceph.type=data", vg_name="vg")
     pvolumes.append(FooPVolume)
     monkeypatch.setattr(api, 'PVolumes', lambda: pvolumes)
     pv = api.get_pv(pv_name="/dev/vg/foo")
     assert pv.vg_name == "vg"
Exemple #10
0
 def test_vg_name_is_set(self, pvolumes, monkeypatch):
     FooPVolume = api.PVolume(
         pv_name='/dev/vg/foo',
         pv_uuid='1111', pv_tags="ceph.type=data", vg_name="vg")
     pvolumes.append(FooPVolume)
     monkeypatch.setattr(api, 'PVolumes', lambda: pvolumes)
     pv = api.get_pv(pv_name="/dev/vg/foo")
     assert pv.vg_name == "vg"
Exemple #11
0
    def single_report(self, device, lvs=None):
        """
        Generate a report for a single device. This can be either a logical
        volume in the form of vg/lv or a device with an absolute path like
        /dev/sda1 or /dev/sda
        """
        if lvs is None:
            lvs = api.Volumes()
        report = {}
        lv = api.get_lv_from_argument(device)

        # check if there was a pv created with the
        # name of device
        pv = api.get_pv(pv_name=device)
        if pv and not lv:
            try:
                lv = api.get_lv(vg_name=pv.vg_name)
            except MultipleLVsError:
                lvs.filter(vg_name=pv.vg_name)
                return self.full_report(lvs=lvs)

        if lv:

            try:
                _id = lv.tags['ceph.osd_id']
            except KeyError:
                logger.warning('device is not part of ceph: %s', device)
                return report

            report.setdefault(_id, [])
            lv_report = lv.as_dict()
            lv_report['devices'] = self.match_devices(lv.lv_uuid)
            report[_id].append(lv_report)

        else:
            # this has to be a journal/wal/db device (not a logical volume) so try
            # to find the PARTUUID that should be stored in the OSD logical
            # volume
            for device_type in ['journal', 'block', 'wal', 'db']:
                device_tag_name = 'ceph.%s_device' % device_type
                device_tag_uuid = 'ceph.%s_uuid' % device_type
                associated_lv = lvs.get(lv_tags={device_tag_name: device})
                if associated_lv:
                    _id = associated_lv.tags['ceph.osd_id']
                    uuid = associated_lv.tags[device_tag_uuid]

                    report.setdefault(_id, [])
                    report[_id].append(
                        {
                            'tags': {'PARTUUID': uuid},
                            'type': device_type,
                            'path': device,
                        }
                    )
        return report
Exemple #12
0
def get_lvm_osd_info(final):
    pv = api.get_pv(pv_name=final['osd_partition'])
    if not pv:
        return

    lv = api.get_lv(vg_name=pv.vg_name)
    if lv:
        final['osd_data_block'] = lv.tags.get('ceph.block_device', '')
        final['osd_data_wal'] = lv.tags.get('ceph.wal_device', '')
        final['osd_data_db'] = lv.tags.get('ceph.db_device', '')
        final['osd_data_osd'] = lv.tags.get('ceph.data_device', '')
        final['osd_data_id'] = lv.tags.get('ceph.osd_id', '')
Exemple #13
0
    def single_report(self, device):
        """
        Generate a report for a single device. This can be either a logical
        volume in the form of vg/lv or a device with an absolute path like
        /dev/sda1 or /dev/sda
        """
        lvs = api.Volumes()
        report = {}
        lv = api.get_lv_from_argument(device)

        # check if there was a pv created with the
        # name of device
        pv = api.get_pv(pv_name=device)
        if pv and not lv:
            try:
                lv = api.get_lv(vg_name=pv.vg_name)
            except MultipleLVsError:
                lvs.filter(vg_name=pv.vg_name)
                return self.full_report(lvs=lvs)

        if lv:
            try:
                _id = lv.tags['ceph.osd_id']
            except KeyError:
                logger.warning('device is not part of ceph: %s', device)
                return report

            report.setdefault(_id, [])
            report[_id].append(
                lv.as_dict()
            )

        else:
            # this has to be a journal/wal/db device (not a logical volume) so try
            # to find the PARTUUID that should be stored in the OSD logical
            # volume
            for device_type in ['journal', 'block', 'wal', 'db']:
                device_tag_name = 'ceph.%s_device' % device_type
                device_tag_uuid = 'ceph.%s_uuid' % device_type
                associated_lv = lvs.get(lv_tags={device_tag_name: device})
                if associated_lv:
                    _id = associated_lv.tags['ceph.osd_id']
                    uuid = associated_lv.tags[device_tag_uuid]

                    report.setdefault(_id, [])
                    report[_id].append(
                        {
                            'tags': {'PARTUUID': uuid},
                            'type': device_type,
                            'path': device,
                        }
                    )
        return report
Exemple #14
0
    def zap(self, args):
        device = args.device
        lv = api.get_lv_from_argument(device)
        if lv:
            # we are zapping a logical volume
            path = lv.lv_path
        else:
            # we are zapping a partition
            #TODO: ensure device is a partition
            path = device

        mlogger.info("Zapping: %s", path)

        # check if there was a pv created with the
        # name of device
        pv = api.get_pv(pv_name=device)
        if pv:
            vg_name = pv.vg_name
            lv = api.get_lv(vg_name=vg_name)

        if lv:
            osd_path = "/var/lib/ceph/osd/{}-{}".format(
                lv.tags['ceph.cluster_name'], lv.tags['ceph.osd_id'])
            if system.path_is_mounted(osd_path):
                mlogger.info("Unmounting %s", osd_path)
                system.unmount(osd_path)

        if args.destroy and pv:
            logger.info(
                "Found a physical volume created from %s, will destroy all it's vgs and lvs",
                device)
            vg_name = pv.vg_name
            mlogger.info(
                "Destroying volume group %s because --destroy was given",
                vg_name)
            api.remove_vg(vg_name)
            mlogger.info(
                "Destroying physical volume %s because --destroy was given",
                device)
            api.remove_pv(device)
        elif args.destroy and not pv:
            mlogger.info(
                "Skipping --destroy because no associated physical volumes are found for %s",
                device)

        wipefs(path)
        zap_data(path)

        if lv and not pv:
            # remove all lvm metadata
            lv.clear_tags()

        terminal.success("Zapping successful for: %s" % path)
Exemple #15
0
    def zap(self, args):
        device = args.device
        lv = api.get_lv_from_argument(device)
        if lv:
            # we are zapping a logical volume
            path = lv.lv_path
        else:
            # we are zapping a partition
            #TODO: ensure device is a partition
            path = device

        mlogger.info("Zapping: %s", path)

        # check if there was a pv created with the
        # name of device
        pv = api.get_pv(pv_name=device)
        if pv:
            vg_name = pv.vg_name
            lv = api.get_lv(vg_name=vg_name)

        if lv:
            osd_path = "/var/lib/ceph/osd/{}-{}".format(lv.tags['ceph.cluster_name'], lv.tags['ceph.osd_id'])
            if system.path_is_mounted(osd_path):
                mlogger.info("Unmounting %s", osd_path)
                system.unmount(osd_path)

        if args.destroy and pv:
            logger.info("Found a physical volume created from %s, will destroy all it's vgs and lvs", device)
            vg_name = pv.vg_name
            mlogger.info("Destroying volume group %s because --destroy was given", vg_name)
            api.remove_vg(vg_name)
            mlogger.info("Destroying physical volume %s because --destroy was given", device)
            api.remove_pv(device)
        elif args.destroy and not pv:
            mlogger.info("Skipping --destroy because no associated physical volumes are found for %s", device)

        wipefs(path)
        zap_data(path)

        if lv and not pv:
            # remove all lvm metadata
            lv.clear_tags()

        terminal.success("Zapping successful for: %s" % path)
Exemple #16
0
 def test_nothing_is_passed_in(self):
     # so we return a None
     assert api.get_pv() is None
Exemple #17
0
 def test_nothing_is_passed_in(self):
     # so we return a None
     assert api.get_pv() is None
Exemple #18
0
    def zap(self, args):
        device = args.device
        if disk.is_mapper_device(device):
            terminal.error(
                "Refusing to zap the mapper device: {}".format(device))
            raise SystemExit(1)
        lv = api.get_lv_from_argument(device)
        if lv:
            # we are zapping a logical volume
            path = lv.lv_path
        else:
            # we are zapping a partition
            #TODO: ensure device is a partition
            path = device

        mlogger.info("Zapping: %s", path)

        # check if there was a pv created with the
        # name of device
        pv = api.get_pv(pv_name=device)
        if pv:
            vg_name = pv.vg_name
            lv = api.get_lv(vg_name=vg_name)

        dmcrypt = False
        dmcrypt_uuid = None
        if lv:
            if lv.tags.get('ceph.cluster_name') and lv.tags.get('ceph.osd_id'):
                lv_path = "/var/lib/ceph/osd/{}-{}".format(
                    lv.tags['ceph.cluster_name'], lv.tags['ceph.osd_id'])
            else:
                lv_path = lv.path
            dmcrypt_uuid = lv.lv_uuid
            dmcrypt = lv.encrypted
            if system.path_is_mounted(lv_path):
                mlogger.info("Unmounting %s", lv_path)
                system.unmount(lv_path)
        else:
            # we're most likely dealing with a partition here, check to
            # see if it was encrypted
            partuuid = disk.get_partuuid(device)
            if encryption.status("/dev/mapper/{}".format(partuuid)):
                dmcrypt_uuid = partuuid
                dmcrypt = True

        if dmcrypt and dmcrypt_uuid:
            dmcrypt_path = "/dev/mapper/{}".format(dmcrypt_uuid)
            mlogger.info("Closing encrypted path %s", dmcrypt_path)
            encryption.dmcrypt_close(dmcrypt_path)

        if args.destroy and pv:
            logger.info(
                "Found a physical volume created from %s, will destroy all it's vgs and lvs",
                device)
            vg_name = pv.vg_name
            mlogger.info(
                "Destroying volume group %s because --destroy was given",
                vg_name)
            api.remove_vg(vg_name)
            mlogger.info(
                "Destroying physical volume %s because --destroy was given",
                device)
            api.remove_pv(device)
        elif args.destroy and not pv:
            mlogger.info(
                "Skipping --destroy because no associated physical volumes are found for %s",
                device)

        wipefs(path)
        zap_data(path)

        if lv and not pv:
            # remove all lvm metadata
            lv.clear_tags()

        terminal.success("Zapping successful for: %s" % path)
Exemple #19
0
 def test_single_pv_is_matched(self, pvolumes, monkeypatch):
     FooPVolume = api.PVolume(vg_name="vg", pv_name='/dev/sda', pv_uuid="0000", pv_tags={})
     pvolumes.append(FooPVolume)
     monkeypatch.setattr(api, 'PVolumes', lambda: pvolumes)
     assert api.get_pv(pv_uuid='0000') == FooPVolume