def genCommand(self, inputFiles, executable, flags=None, fileArgs=None, preExec=None): """ This method is used to retrieve the command (in tuple format) needed to launch the Code. This method checks a boolean environment variable called 'RAVENinterfaceCheck': if true, the subcodeCommand is going to be overwritten with an empty string. In this way we can check the functionality of the interface without having an executable. See Driver.py to understand how this Env variable is set @ In, inputFiles, list, List of input files (length of the list depends on the number of inputs have been added in the Step is running this code) @ In, executable, string, executable name with absolute path (e.g. /home/path_to_executable/code.exe) @ In, flags, dict, optional, dictionary containing the command-line flags the user can specify in the input (e.g. under the node < Code >< clargstype =0 input0arg =0 i0extension =0 .inp0/ >< /Code >) @ In, fileArgs, dict, optional, a dictionary containing the auxiliary input file variables the user can specify in the input (e.g. under the node < Code >< fileargstype =0 input0arg =0 aux0extension =0 .aux0/ >< /Code >) @ In, preExec, string, optional, a string the command that needs to be pre-executed before the actual command here defined @ Out, returnCommand, tuple, tuple containing the generated command. returnCommand[0] is the command to run the code (string), returnCommand[1] is the name of the output root """ subcodeCommand, outputfileroot = self.generateCommand(inputFiles, executable, clargs=flags, fargs=fileArgs, preExec=preExec) if utils.stringIsTrue(os.environ.get('RAVENinterfaceCheck', 'False')): return [('parallel', 'echo')], outputfileroot returnCommand = subcodeCommand, outputfileroot return returnCommand
def XMLread(self, xmlNode): """ XMLread is called with the mode node, and is used here to get extra parameters needed for the simulation mode MPI. @ In, xmlNode, xml.etree.ElementTree.Element, the xml node that belongs to this class instance @ Out, None """ for child in xmlNode: child_tag = child.tag.lower() if child.tag == "nodefileenv": self.__nodefile = os.environ[child.text.strip()] elif child.tag == "nodefile": self.__nodefile = child.text.strip() elif child_tag == "runqsub": self.__runQsub = True elif child_tag == "nosplitnode": self.__noSplitNode = True self.__maxOnNode = child.attrib.get("maxOnNode",None) if self.__maxOnNode is not None: self.__maxOnNode = int(self.__maxOnNode) if "noOverlap" in child.attrib: self.__noOverlap = True elif child_tag == "limitnode": self.__limitNode = True self.__maxOnNode = child.attrib.get("maxOnNode",None) if self.__maxOnNode is not None: self.__maxOnNode = int(self.__maxOnNode) else: self.raiseAnError(IOError, "maxOnNode must be specified with LimitNode") if utils.stringIsTrue(child.attrib.get("noOverlap", None)): self.__noOverlap = True else: self.raiseADebug("We should do something with child "+str(child))
def setColor(self, inColor): """ Allows output to screen to be colorized. @ In, inColor, string, boolean value @ Out, None """ if utils.stringIsTrue(inColor): self.inColor = True
def initialize(self, initDict): """ Initializes basic instance attributes @ In, initDict, dict, dictionary of global options @ Out, None """ self.verbosity = initDict.get('verbosity', 'all').lower() self.callerLength = initDict.get('callerLength', 40) self.tagLength = initDict.get('tagLength', 30) self.suppressErrs = utils.stringIsTrue( initDict.get('suppressErrs', 'False'))
def setTimePrint(self, msg): """ Allows the code to toggle timestamp printing. @ In, msg, string, the string that means true or false @ Out, None """ if utils.stringIsTrue(msg): self.callerLength = 40 self.tagLength = 30 self.printTime = True elif utils.stringIsFalse(msg): self.callerLength = 25 self.tagLength = 15 self.printTime = False
def convert(cls, value): """ Converts value from string to a bool. @ In, value, string, the value to convert @ Out, convert, bool, the converted value """ if utils.stringIsTrue(value): return True elif utils.stringIsFalse(value): return False else: raise IOError( 'Unrecognized boolean value: "{}"! Expected one of {}'.format( value, utils.boolThingsFull))
def readMoreXML(self, xmlNode, ravenWorkingDir): """ Function to read the portion of the xml input that belongs to this class and initialize some members based on inputs. @ In, xmlNode, xml.etree.ElementTree.Element, Xml element node @ In, ravenWorkingDir, str, location of RAVEN's working directory @ Out, None """ self._ravenWorkingDir = ravenWorkingDir self._readMoreXML(xmlNode) # read global options # should we print CSV even if the data can be directly returned to RAVEN? csvLog = xmlNode.find("csv") self._writeCSV = utils.stringIsTrue( csvLog.text if csvLog is not None else "False")
def _handleInput(self, paramInput): """ Function to handle the parsed paramInput for this class. @ In, paramInput, ParameterInput, the already parsed input. @ Out, None """ PostProcessor._handleInput(self, paramInput) for outer in paramInput.subparts: if outer.getName() == 'compare': compareGroup = ComparisonStatistics.CompareGroup() for child in outer.subparts: if child.getName() == 'data': dataName = child.value splitName = dataName.split("|") name, kind = splitName[:2] rest = splitName[2:] compareGroup.dataPulls.append([name, kind, rest]) elif child.getName() == 'reference': # This has name=distribution compareGroup.referenceData = dict( child.parameterValues) if "name" not in compareGroup.referenceData: self.raiseAnError( IOError, 'Did not find name in reference block') self.compareGroups.append(compareGroup) if outer.getName() == 'kind': self.methodInfo['kind'] = outer.value if 'numBins' in outer.parameterValues: self.methodInfo['numBins'] = outer.parameterValues[ 'numBins'] if 'binMethod' in outer.parameterValues: self.methodInfo['binMethod'] = outer.parameterValues[ 'binMethod'].lower() if outer.getName() == 'fz': self.fZStats = utils.stringIsTrue(outer.value.lower()) if outer.getName() == 'interpolation': interpolation = outer.value.lower() if interpolation == 'linear': self.interpolation = 'linear' elif interpolation == 'quadratic': self.interpolation = 'quadratic' else: self.raiseADebug('unexpected interpolation method ' + interpolation) self.interpolation = interpolation
def _readMoreXML(self, xmlNode): """ Function to read the portion of the xml input that belongs to this specialized class and initialize some stuff based on the inputs received @ In, xmlNode, xml.etree.ElementTree.Element, Xml element node @ Out, None The text is supposed to contain the info where and which variable to change. In case of a code the syntax is specified by the code interface itself """ if 'overwrite' in xmlNode.attrib.keys(): if utils.stringIsTrue(xmlNode.attrib['overwrite']): self.overwrite = True else: self.overwrite = False if 'dir' in xmlNode.attrib: self.subDirectory = xmlNode.attrib['dir'] if '~' in self.subDirectory: self.subDirectory = os.path.expanduser(self.subDirectory) self.localReadXML(xmlNode)
def localInputAndChecks(self, xmlNode, paramInput): """ Class specific xml inputs will be read here and checked for validity. @ In, xmlNode, xml.etree.ElementTree.Element, The xml element node that will be checked against the available options specific to this Sampler. @ In, paramInput, InputData.ParameterInput, the parsed parameters @ Out, None """ #TODO remove using xmlNode #check if the hybrid DET has been activated, in case remove the nodes and treat them separaterly hybridNodes = xmlNode.findall("HybridSampler") if len(hybridNodes) != 0: # check the type of hybrid that needs to be performed limitSurfaceHybrid = False for elm in hybridNodes: samplType = elm.attrib['type'] if 'type' in elm.attrib.keys( ) else None if samplType == 'LimitSurface': if len(hybridNodes) != 1: self.raiseAnError( IOError, 'if one of the HybridSampler is of type "LimitSurface", it can not be combined with other strategies. Only one HybridSampler node can be inputted!' ) limitSurfaceHybrid = True if limitSurfaceHybrid == True: #remove the elements from original xmlNode and check if the types are compatible for elm in hybridNodes: xmlNode.remove(elm) self.hybridDETstrategy = 1 else: self.hybridDETstrategy = 2 if self.hybridDETstrategy == 2: self.raiseAnError( IOError, 'The sheaf of LSs for the Adaptive Hybrid DET is not yet available. Use type "LimitSurface"!' ) DynamicEventTree.localInputAndChecks(self, xmlNode, paramInput) # now we put back the nodes into the xmlNode to initialize the LimitSurfaceSearch with those variables as well for elm in hybridNodes: for child in elm: if limitSurfaceHybrid == True: xmlNode.append(child) if child.tag in ['variable', 'Distribution']: self.epistemicVariables[child.attrib['name']] = None LimitSurfaceSearch._readMoreXMLbase(self, xmlNode) LimitSurfaceSearch.localInputAndChecks(self, xmlNode, paramInput) if 'mode' in xmlNode.attrib.keys(): if xmlNode.attrib['mode'].lower() == 'online': self.detAdaptMode = 2 elif xmlNode.attrib['mode'].lower() == 'post': self.detAdaptMode = 1 else: self.raiseAnError( IOError, 'unknown mode ' + xmlNode.attrib['mode'] + '. Available are "online" and "post"!') if 'noTransitionStrategy' in xmlNode.attrib.keys(): if xmlNode.attrib['noTransitionStrategy'].lower() == 'mc': self.noTransitionStrategy = 1 elif xmlNode.attrib['noTransitionStrategy'].lower() == 'grid': self.noTransitionStrategy = 2 else: self.raiseAnError( IOError, 'unknown noTransitionStrategy ' + xmlNode.attrib['noTransitionStrategy'] + '. Available are "mc" and "grid"!') if 'updateGrid' in xmlNode.attrib.keys(): if utils.stringIsTrue(xmlNode.attrib['updateGrid']): self.insertAdaptBPb = True # we add an artificial threshold because I need to find a way to prepend a rootbranch into a Tree object for val in self.branchProbabilities.values(): if min(val) != 1e-3: val.insert(0, 1e-3)
def __readRunInfo(self, xmlNode, runInfoSkip, xmlFilename): """ Method that reads the xml input file for the RunInfo block @ In, xmlNode, xml.etree.Element, the xml node that belongs to Simulation @ In, runInfoSkip, string, the runInfo step to skip @ In, xmlFilename, string, xml input file name @ Out, None """ if 'verbosity' in xmlNode.attrib.keys(): self.verbosity = xmlNode.attrib['verbosity'] self.raiseAMessage('Global verbosity level is "', self.verbosity, '"', verbosity='quiet') for element in xmlNode: if element.tag in runInfoSkip: self.raiseAWarning("Skipped element ", element.tag) elif element.tag == 'printInput': text = element.text.strip() if element.text is not None else '' #extension fixing if len(text) >= 4 and text[-4:].lower() == '.xml': text = text[:-4] # if the user asked to not print input instead of leaving off tag, respect it if utils.stringIsFalse(text): self.runInfoDict['printInput'] = False # if the user didn't provide a name, provide a default elif len(text) < 1: self.runInfoDict['printInput'] = 'duplicated_input.xml' # otherwise, use the user-provided name else: self.runInfoDict['printInput'] = text + '.xml' elif element.tag == 'WorkingDir': # first store the cwd, the "CallDir" self.runInfoDict['CallDir'] = os.getcwd() # then get the requested "WorkingDir" tempName = element.text if element.text is None: self.raiseAnError( IOError, 'RunInfo.WorkingDir is empty! Use "." to signify "work here" or specify a directory.' ) if '~' in tempName: tempName = os.path.expanduser(tempName) if os.path.isabs(tempName): self.runInfoDict['WorkingDir'] = tempName elif "runRelative" in element.attrib: self.runInfoDict['WorkingDir'] = os.path.abspath(tempName) else: if xmlFilename == None: self.raiseAnError( IOError, 'Relative working directory requested but xmlFilename is None.' ) # store location of the input xmlDirectory = os.path.dirname( os.path.abspath(xmlFilename)) self.runInfoDict['InputDir'] = xmlDirectory rawRelativeWorkingDir = element.text.strip() # working dir is file location + relative working dir self.runInfoDict['WorkingDir'] = os.path.join( xmlDirectory, rawRelativeWorkingDir) utils.makeDir(self.runInfoDict['WorkingDir']) elif element.tag == 'maxQueueSize': try: self.runInfoDict['maxQueueSize'] = int(element.text) except ValueError: self.raiseAnError( 'Value give for RunInfo.maxQueueSize could not be converted to integer: {}' .format(element.text)) elif element.tag == 'RemoteRunCommand': tempName = element.text if '~' in tempName: tempName = os.path.expanduser(tempName) if os.path.isabs(tempName): self.runInfoDict['RemoteRunCommand'] = tempName else: self.runInfoDict['RemoteRunCommand'] = os.path.abspath( os.path.join(self.runInfoDict['FrameworkDir'], tempName)) elif element.tag == 'NodeParameter': self.runInfoDict['NodeParameter'] = element.text.strip() elif element.tag == 'MPIExec': self.runInfoDict['MPIExec'] = element.text.strip() elif element.tag == 'JobName': self.runInfoDict['JobName'] = element.text.strip() elif element.tag == 'ParallelCommand': self.runInfoDict['ParallelCommand'] = element.text.strip() elif element.tag == 'queueingSoftware': self.runInfoDict['queueingSoftware'] = element.text.strip() elif element.tag == 'ThreadingCommand': self.runInfoDict['ThreadingCommand'] = element.text.strip() elif element.tag == 'NumThreads': self.runInfoDict['NumThreads'] = int(element.text) elif element.tag == 'totalNumCoresUsed': self.runInfoDict['totalNumCoresUsed'] = int(element.text) elif element.tag == 'NumMPI': self.runInfoDict['NumMPI'] = int(element.text) elif element.tag == 'internalParallel': self.runInfoDict['internalParallel'] = utils.interpretBoolean( element.text) elif element.tag == 'batchSize': self.runInfoDict['batchSize'] = int(element.text) elif element.tag.lower() == 'maxqueuesize': self.runInfoDict['maxQueueSize'] = int(element.text) elif element.tag == 'MaxLogFileSize': self.runInfoDict['MaxLogFileSize'] = int(element.text) elif element.tag == 'precommand': self.runInfoDict['precommand'] = element.text elif element.tag == 'postcommand': self.runInfoDict['postcommand'] = element.text elif element.tag == 'deleteOutExtension': self.runInfoDict['deleteOutExtension'] = element.text.strip( ).split(',') elif element.tag == 'delSucLogFiles': if utils.stringIsTrue(element.text): self.runInfoDict['delSucLogFiles'] = True else: self.runInfoDict['delSucLogFiles'] = False elif element.tag == 'logfileBuffer': self.runInfoDict[ 'logfileBuffer'] = utils.convertMultipleToBytes( element.text.lower()) elif element.tag == 'clusterParameters': self.runInfoDict['clusterParameters'].extend( splitCommand(element.text) ) #extend to allow adding parameters at different points. elif element.tag == 'mode': self.runInfoDict['mode'] = element.text.strip().lower() #parallel environment if self.runInfoDict['mode'] in self.__modeHandlerDict: self.__modeHandler = self.__modeHandlerDict[ self.runInfoDict['mode']](self.messageHandler) self.__modeHandler.XMLread(element) else: self.raiseAnError( IOError, "Unknown mode " + self.runInfoDict['mode']) elif element.tag == 'expectedTime': self.runInfoDict['expectedTime'] = element.text.strip() elif element.tag == 'Sequence': for stepName in element.text.split(','): self.stepSequenceList.append(stepName.strip()) elif element.tag == 'DefaultInputFile': self.runInfoDict['DefaultInputFile'] = element.text.strip() elif element.tag == 'CustomMode': modeName = element.text.strip() modeClass = element.attrib["class"] modeFile = element.attrib["file"] #XXX This depends on if the working directory has been set yet. # So switching the order of WorkingDir and CustomMode can # cause different results. modeFile = modeFile.replace("%BASE_WORKING_DIR%", self.runInfoDict['WorkingDir']) modeFile = modeFile.replace("%FRAMEWORK_DIR%", self.runInfoDict['FrameworkDir']) modeDir, modeFilename = os.path.split(modeFile) if modeFilename.endswith(".py"): modeModulename = modeFilename[:-3] else: modeModulename = modeFilename os.sys.path.append(modeDir) module = __import__(modeModulename) if modeName in self.__modeHandlerDict: self.raiseAWarning("duplicate mode definition " + modeName) self.__modeHandlerDict[modeName] = module.__dict__[modeClass] else: self.raiseAnError( IOError, 'RunInfo element "' + element.tag + '" unknown!')
def findSlaveFiles(self, tree, workingDir): """ find Slave Files @ In, tree, xml.etree.ElementTree.Element, main node of RAVEN @ In, workingDir, string, current working directory @ Out, slaveFiles, list, list of slave input files """ slaveFiles = [] # NOTE: this is only perturbable files # check in files filesNode = tree.find('.//Files') if filesNode is not None: for child in tree.find('.//Files'): # if the file is noted to be in a subdirectory, grab that subDirectory = child.attrib.get('subDirectory','') # this is the absolute path of the file on the system absPath = os.path.abspath(os.path.expanduser(os.path.join(workingDir, subDirectory, child.text.strip()))) # is this file meant to be perturbed? Default to true. perturbable = utils.stringIsTrue(child.attrib.get('perturbable', 't')) if perturbable: # since it will be perturbed, track it so we can copy it to the eventual inner workdir slaveFiles.append(absPath) # we're going to copy it to the working dir, so just leave the file name child.text = os.path.basename(absPath) else: # change the path to be absolute so the inner workflow still knows where it is ## make sure we don't have a subdirectory messing with stuff child.attrib.pop('subDirectory', None) child.text = absPath # check in external models externalModels = tree.findall('.//Models/ExternalModel') if len(externalModels) > 0: for extModel in externalModels: if 'ModuleToLoad' in extModel.attrib: moduleToLoad = extModel.attrib['ModuleToLoad'] if not moduleToLoad.endswith("py"): moduleToLoad += ".py" if self.workingDir not in moduleToLoad: absPath = os.path.abspath(os.path.expanduser(os.path.join(workingDir, moduleToLoad))) else: absPath = os.path.abspath(os.path.expanduser(moduleToLoad)) # because ExternalModels aren't perturbed, just update the path to be absolute extModel.attrib['ModuleToLoad'] = absPath else: if 'subType' not in extModel.attrib or len(extModel.attrib['subType']) == 0: raise IOError(self.printTag+' ERROR: ExternalModel "'+extModel.attrib['name']+'" does not have any attribute named "ModuleToLoad" or "subType" with an available plugin name!') # check in external functions externalFunctions = tree.findall('.//Functions/External') if len(externalFunctions) > 0: for extFunct in externalFunctions: if 'file' in extFunct.attrib: moduleToLoad = extFunct.attrib['file'] if not moduleToLoad.endswith("py"): moduleToLoad += ".py" if workingDir not in moduleToLoad: absPath = os.path.abspath(os.path.expanduser(os.path.join(workingDir, moduleToLoad))) else: absPath = os.path.abspath(os.path.expanduser(moduleToLoad)) # because ExternalFunctions aren't perturbed, just update the path to be absolute extFunct.attrib['file'] = absPath else: raise IOError(self.printTag+' ERROR: Functions/External ' +extFunct.attrib['name']+ ' does not have any attribute named "file"!!') # make the paths absolute return slaveFiles