def summarize_device(device, part_filter=lambda p: True): """Return content for a table summarizing device. This (obj, cells) where obj is either device itself, a partition of device or None and cells is part of an argument to TableRow that will span 4 columns that describes device or a partition of device. This sounds a bit strange but hopefully you can figure it out by looking at the uses of this function. """ label = labels.label(device) anns = labels.annotations(device) if anns: label = "{} ({})".format(label, ", ".join(anns)) rows = [(device, [ (2, Text(label)), Text(labels.desc(device)), Text(humanize_size(device.size), align="right"), ])] partitions = device.partitions() if partitions: for part in device.partitions(): if not part_filter(part): continue details = ", ".join( labels.annotations(part) + labels.usage_labels(part)) rows.append((part, [ Text(labels.label(part, short=True)), (2, Text(details)), Text(humanize_size(part.size), align="right"), ])) else: rows.append((None, [ (4, Color.info_minor(Text(", ".join(labels.usage_labels(device))))) ])) return rows
def __init__(self, parent, obj): self.parent = parent self.obj = obj fs = obj.fs() if fs is not None: title = _("Remove filesystem from {device}").format( device=labels.desc(obj)) lines = [ _("Do you really want to remove the existing filesystem " "from {device}?").format(device=labels.label(obj)), "", ] m = fs.mount() if m is not None: lines.append( _("It is formatted as {fstype} and mounted at " "{path}").format(fstype=fs.fstype, path=m.path)) else: lines.append( _("It is formatted as {fstype} and not mounted.").format( fstype=fs.fstype)) else: if obj.type == "lvm_volgroup": things = _("logical volumes") else: things = _("partitions") # things is either "logical volumes" or "partitions" title = _("Remove all {things} from {obj}").format( things=things, obj=labels.desc(obj)) lines = [ _("Do you really want to remove all {things} from " "{obj}?").format(things=things, obj=labels.label(obj)), "", ] # XXX summarize partitions here? delete_btn = danger_btn(label=_("Reformat"), on_press=self.confirm) widgets = [ Text("\n".join(lines)), Text(""), button_pile([ delete_btn, other_btn(label=_("Cancel"), on_press=self.cancel), ]), ] super().__init__(title, widgets, 0, 2)
def set_bound_form_field(self, bff): super().set_bound_form_field(bff) self.all_rows = [] for kind, device in bff.form.possible_components: if kind == LABEL: self.all_rows.append(TableRow([ Text(" " + labels.label(device)), Text(humanize_size(device.size), align='right') ])) self.no_selector_rows.append(self.all_rows[-1]) self.all_rows.append(TableRow([ (2, Color.info_minor(Text(" " + labels.desc(device)))) ])) self.no_selector_rows.append(self.all_rows[-1]) else: label = labels.label(device, short=True) if kind == DEVICE: prefix = " " elif kind == PART: label = " " + label prefix = " " else: raise Exception("unexpected kind {}".format(kind)) box = CheckBox( label, on_state_change=self._state_change_device, user_data=device) self.device_to_checkbox[device] = box size = Text(humanize_size(device.size), align='right') self.all_rows.append(Color.menu_button(TableRow([box, size]))) self.no_selector_rows.append(self.all_rows[-1]) selector = Selector(['active', 'spare']) connect_signal( selector, 'select', self._select_active_spare, device) selector = Toggleable( UrwidPadding( Color.menu_button(selector), left=len(prefix))) selector.enabled = False self.device_to_selector[device] = selector self.all_rows.append(TableRow([(2, selector)])) # Do not append that one to no_selector_rows! self.all_rows.append(self._summarize(prefix, device)) self.no_selector_rows.append(self.all_rows[-1]) self.table.set_contents(self.all_rows)
def for_client(self, min_size): from subiquity.common.filesystem import labels from subiquity.common.types import Disk return Disk( id=self.id, label=labels.label(self), type=labels.desc(self), size=self.size, usage_labels=labels.usage_labels(self), partitions=[p.for_client() for p in self._partitions], ok_for_guided=self.size >= min_size)
def __init__(self, parent, obj): self.parent = parent self.obj = obj lines = [ Text( _("Do you really want to delete the {desc} {label}?").format( desc=labels.desc(obj), label=labels.label(obj))), Text(""), ] stretchy_index = 0 fs = obj.fs() if fs is not None: m = fs.mount() if m is not None: lines.append( Text( _("It is formatted as {fstype} and mounted at " "{path}").format(fstype=fs.fstype, path=m.path))) else: lines.append( Text( _("It is formatted as {fstype} and not mounted."). format(fstype=fs.fstype))) elif hasattr(obj, 'partitions') and len(obj.partitions()) > 0: n = len(obj.partitions()) if obj.type == "lvm_volgroup": line = ngettext("It contains 1 logical volume", "It contains {n} logical volumes", n) else: line = ngettext("It contains 1 partition", "It contains {n} partitions", n) lines.append(Text(line.format(n=n))) lines.append(Text("")) stretchy_index = len(lines) rows = [] for p, cells in summarize_device(obj): if p not in [None, obj]: rows.append(TableRow(cells)) lines.append(TablePile(rows)) else: lines.append(Text(_("It is not formatted or mounted."))) delete_btn = danger_btn(label=_("Delete"), on_press=self.confirm) widgets = lines + [ Text(""), button_pile([ delete_btn, other_btn(label=_("Cancel"), on_press=self.cancel), ]), ] super().__init__("", widgets, stretchy_index, len(lines) + 1)
def validate_mount(self): mount = self.mount.value if mount is None: return # /usr/include/linux/limits.h:PATH_MAX if len(mount) > 4095: return _('Path exceeds PATH_MAX') dev = self.mountpoints.get(mount) if dev is not None: return _("{device} is already mounted at {path}.").format( device=labels.label(dev).title(), path=mount) if self.existing_fs_type is not None: if self.fstype.value is None: if mount in common_mountpoints: if mount not in suitable_mountpoints_for_existing_fs: self.mount.show_extra( ('info_error', _("Mounting an existing filesystem at " "{mountpoint} is usually a bad idea, " "proceed only with caution.").format( mountpoint=mount)))
def __init__(self, parent, device): self.device = device self.model = parent.model self.controller = parent.controller self.parent = parent initial = {} fs = device.fs() if fs is not None: initial.update(initial_data_for_fs(fs)) elif not isinstance(device, Disk): initial['fstype'] = 'ext4' self.form = PartitionForm(self.model, 0, initial, None, device) self.form.remove_field('size') self.form.remove_field('name') connect_signal(self.form, 'submit', self.done) connect_signal(self.form, 'cancel', self.cancel) rows = [] if isinstance(device, Disk): rows = [ Text(_("Formatting and mounting a disk directly is unusual. " "You probably want to add a partition instead.")), Text(""), ] rows.extend(self.form.as_rows()) self.form.form_pile = Pile(rows) widgets = [ self.form.form_pile, Text(""), self.form.buttons, ] title = _("Format and/or mount {device}").format( device=labels.label(device)) super().__init__(title, widgets, 0, 0)
def __init__(self, parent, disk, partition=None): self.disk = disk self.partition = partition self.model = parent.model self.controller = parent.controller self.parent = parent max_size = disk.free_for_partitions initial = {} label = _("Create") if isinstance(disk, LVM_VolGroup): lvm_names = {p.name for p in disk.partitions()} else: lvm_names = None if self.partition: if partition.flag in ["bios_grub", "prep"]: label = None initial['mount'] = None elif boot.is_esp(partition) and not partition.grub_device: label = None else: label = _("Save") initial['size'] = humanize_size(self.partition.size) max_size += self.partition.size if not boot.is_esp(partition): initial.update(initial_data_for_fs(self.partition.fs())) else: if partition.fs() and partition.fs().mount(): initial['mount'] = '/boot/efi' else: initial['mount'] = None if isinstance(disk, LVM_VolGroup): initial['name'] = partition.name lvm_names.remove(partition.name) else: initial['fstype'] = 'ext4' if isinstance(disk, LVM_VolGroup): x = 0 while True: name = 'lv-{}'.format(x) if name not in lvm_names: break x += 1 initial['name'] = name self.form = PartitionForm( self.model, max_size, initial, lvm_names, partition) if not isinstance(disk, LVM_VolGroup): self.form.remove_field('name') if label is not None: self.form.buttons.base_widget[0].set_label(label) else: del self.form.buttons.base_widget.contents[0] self.form.buttons.base_widget[0].set_label(_("OK")) if partition is not None: if boot.is_esp(partition): if partition.original_fstype(): opts = [ Option(( _("Use existing fat32 filesystem"), True, None )), Option(("---", False)), Option(( _("Reformat as fresh fat32 filesystem"), True, "fat32" )), ] self.form.fstype.widget.options = opts if partition.fs().preserve: self.form.fstype.widget.index = 0 else: self.form.fstype.widget.index = 2 if not self.partition.grub_device: self.form.fstype.enabled = False self.form.mount.enabled = False else: opts = [Option(("fat32", True))] self.form.fstype.widget.options = opts self.form.fstype.widget.index = 0 self.form.mount.enabled = False self.form.fstype.enabled = False elif partition.flag in ["bios_grub", "prep"]: self.form.mount.enabled = False self.form.fstype.enabled = False self.form.size.enabled = False if partition.preserve: self.form.name.enabled = False self.form.size.enabled = False connect_signal(self.form, 'submit', self.done) connect_signal(self.form, 'cancel', self.cancel) rows = [] focus_index = 0 if partition is not None: if boot.is_esp(self.partition): if self.partition.grub_device: desc = _(configured_boot_partition_description) if self.partition.preserve: desc += _(boot_partition_description_reformat) else: desc += _(boot_partition_description_size) else: focus_index = 2 desc = _(unconfigured_boot_partition_description) rows.extend([ Text(rewrap(desc)), Text(""), ]) elif self.partition.flag == "bios_grub": if self.partition.device.grub_device: middle = _(configured_bios_grub_partition_middle) else: middle = _(unconfigured_bios_grub_partition_middle) desc = _(bios_grub_partition_description).format(middle=middle) rows.extend([ Text(rewrap(desc)), Text(""), ]) focus_index = 2 elif self.partition.flag == "prep": if self.partition.grub_device: desc = _(configured_prep_partition_description) else: desc = _(unconfigured_prep_partition_description) rows.extend([ Text(rewrap(desc)), Text(""), ]) focus_index = 2 rows.extend(self.form.as_rows()) self.form.form_pile = Pile(rows) widgets = [ self.form.form_pile, Text(""), self.form.buttons, ] if partition is None: if isinstance(disk, LVM_VolGroup): title = _("Adding logical volume to {vgname}").format( vgname=labels.label(disk)) else: title = _("Adding {ptype} partition to {device}").format( ptype=disk.ptable_for_new_partition().upper(), device=labels.label(disk)) else: if isinstance(disk, LVM_VolGroup): title = _( "Editing logical volume {lvname} of {vgname}" ).format( lvname=partition.name, vgname=labels.label(disk)) else: title = _("Editing partition {number} of {device}").format( number=partition.number, device=labels.label(disk)) super().__init__(title, widgets, 0, focus_index)