More documentation and added another column for default_dispvm to Qube Manager

Including also a minor visual fix - the headers in Qube Manager
will now be multi-line when it looks needed.

fixes QubesOS/qubes-issues#4912
This commit is contained in:
Marta Marczykowska-Górecka 2019-04-03 18:47:15 +02:00
parent cf1dd0d355
commit c2e7010b25
No known key found for this signature in database
GPG Key ID: 9A752C30B26FD04B
3 changed files with 76 additions and 23 deletions

View File

@ -75,8 +75,6 @@ class VmRowInTable:
# pylint: disable=too-few-public-methods # pylint: disable=too-few-public-methods
def __init__(self, vm, row_no, table): def __init__(self, vm, row_no, table):
self.vm = vm self.vm = vm
# TODO: replace a various different widgets with a more generic
# VmFeatureWidget or VMPropertyWidget
table_widgets.row_height = VmManagerWindow.row_height table_widgets.row_height = VmManagerWindow.row_height
table.setRowHeight(row_no, VmManagerWindow.row_height) table.setRowHeight(row_no, VmManagerWindow.row_height)
@ -136,10 +134,16 @@ class VmRowInTable:
'Last backup'], self.last_backup_widget) 'Last backup'], self.last_backup_widget)
self.dvm_template_widget = table_widgets.VMPropertyItem( self.dvm_template_widget = table_widgets.VMPropertyItem(
vm, "template_for_dispvms", empty_function=(lambda x: not x)) vm, "default_dispvm")
table.setItem(row_no, VmManagerWindow.columns_indices['DVM Template'], table.setItem(row_no, VmManagerWindow.columns_indices['Default DispVM'],
self.dvm_template_widget) self.dvm_template_widget)
self.is_dispvm_template_widget = table_widgets.VMPropertyItem(
vm, "template_for_dispvms", empty_function=(lambda x: not x))
table.setItem(
row_no, VmManagerWindow.columns_indices['Is DVM Template'],
self.is_dispvm_template_widget)
self.table = table self.table = table
def update(self, update_size_on_disk=False, event=None): def update(self, update_size_on_disk=False, event=None):
@ -167,6 +171,10 @@ class VmRowInTable:
self.include_in_backups_widget.update() self.include_in_backups_widget.update()
if not event or event.endswith(':backup_timestamp'): if not event or event.endswith(':backup_timestamp'):
self.last_backup_widget.update() self.last_backup_widget.update()
if not event or event.endswith(':default_dispvm'):
self.dvm_template_widget.update()
if not event or event.endswith(':template_for_dispvms'):
self.is_dispvm_template_widget.update()
if update_size_on_disk: if update_size_on_disk:
self.size_widget.update() self.size_widget.update()
except exc.QubesPropertyAccessError: except exc.QubesPropertyAccessError:
@ -340,7 +348,8 @@ class VmManagerWindow(ui_qubemanager.Ui_VmManagerWindow, QtGui.QMainWindow):
"IP": 8, "IP": 8,
"Include in backups": 9, "Include in backups": 9,
"Last backup": 10, "Last backup": 10,
"DVM Template": 11 "Default DispVM": 11,
"Is DVM Template": 12
} }
def __init__(self, qt_app, qubes_app, dispatcher, parent=None): def __init__(self, qt_app, qubes_app, dispatcher, parent=None):
@ -384,7 +393,8 @@ class VmManagerWindow(ui_qubemanager.Ui_VmManagerWindow, QtGui.QMainWindow):
self.columns_indices["IP"]: self.action_ip, self.columns_indices["IP"]: self.action_ip,
self.columns_indices["Include in backups"]: self.action_backups, self.columns_indices["Include in backups"]: self.action_backups,
self.columns_indices["Last backup"]: self.action_last_backup, self.columns_indices["Last backup"]: self.action_last_backup,
self.columns_indices["DVM Template"]: self.action_dvm_template self.columns_indices["Default DispVM"]: self.action_dispvm_template,
self.columns_indices["Is DVM Template"]: self.action_is_dvm_template
} }
self.visible_columns_count = len(self.columns_indices) self.visible_columns_count = len(self.columns_indices)
@ -1187,8 +1197,13 @@ class VmManagerWindow(ui_qubemanager.Ui_VmManagerWindow, QtGui.QMainWindow):
def on_action_size_on_disk_toggled(self, checked): def on_action_size_on_disk_toggled(self, checked):
self.showhide_column(self.columns_indices['Size'], checked) self.showhide_column(self.columns_indices['Size'], checked)
def on_action_dvm_template_toggled(self, checked): # pylint: disable=invalid-name
self.showhide_column(self.columns_indices['DVM Template'], checked) def on_action_dispvm_template_toggled(self, checked):
self.showhide_column(self.columns_indices['Default DispVM'], checked)
# pylint: disable=invalid-name
def on_action_is_dvm_template_toggled(self, checked):
self.showhide_column(self.columns_indices['Is DVM Template'], checked)
# noinspection PyArgumentList # noinspection PyArgumentList
@QtCore.pyqtSlot(name='on_action_about_qubes_triggered') @QtCore.pyqtSlot(name='on_action_about_qubes_triggered')

View File

@ -267,6 +267,18 @@ class VmInfoWidget(QtGui.QWidget):
class VMPropertyItem(QtGui.QTableWidgetItem): class VMPropertyItem(QtGui.QTableWidgetItem):
def __init__(self, vm, property_name, empty_function=(lambda x: False), def __init__(self, vm, property_name, empty_function=(lambda x: False),
check_default=False): check_default=False):
"""
Class used to represent Qube Manager table widget.
:param vm: vm object
:param property_name: name of the property the widget represents
:param empty_function: a function that, when applied to values of
vm.property_name, returns True when the property value should be
represented as an empty string and False otherwise; by default this
function always returns false (vm.property_name is represented by an
empty string only when it actually is one)
:param check_default: if True, the widget will prepend its text with
"default" if the if the property is set to DEFAULT
"""
super(VMPropertyItem, self).__init__() super(VMPropertyItem, self).__init__()
self.setFlags(QtCore.Qt.ItemIsSelectable | QtCore.Qt.ItemIsEnabled) self.setFlags(QtCore.Qt.ItemIsSelectable | QtCore.Qt.ItemIsEnabled)
self.setTextAlignment(QtCore.Qt.AlignVCenter) self.setTextAlignment(QtCore.Qt.AlignVCenter)
@ -281,16 +293,18 @@ class VMPropertyItem(QtGui.QTableWidgetItem):
def update(self): def update(self):
val = getattr(self.vm, self.property_name, None) val = getattr(self.vm, self.property_name, None)
if self.empty_function(val): if self.empty_function(val):
self.setText("") text = ""
elif val is None: elif val is None:
self.setText("n/a") text = "n/a"
elif self.check_default and \
self.vm.property_is_default(self.property_name):
self.setText('default (' + str(val) + ')')
elif val is True: elif val is True:
self.setText("Yes") text = "Yes"
else: else:
self.setText(str(val)) text = str(val)
if self.check_default and hasattr(self.vm, self.property_name) and \
self.vm.property_is_default(self.property_name):
text = 'default (' + text + ')'
self.setText(text)
def __lt__(self, other): def __lt__(self, other):
if self.qid == 0: if self.qid == 0:

View File

@ -136,7 +136,7 @@
<number>10</number> <number>10</number>
</property> </property>
<property name="columnCount"> <property name="columnCount">
<number>12</number> <number>13</number>
</property> </property>
<attribute name="horizontalHeaderCascadingSectionResizes"> <attribute name="horizontalHeaderCascadingSectionResizes">
<bool>false</bool> <bool>false</bool>
@ -211,7 +211,8 @@
</column> </column>
<column> <column>
<property name="text"> <property name="text">
<string>Disk usage</string> <string>Disk
usage</string>
</property> </property>
</column> </column>
<column> <column>
@ -226,7 +227,8 @@
</column> </column>
<column> <column>
<property name="text"> <property name="text">
<string>Include in backups</string> <string>Include
in backups</string>
</property> </property>
</column> </column>
<column> <column>
@ -236,7 +238,14 @@
</column> </column>
<column> <column>
<property name="text"> <property name="text">
<string>Template for DispVMs</string> <string>Default
DisposableVM</string>
</property>
</column>
<column>
<property name="text">
<string>Is template for
DisposableVMs</string>
</property> </property>
</column> </column>
</widget> </widget>
@ -281,8 +290,9 @@
<addaction name="action_ip"/> <addaction name="action_ip"/>
<addaction name="action_backups"/> <addaction name="action_backups"/>
<addaction name="action_last_backup"/> <addaction name="action_last_backup"/>
<addaction name="action_dispvm_template"/>
<addaction name="action_is_dvm_template"/>
<addaction name="separator"/> <addaction name="separator"/>
<addaction name="action_dvm_template"/>
<addaction name="action_toolbar"/> <addaction name="action_toolbar"/>
<addaction name="action_menubar"/> <addaction name="action_menubar"/>
<addaction name="separator"/> <addaction name="separator"/>
@ -836,7 +846,7 @@
<string>Launch a tool that allows multiple templates to be changed at once</string> <string>Launch a tool that allows multiple templates to be changed at once</string>
</property> </property>
</action> </action>
<action name="action_dvm_template"> <action name="action_dispvm_template">
<property name="checkable"> <property name="checkable">
<bool>true</bool> <bool>true</bool>
</property> </property>
@ -844,10 +854,24 @@
<bool>true</bool> <bool>true</bool>
</property> </property>
<property name="text"> <property name="text">
<string>Template for DispVMs</string> <string>Default DisposableVMs</string>
</property> </property>
<property name="toolTip"> <property name="toolTip">
<string>Template for DispVMs</string> <string>Default DisposableVMs</string>
</property>
</action>
<action name="action_is_dvm_template">
<property name="checkable">
<bool>true</bool>
</property>
<property name="checked">
<bool>true</bool>
</property>
<property name="text">
<string>Is Template for DisposableVMs</string>
</property>
<property name="toolTip">
<string>Is Template for DisposableVMs</string>
</property> </property>
</action> </action>
</widget> </widget>