Code Search for Developers
 
 
  

externaltask.py from The Nebula Device at Krugle


Show externaltask.py syntax highlighted

#--------------------------------------------------------------------------
# 3rd Generation Nebula 2 Build System
# External Task Launcher
#
# (c) 2005 Vadim Macagon
#
# Contents are licensed under the Nebula license.
#--------------------------------------------------------------------------

import os, subprocess, signal, threading, platform

#--------------------------------------------------------------------------
# Terminate the given process and it's immediate children.
def TerminateChildProcess(proc):
    if proc != None:
        if platform.system() == 'Windows':
            try:
                from buildsys3 import pykillwinproc as prockiller
            except ImportError, err:
                #print str(err) + '\n'
                pass
            else:
                #print 'terminating process with pid = ' + str(proc.pid)
                prockiller.kill_process_tree(proc.pid)
        else:
            os.kill(proc.pid, signal.SIGTERM)

#--------------------------------------------------------------------------
# Use an instance of this class to launch an external program and wait for
# it's completion. When the build system is run in GUI mode a dialog will
# pop up to display standard output/errors from the external program.
class ExternalTask:

    #--------------------------------------------------------------------------
    def __init__(self, taskName, cmdLine, workingDir = None, mainFrame = None):
        self.taskName = taskName
        self.mainFrame = mainFrame
        self.cmdLine = cmdLine
        self.workingDir = workingDir
        self.dialogProxy = None
        self.evtDialogCreated = threading.Event()
        self.evtDialogClosed = threading.Event()
        self.proc = None
        self.userCancelled = False
        self.firstRun = True

    #--------------------------------------------------------------------------
    # Run the task (blocks until task terminates).
    # Return True if the task completed successfuly, or False if it didn't run
    # to completion (usually due to the user aborting it).
    def Run(self):
        assert self.firstRun # for now only allow the task to be run once
        if self.firstRun:
            self.firstRun = False
            if self.mainFrame != None:
                return self.runWithGUI()
            else:
                return self.runWithoutGUI()
        return False

    #--------------------------------------------------------------------------
    # Private Stuff
    #--------------------------------------------------------------------------

    #--------------------------------------------------------------------------
    # Will be called by self.mainFrame when the dialog proxy associated with
    # this task is created.
    def OnCreateDialogProxy(self, dlgProxy):
        assert dlgProxy != None
        self.dialogProxy = dlgProxy
        # wake up any threads waiting for the dialog proxy to be set
        self.evtDialogCreated.set()

    #--------------------------------------------------------------------------
    def createDialogProxy(self):
        self.mainFrame.CreateExternalTaskDialogProxy(self.taskName + ' Output',
                                                     self.OnCreateDialogProxy,
                                                     self.OnOkBtn,
                                                     self.OnCancelBtn)
        # block until the dialog is created
        self.evtDialogCreated.wait()

    #--------------------------------------------------------------------------
    def destroyDialogProxy(self):
        # block until the user closes the dialog
        self.evtDialogClosed.wait()
        self.mainFrame.DestroyExternalTaskDialogProxy(self.dialogProxy)
        self.dialogProxy = None

    #--------------------------------------------------------------------------
    # This will be called after the user presses the OK button to close the
    # dialog associated with this task.
    def OnOkBtn(self):
        # wake up any threads waiting for the dialog to close
        self.evtDialogClosed.set()

    #--------------------------------------------------------------------------
    # This will be called after the user presses the Cancel button to close the
    # dialog associated with this task.
    def OnCancelBtn(self):
        if not self.userCancelled:
            self.userCancelled = True
            TerminateChildProcess(self.proc)
        # wake up any threads waiting for the dialog to close
        self.evtDialogClosed.set()

    #--------------------------------------------------------------------------
    def runWithGUI(self):
        oldPath = os.getcwd()
        if self.workingDir != None:
            os.chdir(self.workingDir)

        self.createDialogProxy()
        self.dialogProxy.Display()

        try:
            self.proc = subprocess.Popen(self.cmdLine,
                                         shell = True,
                                         stdin = None,
                                         stdout = subprocess.PIPE,
                                         stderr = subprocess.STDOUT)
        except:
            os.chdir(oldPath)
            raise
        else:
            outLine = self.proc.stdout.readline()
            while outLine != '':
                self.dialogProxy.AppendText(outLine)
                outLine = self.proc.stdout.readline()

            if not self.userCancelled:
                # enable OK button and disable Cancel button
                self.dialogProxy.EnableButtons(True, False)

            self.proc.stdout.close()

        self.destroyDialogProxy()
        os.chdir(oldPath)
        return not self.userCancelled

    #--------------------------------------------------------------------------
    def runWithoutGUI(self):
        oldPath = os.getcwd()
        if self.workingDir != None:
            os.chdir(self.workingDir)
        os.system(self.cmdLine)
        os.chdir(oldPath)
        return True

#--------------------------------------------------------------------------
# EOF
#--------------------------------------------------------------------------





See more files for this project here

The Nebula Device

Realtime 3D game/visualization engine, written in C++, scriptable through Tcl/Tk, Python and Lua. Supports D3D and OpenGL for rendering, runs under Linux and Windows.

Project homepage: http://sourceforge.net/projects/nebuladevice
Programming language(s): C,C++,Python
License: other

  Plex/
    Actions.py
    DFA.py
    Errors.py
    Lexicons.py
    Machines.py
    README
    Regexps.py
    Scanners.py
    TODO
    Timing.py
    Traditional.py
    Transitions.py
    __init__.py
    test_tm.py
  docs/
    layout/
      inset-h.jpg
      nav-end.gif
      nav-start.jpg
      nebuladevice2.gif
      tnd.css
      top-back.gif
      top-image.jpg
    screens/
      classbuilderconfirm.png
      classbuildertab.png
      workspacestab.png
    Manual.html
  generators/
    __init__.py
    doxygen.py
    factory.py
    makefile.py
    vstudio7.py
    vstudio71.py
    vstudio8.py
  gui/
    xrc/
      format_dlg.xrc
      renderpath.xrc
    __init__.py
    buildlog.py
    classbuilderpanel.py
    cmddatapanels.py
    cmdeditorpanel.py
    cmdparser.py
    doxygengeneratorsettings.py
    externaltaskdialog.py
    main.py
    workspacespanel.py
    xrcguiutils.py
  __init__.py
  bldscanner.py
  buildconfig.py
  buildsys.py
  bundle.py
  config.mak
  externaltask.py
  guid.py
  module.py
  pykillwinproc.pyd
  target.py
  workspace.py