Example #1
0
    def createExpandFile(self):
        '''
        determine if this is an expand node, and if so,
        generate a temp file (descriptor) to hold the results,
        otherwise return None
        '''

        #
        # Tractor supports the extension that "Cmd -expand x"
        # can specify a filename explictly that the launched
        # command is known to write to, or it can be a number
        # (0 or 1) as in classic alfred scripts.
        #
        f = None
        if type(self.expands) in (str, unicode):
            # filename (string) given as -expand arg
            s = self.expands.strip()
            if len(s):
                try:     f = open(s, "wb")
                except:  pass
                if f:
                    trSetNoInherit( f )
                    self.expandfile = s
 
        elif self.expands > 0:
            # "classic" usage: -expand 1
            s = "trxJ%sT%sC%s.%s." % (self.jid, self.tid, self.cid, self.rev)
            try:    
                fd = tempfile.mkstemp(prefix=s, suffix=".xalf")
                f = os.fdopen(fd[0], 'w')
                trSetNoInherit( f )
                self.expandfile = fd[1]
            except:
                pass

        return f
Example #2
0
    def __init__(self, cmd):
        #
        # Some subprocess module parameters are not supported on all
        # platforms, so we we create our own member variables and apply
        # the settings selectively in _execute_child.  For example,
        # on unix we'd -like- to add the parameter 'close_fds=True'
        # to Popen. But the mere presence of the parameter raises an
        # error on windows.  So rather than having multiple os-dependent
        # constructor lines here, we just set the parameter explicitly
        # in _execute_child below.  Similarly, since the subprocess
        # module doesn't have an os-independent abstraction for login
        # impersonation, we must apply those settings in _execute_child
        # as well.
        #
        self.login = cmd.login
        self.pidIsProcessGroupLeader = False
        self._child_created = False  # prevent __del__ errors if we fail
        self.launchTime = time.time() # stand-in, updated closer to launch

        fxpnd = cmd.createExpandFile()
        
        nrm = hasattr(cmd, 'sockDict')

        if nrm and 'stdio' in cmd.sockDict:
            sIn  = cmd.sockDict['stdio']

            if fxpnd:
                sOut = fxpnd
            elif 'err' in cmd.sockDict:
                sOut = cmd.sockDict['err']
            else:
                sOut = cmd.sockDict['stdio']

            sErr = subprocess.STDOUT
            self.closeFDs = False
            try:
                trSetInherit( cmd.sockDict['dspy'] )
                trSetInherit( cmd.sockDict['file'] )
            except:
                pass
        else:
            sIn  = subprocess.PIPE
            sErr = subprocess.PIPE
            if fxpnd:
                sOut = fxpnd
            else:
                sOut = subprocess.PIPE
            self.closeFDs = True

        cmd.launchnote = ""
        cmd.guise = ""
        cmd.uid = 0

        self.cmd = cmd

        if subprocess.mswindows:
            fullapp = cmd.argv[0]
        else:
            fullapp = None

        pid = subprocess.Popen.__init__(self,
                        cmd.argv, bufsize=1, executable=fullapp,
                        stdin=sIn, stdout=sOut, stderr=sErr,
                        env=cmd.env, cwd=None)

        # ensure stray descriptors, especially netrender sockets,
        # can't be inherited by future execs
        if fxpnd:
            try:    trSetNoInherit( fxpnd )
            except: pass
        if nrm:
            for s in cmd.sockDict:
                try:    trSetNoInherit( cmd.sockDict[s] )
                except: pass

        return pid
Example #3
0
    def __init__(self, cmd):
        #
        # Some subprocess module parameters are not supported on all
        # platforms, so we we create our own member variables and apply
        # the settings selectively in _execute_child.  For example,
        # on unix we'd -like- to add the parameter 'close_fds=True'
        # to Popen. But the mere presence of the parameter raises an
        # error on windows.  So rather than having multiple os-dependent
        # constructor lines here, we just set the parameter explicitly
        # in _execute_child below.  Similarly, since the subprocess
        # module doesn't have an os-independent abstraction for login
        # impersonation, we must apply those settings in _execute_child
        # as well.
        #
        self.login = cmd.login
        self.pidIsProcessGroupLeader = False
        self._child_created = False  # prevent __del__ errors if we fail
        self.launchTime = time.time() # stand-in, updated closer to launch

        fxpnd = cmd.createExpandFile()
        
        nrm = hasattr(cmd, 'sockDict')

        if nrm and 'stdio' in cmd.sockDict:
            sIn  = cmd.sockDict['stdio']

            if fxpnd:
                sOut = fxpnd
            elif 'err' in cmd.sockDict:
                sOut = cmd.sockDict['err']
            else:
                sOut = cmd.sockDict['stdio']

            sErr = subprocess.STDOUT
            self.closeFDs = False
            try:
                trSetInherit( cmd.sockDict['dspy'] )
                trSetInherit( cmd.sockDict['file'] )
            except:
                pass
        else:
            sIn  = subprocess.PIPE
            sErr = subprocess.PIPE
            if fxpnd:
                sOut = fxpnd
            else:
                sOut = subprocess.PIPE
            self.closeFDs = True

        cmd.launchnote = ""
        cmd.guise = ""
        cmd.uid = 0

        self.cmd = cmd

        if subprocess.mswindows:
            fullapp = cmd.argv[0]
        else:
            fullapp = None

        pid = subprocess.Popen.__init__(self,
                        cmd.argv, bufsize=1, executable=fullapp,
                        stdin=sIn, stdout=sOut, stderr=sErr,
                        env=cmd.env, cwd=None)

        # ensure stray descriptors, especially netrender sockets,
        # can't be inherited by future execs
        if fxpnd:
            try:    trSetNoInherit( fxpnd )
            except: pass
        if nrm:
            for s in cmd.sockDict:
                try:    trSetNoInherit( cmd.sockDict[s] )
                except: pass

        return pid
Example #4
0
    def SaveOutput (self, txt, now=None, xbanner=""):
        if self.jid <= 0 and not self.altMode:
            self.logger.info("missing jid for logging")
            return
        try:
            isInternal = False
            if None == now:
                # this is a "system" message, generated by tractor,
                # not emitted by the cmd itself
                now = time.time()
                isInternal = True

            tm = time.strftime('%Y/%m/%d %H:%M:%S', time.localtime(now))

            if isInternal:
                txt = "\n"+xbanner+"[" + tm + " " + txt + "]"+xbanner+"\n"

            if self.cmdtee and xbanner=="":
                self.logger.info("cmd output:\n\n" + txt)

            if self.altMode:
                return

            if self.logdir:
                # note that all cmds within the same task are
                # logged to the same (task) file
                #
                # fnm = "%s/J%s/T%s.log" % (self.logdir, self.jid, self.tid)
                #

                prior = False
                if not self.logfile:
                    (type,_,loginfo) = self.cmdOutputLogging.partition("=")
                    fnm = loginfo.replace("%u", self.login).replace("%j", str(self.jid)).replace("%t", str(self.tid))
                    prior = os.path.exists(fnm)
                    self.logfile = open(fnm, "ab")
                    trSetNoInherit( self.logfile )

                if not self.hasEverLogged():
                    if prior:
                        self.logfile.write("\n\n") # sep txt of nxt cmds

                    self.logfile.write("====[%s %s on %s ]====\n\n" %
                                      (tm, self.logref, self.bladehost))

                    # mark this command as having generated output
                    self.indicateLogging(now)

                self.logfile.write(txt)

                # don't self.logfile.close() for now,
                # leave open while cmd is running
                # ... but if you do close it, remember:  self.logfile=None

                self.logfile.flush()  # might consider this only once/sec
                
            elif self.tasklogger:
                # log modules are being served by the remote logger

                d={"user": self.login, "jid": self.jid, "tid": self.tid,
                    "cid": self.cid, "rev": self.rev}

                if not self.hasEverLogged():
                    self.tasklogger.info("====[%s %s on %s ]====\n\n" %
                                      (tm, self.logref, self.bladehost), extra=d)
    
                    # mark this command as having generated output
                    self.indicateLogging(now)
 
                self.tasklogger.info(txt, extra=d)

            else:
                self.logger.error("no cmd output logging scheme defined!")

        except Exception:
            self.logger.error("cmd output logging failed: %s" % \
                            (self.logger.Xcpt()))