diff --git a/schainpy2/IO/JRODataIO.py b/schainpy2/IO/JRODataIO.py index 85c9888..058581c 100644 --- a/schainpy2/IO/JRODataIO.py +++ b/schainpy2/IO/JRODataIO.py @@ -76,8 +76,90 @@ def isThisFileinRange(filename, startUTSeconds, endUTSeconds): return 1 +def getlastFileFromPath(path, ext): + """ + Depura el fileList dejando solo los que cumplan el formato de "PYYYYDDDSSS.ext" + al final de la depuracion devuelve el ultimo file de la lista que quedo. + + Input: + fileList : lista conteniendo todos los files (sin path) que componen una determinada carpeta + ext : extension de los files contenidos en una carpeta + + Return: + El ultimo file de una determinada carpeta, no se considera el path. + """ + validFilelist = [] + fileList = os.listdir(path) + + # 0 1234 567 89A BCDE + # H YYYY DDD SSS .ext + + for file in fileList: + try: + year = int(file[1:5]) + doy = int(file[5:8]) + + if (os.path.splitext(file)[-1].upper() != ext.upper()) : continue + except: + continue + + validFilelist.append(file) + if validFilelist: + validFilelist = sorted( validFilelist, key=str.lower ) + return validFilelist[-1] + return None + +def checkForRealPath(path, year, doy, set, ext): + """ + Por ser Linux Case Sensitive entonces checkForRealPath encuentra el nombre correcto de un path, + Prueba por varias combinaciones de nombres entre mayusculas y minusculas para determinar + el path exacto de un determinado file. + + Example : + nombre correcto del file es .../.../D2009307/P2009307367.ext + + Entonces la funcion prueba con las siguientes combinaciones + .../.../x2009307/y2009307367.ext + .../.../x2009307/Y2009307367.ext + .../.../X2009307/y2009307367.ext + .../.../X2009307/Y2009307367.ext + siendo para este caso, la ultima combinacion de letras, identica al file buscado + + Return: + Si encuentra la cobinacion adecuada devuelve el path completo y el nombre del file + caso contrario devuelve None como path y el la ultima combinacion de nombre en mayusculas + para el filename + """ + filepath = None + find_flag = False + filename = None + + if ext.lower() == ".r": #voltage + header1 = "dD" + header2 = "dD" + elif ext.lower() == ".pdata": #spectra + header1 = "dD" + header2 = "pP" + else: + return None, filename + + for dir in header1: #barrido por las dos combinaciones posibles de "D" + for fil in header2: #barrido por las dos combinaciones posibles de "D" + doypath = "%s%04d%03d" % ( dir, year, doy ) #formo el nombre del directorio xYYYYDDD (x=d o x=D) + filename = "%s%04d%03d%03d%s" % ( fil, year, doy, set, ext ) #formo el nombre del file xYYYYDDDSSS.ext + filepath = os.path.join( path, doypath, filename ) #formo el path completo + if os.path.exists( filepath ): #verifico que exista + find_flag = True + break + if find_flag: + break + + if not(find_flag): + return None, filename + + return filepath, filename class JRODataIO: @@ -150,6 +232,13 @@ class JRODataReader(JRODataIO): nReadBlocks = 0 + delay = 60 #number of seconds waiting a new file + + nTries = 3 #quantity tries + + nFiles = 3 #number of files for searching + + def __init__(self): pass @@ -227,7 +316,97 @@ class JRODataReader(JRODataIO): self.filenameList = filenameList return pathList, filenameList + + def __searchFilesOnLine(self, path, startDate=None, endDate=None, startTime=None, endTime=None, expLabel = "", ext = None): + + """ + Busca el ultimo archivo de la ultima carpeta (determinada o no por startDateTime) y + devuelve el archivo encontrado ademas de otros datos. + + Input: + path : carpeta donde estan contenidos los files que contiene data + + startDate : Fecha inicial. Rechaza todos los directorios donde + file end time < startDate (obejto datetime.date) + + endDate : Fecha final. Rechaza todos los directorios donde + file start time > endDate (obejto datetime.date) + + startTime : Tiempo inicial. Rechaza todos los archivos donde + file end time < startTime (obejto datetime.time) + + endTime : Tiempo final. Rechaza todos los archivos donde + file start time > endTime (obejto datetime.time) + + expLabel : Nombre del subexperimento (subfolder) + + ext : extension de los files + Return: + directory : eL directorio donde esta el file encontrado + filename : el ultimo file de una determinada carpeta + year : el anho + doy : el numero de dia del anho + set : el set del archivo + + + """ + dirList = [] + pathList = [] + directory = None + + #Filtra solo los directorios + for thisPath in os.listdir(path): + if os.path.isdir(os.path.join(path, thisPath)): + dirList.append(thisPath) + + if not(dirList): + return None, None, None, None, None + + dirList = sorted( dirList, key=str.lower ) + + if startDate: + startDateTime = datetime.datetime.combine(startDate, startTime) + thisDateTime = startDateTime + if endDate == None: endDateTime = startDateTime + else: endDateTime = datetime.datetime.combine(endDate, endTime) + + while(thisDateTime <= endDateTime): + year = thisDateTime.timetuple().tm_year + doy = thisDateTime.timetuple().tm_yday + + match = fnmatch.filter(dirList, '?' + '%4.4d%3.3d' % (year,doy)) + if len(match) == 0: + thisDateTime += datetime.timedelta(1) + continue + + pathList.append(os.path.join(path,match[0], expLabel)) + thisDateTime += datetime.timedelta(1) + + if not(pathList): + print "\tNo files in range: %s - %s" %(startDateTime.ctime(), endDateTime.ctime()) + return None, None, None, None, None + + directory = pathList[0] + + else: + directory = dirList[-1] + directory = os.path.join(path,directory) + + filename = getlastFileFromPath(directory, ext) + + if not(filename): + return None, None, None, None, None + + if not(self.__verifyFile(os.path.join(directory, filename))): + return None, None, None, None, None + + year = int( filename[1:5] ) + doy = int( filename[5:8] ) + set = int( filename[8:11] ) + + return directory, filename, year, doy, set + def setup(self,dataOutObj=None, path=None, startDate=None, @@ -237,7 +416,8 @@ class JRODataReader(JRODataIO): set=0, expLabel = "", ext = None, - online = 0): + online = False, + delay = 60): if path == None: raise ValueError, "The path is not valid" @@ -251,7 +431,25 @@ class JRODataReader(JRODataIO): self.dataOutObj = dataOutObj if online: - pass + print "Searching files in online mode..." + doypath, file, year, doy, set = self.__searchFilesOnLine(path=path, expLabel=expLabel, ext=ext) + + if not(doypath): + for nTries in range( self.nTries ): + print '\tWaiting %0.2f sec for an valid file in %s: try %02d ...' % (self.delay, path, nTries+1) + time.sleep( self.delay ) + doypath, file, year, doy, set = self.__searchFilesOnLine(path=path, expLabel=expLabel, ext=exp) + if doypath: + break + + if not(doypath): + print "There 'isn't valied files in %s" % path + return None + + self.year = year + self.doy = doy + self.set = set - 1 + self.path = path else: print "Searching files in offline mode ..." @@ -270,6 +468,7 @@ class JRODataReader(JRODataIO): self.filenameList = filenameList self.online = online + self.delay = delay ext = ext.lower() self.ext = ext @@ -288,6 +487,7 @@ class JRODataReader(JRODataIO): return self.dataOutObj def __setNextFileOffline(self): + idFile = self.fileIndex while (True): @@ -316,6 +516,90 @@ class JRODataReader(JRODataIO): return 1 + def __setNextFileOnline(self): + """ + Busca el siguiente file que tenga suficiente data para ser leida, dentro de un folder especifico, si + no encuentra un file valido espera un tiempo determinado y luego busca en los posibles n files + siguientes. + + Affected: + self.flagIsNewFile + self.filename + self.fileSize + self.fp + self.set + self.flagNoMoreFiles + + Return: + 0 : si luego de una busqueda del siguiente file valido este no pudo ser encontrado + 1 : si el file fue abierto con exito y esta listo a ser leido + + Excepciones: + Si un determinado file no puede ser abierto + """ + nFiles = 0 + fileOk_flag = False + firstTime_flag = True + + self.set += 1 + + #busca el 1er file disponible + file, filename = checkForRealPath( self.path, self.year, self.doy, self.set, self.ext ) + if file: + if self.__verifyFile(file, False): + fileOk_flag = True + + #si no encuentra un file entonces espera y vuelve a buscar + if not(fileOk_flag): + for nFiles in range(self.nFiles+1): #busco en los siguientes self.nFiles+1 files posibles + + if firstTime_flag: #si es la 1era vez entonces hace el for self.nTries veces + tries = self.nTries + else: + tries = 1 #si no es la 1era vez entonces solo lo hace una vez + + for nTries in range( tries ): + if firstTime_flag: + print "\tWaiting %0.2f sec for the file \"%s\" , try %03d ..." % ( self.delay, filename, nTries+1 ) + time.sleep( self.delay ) + else: + print "\tSearching next \"%s%04d%03d%03d%s\" file ..." % (self.optchar, self.year, self.doy, self.set, self.ext) + + file, filename = checkForRealPath( self.path, self.year, self.doy, self.set, self.ext ) + if file: + if self.__verifyFile(file): + fileOk_flag = True + break + + if fileOk_flag: + break + + firstTime_flag = False + + print "\tSkipping the file \"%s\" due to this file doesn't exist" % filename + self.set += 1 + + if nFiles == (self.nFiles-1): #si no encuentro el file buscado cambio de carpeta y busco en la siguiente carpeta + self.set = 0 + self.doy += 1 + + if fileOk_flag: + self.fileSize = os.path.getsize( file ) + self.filename = file + self.flagIsNewFile = 1 + if self.fp != None: self.fp.close() + self.fp = open(file) + self.flagNoMoreFiles = 0 + print 'Setting the file: %s' % file + else: + self.fileSize = 0 + self.filename = None + self.flagIsNewFile = 0 + self.fp = None + self.flagNoMoreFiles = 1 + print 'No more Files' + + return fileOk_flag def setNextFile(self):