Browse Source

Run command in VM (#544)

Agnieszka Kostrzewa 12 years ago
parent
commit
c809896b52
4 changed files with 59 additions and 0 deletions
  1. BIN
      icons/run-command.png
  2. 13 0
      mainwindow.ui
  3. 45 0
      qubesmanager/main.py
  4. 1 0
      resources.qrc

BIN
icons/run-command.png


+ 13 - 0
mainwindow.ui

@@ -295,6 +295,7 @@
     <addaction name="action_editfwrules"/>
     <addaction name="action_appmenus"/>
     <addaction name="action_updatevm"/>
+    <addaction name="action_run_command_in_vm"/>
     <addaction name="action_set_keyboard_layout"/>
     <addaction name="separator"/>
     <addaction name="logs_menu"/>
@@ -725,6 +726,18 @@
     <string>Size on Disk</string>
    </property>
   </action>
+  <action name="action_run_command_in_vm">
+   <property name="icon">
+    <iconset resource="resources.qrc">
+     <normaloff>:/run-command.png</normaloff>:/run-command.png</iconset>
+   </property>
+   <property name="text">
+    <string>Run command in VM</string>
+   </property>
+   <property name="toolTip">
+    <string>Run command in the specified VM</string>
+   </property>
+  </action>
  </widget>
  <resources>
   <include location="resources.qrc"/>

+ 45 - 0
qubesmanager/main.py

@@ -23,6 +23,7 @@
 import sys
 import os
 import fcntl
+import errno
 import dbus
 from PyQt4.QtCore import *
 from PyQt4.QtGui import *
@@ -735,6 +736,7 @@ class VmManagerWindow(Ui_VmManagerWindow, QMainWindow):
         self.context_menu.addAction(self.action_appmenus)
         self.context_menu.addAction(self.action_editfwrules)
         self.context_menu.addAction(self.action_updatevm)
+        self.context_menu.addAction(self.action_run_command_in_vm)
         self.context_menu.addAction(self.action_set_keyboard_layout)
         self.context_menu.addMenu(self.logs_menu)
         self.context_menu.addMenu(self.blk_menu)
@@ -1040,6 +1042,7 @@ class VmManagerWindow(Ui_VmManagerWindow, QMainWindow):
             self.action_appmenus.setEnabled(not vm.is_netvm())
             self.action_editfwrules.setEnabled(vm.is_networked() and not (vm.is_netvm() and not vm.is_proxyvm()))
             self.action_updatevm.setEnabled(vm.is_updateable() or vm.qid == 0)
+            self.action_run_command_in_vm.setEnabled(vm.qid != 0)
             self.action_set_keyboard_layout.setEnabled(vm.qid != 0 and vm.last_running)
         else:
             self.action_settings.setEnabled(False)
@@ -1051,6 +1054,7 @@ class VmManagerWindow(Ui_VmManagerWindow, QMainWindow):
             self.action_appmenus.setEnabled(False)
             self.action_editfwrules.setEnabled(False)
             self.action_updatevm.setEnabled(False)
+            self.action_run_command_in_vm.setEnabled(False)
             self.action_set_keyboard_layout.setEnabled(False)
 
 
@@ -1401,6 +1405,47 @@ class VmManagerWindow(Ui_VmManagerWindow, QMainWindow):
         thread_monitor.set_finished()
 
  
+    @pyqtSlot(name='on_action_run_command_in_vm_triggered')
+    def action_run_command_in_vm_triggered(self):
+        vm = self.get_selected_vm()
+
+        thread_monitor = ThreadMonitor()
+        thread = threading.Thread (target=self.do_run_command_in_vm, args=(vm, thread_monitor))
+        thread.daemon = True
+        thread.start()
+
+        while not thread_monitor.is_finished():
+            app.processEvents()
+            time.sleep (0.2)
+
+        if not thread_monitor.success:
+            QMessageBox.warning (None, "Error while running command", "Exception while running command:<br>{0}".format(thread_monitor.error_msg))
+
+
+    def do_run_command_in_vm(self, vm, thread_monitor):
+        cmd = ['kdialog', '--title', 'Qubes command entry', '--inputbox', 'Run command in <b>'+vm.name+'</b>:']
+        kdialog = subprocess.Popen(cmd, stdout = subprocess.PIPE)
+        command_to_run = kdialog.stdout.read()
+        command_to_run = "'"+command_to_run.strip()+"'"
+        if command_to_run != "":
+            command_to_run = "qvm-run -a "+ vm.name + " " + command_to_run
+            try:
+                subprocess.check_call(command_to_run, shell=True)
+            except OSError as ex:
+                if ex.errno == errno.EINTR:
+                    pass
+                else:
+                    thread_monitor.set_error_msg(str(ex))
+                    thread_monitor.set_finished()
+            except Exception as ex:
+                thread_monitor.set_error_msg(str(ex))
+                thread_monitor.set_finished()
+        thread_monitor.set_finished()
+               
+
+        
+
+ 
     @pyqtSlot(name='on_action_set_keyboard_layout_triggered')
     def action_set_keyboard_layout_triggered(self):
         vm = self.get_selected_vm()

+ 1 - 0
resources.qrc

@@ -12,6 +12,7 @@
     <file alias="show-all-running.png">icons/show-all-running.png</file>
     <file alias="mount.png">icons/mount.png</file>
     <file alias="log.png">icons/log.png</file>
+    <file alias="run-command.png">icons/run-command.png</file>
     <file alias="kbd-layout.png">icons/kbd-layout.png</file>
     <file alias="copy.png">icons/copy.png</file>
     <file alias="pencil.png">icons/pencil.png</file>