class ShellCommandAction( Action ): """ShellCommandAction encapsulates the execution of one command in the Step class. It is mostly used internally, but can be of general use as well.""" def __init__( self, command = None, timeout = None, combineOutput = True, searchPaths = None ): Action.__init__( self ) self.setCommand( command, timeout, searchPaths ) self.__combineOutput = combineOutput self.__runner = None def getLogDescription( self ): """Provide a textual description for the Action that can be added to the execution log file.""" return '{0}'.format( ' '.join( self.getCommand() ) ) def setCommand( self, command, timeOutPeriod = None, searchPaths = None ): """Set the shell command""" check_for_list_of_paths( command, "The shell command must be a list of strings or paths." ) if timeOutPeriod != None: check_for_nonnegative_int( timeOutPeriod, 'invalid timeout period, valid periods are [0..inf] or None for no timeout' ) if searchPaths is None: searchPaths = [] check_for_list_of_paths( searchPaths, "The search paths need to be a list of strings." ) self.__command = command self.__timeOutPeriod = timeOutPeriod self.__searchPaths = searchPaths def getCommand( self ): """Returns the command""" return map( lambda x: str( x ) , self.__command ) def _getRunner( self ): if self.__runner == None: raise MomError( "The command runner was not initialized before being queried" ) return self.__runner def run( self ): """Executes the shell command. Needs a command to be set.""" self.__runner = RunCommand( self.__command, self.__timeOutPeriod, self.__combineOutput, self.__searchPaths ) if self.getWorkingDirectory() != None: self.__runner.setWorkingDir( self.getWorkingDirectory() ) self._getRunner().run() self._setStdOut( self._getRunner().getStdOut() ) self._setStdErr( self._getRunner().getStdErr() ) return self._getRunner().getReturnCode() def hasTimedOut( self ): """Returns True if the shell command process timed out, e.g., was not completed within the timeout period. Can only be called after execution.""" if not self.__started: raise MomError( 'timedOut() queried before the command was executed' ) return self._getRunner().getTimedOut()
def update( self, folder ): cmd = [ 'git', 'pull' ] if self.getUseRebase(): cmd.append( '--rebase' ) runner = RunCommand( cmd ) runner.setWorkingDir( folder ) runner.run() if runner.getReturnCode() == 0: mApp().debugN( self, 2, 'Updated the git repository at "{0}"'.format( folder ) ) else: # we are not raising an exception, because we do not want the master to die because of, for example, a temporary # network outage message = runner.getStdErrAsString() mApp().message( self, 'Updating the git repository at "{0}" failed: "{1}"'.format( folder, message ) )
def fetchRepositoryFolder( self, remotePath ): # FIXME Mike abstract cache location path = tempfile.mkdtemp( prefix = 'mom_buildscript-', suffix = make_foldername_from_string( self.getUrl() ) ) if not self.getRevision(): self.setRevision( 'HEAD' ) location = self.getUrl() if remotePath: location += '/' + remotePath cmd = [ self.getCommand(), 'co', '-r', self.getRevision(), location ] runner = RunCommand( cmd, searchPaths = self.getCommandSearchPaths() ) runner.setWorkingDir( path ) runner.run() if runner.getReturnCode() == 0: localPath = os.path.join( path, remotePath ) if os.path.exists( localPath ): return localPath, [ path ] raise ConfigurationError( 'The remote path {0} was not found in the repository at revision {1}'.format( remotePath, self.getRevision() ) )