##// END OF EJS Templates
Se modifico la clase JRODataReader y JRODataWriter para albergar todos los metodos comunes entre Voltaje y Espectra. Solo los metodos particulares se dejaron en la clase VoltageReader, VoltageWriter, SpectraReader y SpectraWriter
Miguel Valdez -
r53:f934921c259c
parent child
Show More
This diff has been collapsed as it changes many lines, (1104 lines changed) Show them Hide them
@@ -1,1854 +1,1360
1 1 '''
2 2 Created on 23/01/2012
3 3
4 4 @author $Author$
5 5 @version $Id$
6 6 '''
7 7 import os, sys
8 8 import glob
9 9 import time
10 10 import numpy
11 11 import fnmatch
12 12 import time, datetime
13 13
14 14 path = os.path.split(os.getcwd())[0]
15 15 sys.path.append(path)
16 16
17 17 from Model.JROHeader import *
18 18 from Model.JROData import JROData
19 19
20
21 def isFileOK(filename):
22 """
23 Determina si la cabecera de un archivo es valido o no, si lo es entonces seria un archivo que podria contener data,
24 si no seria un archivo invalido
25
26 Return:
27 True : si es un archivo valido
28 False : si no es un archivo valido
29
30 Exceptions:
31 Si al leer la cabecera esta no coincide con el tipo de las variables que la contienen entonces se dispara
32 una exception
33 """
34 m_BasicHeader = BasicHeader()
35 m_ProcessingHeader = ProcessingHeader()
36 m_RadarControllerHeader = RadarControllerHeader()
37 m_SystemHeader = SystemHeader()
38 fp = None
39
40 try:
41 fp = open( filename,'rb' )
42 m_BasicHeader.read(fp)
43 m_SystemHeader.read(fp)
44 m_RadarControllerHeader.read(fp)
45 m_ProcessingHeader.read(fp)
46 fp.close()
47 except:
48 if fp != None: fp.close()
49 return False
50
51 return True
52
53
54 20 def checkForRealPath(path, year, doy, set, ext):
55 21 """
56 22 Por ser Linux Case Sensitive entonces checkForRealPath encuentra el nombre correcto de un path,
57 23 Prueba por varias combinaciones de nombres entre mayusculas y minusculas para determinar
58 24 el path exacto de un determinado file.
59 25
60 26 Example :
61 27 nombre correcto del file es .../.../D2009307/P2009307367.ext
62 28
63 29 Entonces la funcion prueba con las siguientes combinaciones
64 30 .../.../x2009307/y2009307367.ext
65 31 .../.../x2009307/Y2009307367.ext
66 32 .../.../X2009307/y2009307367.ext
67 33 .../.../X2009307/Y2009307367.ext
68 34 siendo para este caso, la ultima combinacion de letras, identica al file buscado
69 35
70 36 Return:
71 37 Si encuentra la cobinacion adecuada devuelve el path completo y el nombre del file
72 38 caso contrario devuelve None como path y el la ultima combinacion de nombre en mayusculas
73 39 para el filename
74 40 """
75 41 filepath = None
76 42 find_flag = False
77 43 filename = None
78 44
79 45 if ext.lower() == ".r": #voltage
80 46 str1 = "dD"
81 47 str2 = "dD"
82 48 elif ext.lower() == ".pdata": #spectra
83 49 str1 = "dD"
84 50 str2 = "pP"
85 51 else:
86 52 return None, filename
87 53
88 54 for dir in str1: #barrido por las dos combinaciones posibles de "D"
89 55 for fil in str2: #barrido por las dos combinaciones posibles de "D"
90 56 doypath = "%s%04d%03d" % ( dir, year, doy ) #formo el nombre del directorio xYYYYDDD (x=d o x=D)
91 57 filename = "%s%04d%03d%03d%s" % ( fil, year, doy, set, ext ) #formo el nombre del file xYYYYDDDSSS.ext
92 58 filepath = os.path.join( path, doypath, filename ) #formo el path completo
93 59 if os.path.exists( filepath ): #verifico que exista
94 60 find_flag = True
95 61 break
96 62 if find_flag:
97 63 break
98 64
99 65 if not(find_flag):
100 66 return None, filename
101 67
102 68 return filepath, filename
103 69
104 70
105 71 def isNumber(str):
106 72 """
107 73 Chequea si el conjunto de caracteres que componen un string puede ser convertidos a un numero.
108 74
109 75 Excepciones:
110 76 Si un determinado string no puede ser convertido a numero
111 77 Input:
112 78 str, string al cual se le analiza para determinar si convertible a un numero o no
113 79
114 80 Return:
115 81 True : si el string es uno numerico
116 82 False : no es un string numerico
117 83 """
118 84 try:
119 85 float( str )
120 86 return True
121 87 except:
122 88 return False
123 89
124 90
125 91 def isThisFileinRange(filename, startUTSeconds, endUTSeconds):
126 92 """
127 93 Esta funcion determina si un archivo de datos se encuentra o no dentro del rango de fecha especificado.
128 94
129 95 Inputs:
130 96 filename : nombre completo del archivo de datos en formato Jicamarca (.r)
131 97
132 98 startUTSeconds : fecha inicial del rango seleccionado. La fecha esta dada en
133 99 segundos contados desde 01/01/1970.
134 100 endUTSeconds : fecha final del rango seleccionado. La fecha esta dada en
135 101 segundos contados desde 01/01/1970.
136 102
137 103 Return:
138 104 Boolean : Retorna True si el archivo de datos contiene datos en el rango de
139 105 fecha especificado, de lo contrario retorna False.
140 106
141 107 Excepciones:
142 108 Si el archivo no existe o no puede ser abierto
143 109 Si la cabecera no puede ser leida.
144 110
145 111 """
146 112 m_BasicHeader = BasicHeader()
147 113
148 114 try:
149 115 fp = open(filename,'rb')
150 116 except:
151 117 raise IOError, "The file %s can't be opened" %(filename)
152 118
153 if not(m_BasicHeader.read(fp)):
154 raise IOError, "The file %s has not a valid header" %(filename)
155
119 sts = m_BasicHeader.read(fp)
156 120 fp.close()
157 121
122 if not(sts):
123 print "Skipping the file %s because it has not a valid header" %(filename)
124 return 0
125
158 126 if not ((startUTSeconds <= m_BasicHeader.utc) and (endUTSeconds >= m_BasicHeader.utc)):
159 127 return 0
160 128
161 129 return 1
162 130
163 131
164 def getlastFileFromPath(pathList, ext):
132 def getlastFileFromPath(path, ext):
165 133 """
166 Depura el pathList dejando solo los que cumplan el formato de "PYYYYDDDSSS.ext"
134 Depura el fileList dejando solo los que cumplan el formato de "PYYYYDDDSSS.ext"
167 135 al final de la depuracion devuelve el ultimo file de la lista que quedo.
168 136
169 137 Input:
170 pathList : lista conteniendo todos los filename completos que componen una determinada carpeta
138 fileList : lista conteniendo todos los files (sin path) que componen una determinada carpeta
171 139 ext : extension de los files contenidos en una carpeta
172 140
173 141 Return:
174 El ultimo file de una determinada carpeta
142 El ultimo file de una determinada carpeta, no se considera el path.
175 143 """
176 144
177 filesList = []
178 filename = None
179
145 validFilelist = []
146 fileList = os.listdir(path)
147
180 148 # 0 1234 567 89A BCDE
181 149 # D YYYY DDD SSS .ext
182 150
183 for filename in pathList:
184 year = filename[1:5]
185 doy = filename[5:8]
186 leng = len( ext )
151 for file in fileList:
152 try:
153 year = int(file[1:5])
154 doy = int(file[5:8])
155 except:
156 continue
187 157
188 if ( filename[-leng:].upper() != ext.upper() ) : continue
189 if not( isNumber( year ) ) : continue
190 if not( isNumber( doy ) ) : continue
158 if (os.path.splitext(file)[-1].upper() != ext.upper()) : continue
191 159
192 filesList.append(filename)
160 validFilelist.append(file)
193 161
194 if len( filesList ) > 0:
195 filesList = sorted( filesList, key=str.lower )
196 filename = filesList[-1]
162 if len(validFilelist) > 0:
163 validFilelist = sorted( validFilelist, key=str.lower )
164 return validFilelist[-1]
197 165
198 return filename
166 return None
199 167
200 168
201 169 class DataReader():
202 170
203 171 def __init__(self):
204 172 pass
205 173
206 174
207 175 class DataWriter():
208 176
209 177 def __init__(self):
210 178 pass
211 179
212 180
213 181 class JRODataReader(DataReader):
214 182
215 183 """
216 184 Esta clase es usada como la clase padre de las clases DataReader,
217 185 contiene todos lo metodos necesarios para leer datos desde archivos en formato
218 186 jicamarca o pdata (.r o .pdata). La lectura de los datos siempre se realiza por bloques. Los datos
219 187 leidos son array de 3 dimensiones:
220 188 perfiles*alturas*canales
221 189
222 190 y son almacenados en la variable "datablock".
223 191
224 192 Esta clase contiene instancias (objetos) de las clases BasicHeader, SystemHeader,
225 193 RadarControllerHeader y DataObj. Los tres primeros se usan para almacenar informacion de la
226 194 cabecera de datos (metadata), y el cuarto (DataObj) para obtener y almacenar los datos desde
227 195 el "datablock" cada vez que se ejecute el metodo "getData".
228 196 """
229 197
230 """
231 198 m_BasicHeader = BasicHeader()
232 199
233 200 m_SystemHeader = SystemHeader()
234 201
235 202 m_RadarControllerHeader = RadarControllerHeader()
236 203
237 204 m_ProcessingHeader = ProcessingHeader()
238 205
239 206 m_DataObj = None
240 207
241 208 online = 0
242 209
243 __startDateTime = None
210 startDateTime = None
244 211
245 __endDateTime = None
212 endDateTime = None
246 213
247 __fp = None
214 fp = None
248 215
249 __fileSizeByHeader = None
216 fileSizeByHeader = None
250 217
251 __pathList = []
218 pathList = []
252 219
253 __filenameList = []
220 filenameList = []
254 221
255 __fileIndex = None
222 fileIndex = None
256 223
257 224 filename = None
258 225
259 226 fileSize = None
260 227
261 228 firstHeaderSize = 0
262 229
263 230 basicHeaderSize = 24
264 231
265 __dataType = None
232 dataType = None
266 233
267 __blocksize = 0
234 blocksize = 0
268 235
269 236 datablock = None
270 237
271 __datablockIndex = None
238 datablockIndex = None
272 239
273 __pts2read = 0
240 pts2read = 0
274 241
275 242 #Parametros para el procesamiento en linea
276 __year = 0
243 year = 0
244
245 doy = 0
277 246
278 __doy = 0
247 set = 0
279 248
280 __set = 0
249 ext = None
281 250
282 __ext = None
251 path = None
283 252
284 __path = None
253 optchar = None
285 254
286 __delay = 60 #seconds
255 delay = 7 #seconds
287 256
288 __nTries = 3 #quantity tries
257 nTries = 3 #quantity tries
289 258
290 __nFiles = 3 #number of files for searching
259 nFiles = 3 #number of files for searching
260
261 pts2read = 0
262
263 blocksize = 0
264
265 utc = 0
291 266
292 __pts2read = 0
293 __blocksize = 0
294 __utc = 0
295 267 nBlocks = 0
296 """
268
297 269 #speed of light
298 __c = 3E8
270 c = 3E8
299 271
300 272 def __init__(self, m_DataObj=None):
301 273 """
302 274 Inicializador de la clase JRODataReader para la lectura de datos.
303 275
304 276 Input:
305 277 m_DataObj : Objeto de la clase JROData. Este objeto sera utilizado para
306 278 almacenar un perfil de datos cada vez que se haga un requerimiento
307 279 (getData). El perfil sera obtenido a partir del buffer de datos,
308 280 si el buffer esta vacio se hara un nuevo proceso de lectura de un
309 281 bloque de datos.
310 282 Si este parametro no es pasado se creara uno internamente.
311 283
312 284 Variables afectadas:
313 285 self.m_DataObj
314 286 self.m_BasicHeader
315 287 self.m_SystemHeader
316 288 self.m_RadarControllerHeader
317 289 self.m_ProcessingHeader
318 290
319 291 Return:
320 292 None
321 293 """
322 if m_DataObj == None:
323 m_DataObj = JROData()
324 294
325 if not(isinstance(m_DataObj, JROData)):
326 raise ValueError, "in JRODataReader, m_DataObj must be an class object"
327
328 self.m_DataObj = m_DataObj
329
330 self.m_BasicHeader = BasicHeader()
331
332 self.m_SystemHeader = SystemHeader()
333
334 self.m_RadarControllerHeader = RadarControllerHeader()
335
336 self.m_ProcessingHeader = ProcessingHeader()
337
338 self.__fp = None
339
340 self.__fileIndex = None
341
342 self.__startDateTime = None
343
344 self.__endDateTime = None
345
346 self.__dataType = None
347
348 self.__fileSizeByHeader = 0
349
350 self.__pathList = []
351
352 self.filenameList = []
353
354 self.__lastUTTime = 0
355
356 self.__maxTimeStep = 30
357
358 self.__flagIsNewFile = 0
359
360 self.__ippSeconds = 0
361
362 self.flagResetProcessing = 0
363
364 self.flagIsNewBlock = 0
365
366 self.noMoreFiles = 0
367
368 self.nReadBlocks = 0
369
370 self.online = 0
371
372 self.filename = None
373
374 self.fileSize = None
375
376 self.firstHeaderSize = 0
377
378 self.basicHeaderSize = 24
379
380 self.idProfile = 0
381
382 self.datablock = None
383
384 self.__datablockIndex = 9999
385
386 self.__delay = 7 #seconds
387 self.__nTries = 3 #quantity tries
388 self.__nFiles = 3 #number of files for searching
389 self.__year = 0
390 self.__doy = 0
391 self.__set = 0
392 self.__ext = None
393 self.__path = None
394 self.__blocksize = 0
395 self.__utc = 0
396 self.nBlocks = 0
397
398 self.__pts2read = 0
399 self.__pts2read_SelfSpectra = 0
400 self.__pts2read_CrossSpectra = 0
401 self.__pts2read_DCchannels = 0
402 self.__blocksize = 0
403
404 self.__format = None
295 raise ValueError, "This class can't be instanced"
405 296
406 297
407 298 def __rdSystemHeader(self, fp=None):
408 299
409 300 if fp == None:
410 fp = self.__fp
301 fp = self.fp
411 302
412 303 self.m_SystemHeader.read(fp)
413 304
414 305
415 306 def __rdRadarControllerHeader(self, fp=None):
416 307 if fp == None:
417 fp = self.__fp
308 fp = self.fp
418 309
419 310 self.m_RadarControllerHeader.read(fp)
420 311
421 312
422 313 def __rdProcessingHeader(self, fp=None):
423 314 if fp == None:
424 fp = self.__fp
315 fp = self.fp
425 316
426 317 self.m_ProcessingHeader.read(fp)
427 318
428 319
429 320 def __rdBasicHeader(self, fp=None):
430 321
431 322 if fp == None:
432 fp = self.__fp
323 fp = self.fp
433 324
434 325 self.m_BasicHeader.read(fp)
435
436 326
437 327 def __readFirstHeader(self):
438 328 """
439 329 Lectura del First Header, es decir el Basic Header y el Long Header
440 330
441 331 Affected:
442 332 self.m_BasicHeader
443 333 self.m_SystemHeader
444 334 self.m_RadarControllerHeader
445 335 self.m_ProcessingHeader
446 336 self.firstHeaderSize
447 self.__heights
448 self.__dataType
449 self.__fileSizeByHeader
450 self.__ippSeconds
337 self.heights
338 self.dataType
339 self.fileSizeByHeader
340 self.ippSeconds
451 341 self.nChannels
452 342 self.nPairs
453 self.__pts2read_SelfSpectra
454 self.__pts2read_CrossSpectra
343 self.pts2read_SelfSpectra
344 self.pts2read_CrossSpectra
455 345
456 346 Return:
457 347 None
458 348 """
459 349 self.__rdBasicHeader()
460 350 self.__rdSystemHeader()
461 351 self.__rdRadarControllerHeader()
462 352 self.__rdProcessingHeader()
463 353 self.firstHeaderSize = self.m_BasicHeader.size
464 354
465 355 data_type=int(numpy.log2((self.m_ProcessingHeader.processFlags & PROCFLAG.DATATYPE_MASK))-numpy.log2(PROCFLAG.DATATYPE_CHAR))
466 356 if data_type == 0:
467 357 tmp = numpy.dtype([('real','<i1'),('imag','<i1')])
468 358
469 359 elif data_type == 1:
470 360 tmp = numpy.dtype([('real','<i2'),('imag','<i2')])
471 361
472 362 elif data_type == 2:
473 363 tmp = numpy.dtype([('real','<i4'),('imag','<i4')])
474 364
475 365 elif data_type == 3:
476 366 tmp = numpy.dtype([('real','<i8'),('imag','<i8')])
477 367
478 368 elif data_type == 4:
479 369 tmp = numpy.dtype([('real','<f4'),('imag','<f4')])
480 370
481 371 elif data_type == 5:
482 372 tmp = numpy.dtype([('real','<f8'),('imag','<f8')])
483 373
484 374 else:
485 375 raise ValueError, 'Data type was not defined'
486 376
487 377 xi = self.m_ProcessingHeader.firstHeight
488 378 step = self.m_ProcessingHeader.deltaHeight
489 379 xf = xi + self.m_ProcessingHeader.numHeights*step
490 380
491 self.__heights = numpy.arange(xi, xf, step)
492 self.__dataType = tmp
493 self.__fileSizeByHeader = self.m_ProcessingHeader.dataBlocksPerFile * self.m_ProcessingHeader.blockSize + self.firstHeaderSize + self.basicHeaderSize*(self.m_ProcessingHeader.dataBlocksPerFile - 1)
494 self.__ippSeconds = 2 * 1000 * self.m_RadarControllerHeader.ipp / self.__c
495
496 if self.__format == "jicamarca":
497 self.__pts2read = self.m_ProcessingHeader.profilesPerBlock * self.m_ProcessingHeader.numHeights * self.m_SystemHeader.numChannels
498 self.__blocksize = self.__pts2read
499
500 elif self.__format == "pdata":
501 self.nChannels = 0
502 self.nPairs = 0
503
504 for i in range( 0, self.m_ProcessingHeader.totalSpectra*2, 2 ):
505 if self.m_ProcessingHeader.spectraComb[i] == self.m_ProcessingHeader.spectraComb[i+1]:
506 self.nChannels = self.nChannels + 1
507 else:
508 self.nPairs = self.nPairs + 1
509
510 pts2read = self.m_ProcessingHeader.profilesPerBlock * self.m_ProcessingHeader.numHeights
511 self.__pts2read_SelfSpectra = int( pts2read * self.nChannels )
512 self.__pts2read_CrossSpectra = int( pts2read * self.nPairs )
513 self.__pts2read_DCchannels = int( self.m_ProcessingHeader.numHeights * self.m_SystemHeader.numChannels )
514
515 self.__blocksize = self.__pts2read_SelfSpectra + self.__pts2read_CrossSpectra + self.__pts2read_DCchannels
516
517 self.m_DataObj.nChannels = self.nChannels
518 self.m_DataObj.nPairs = self.nPairs
519
381 self.heights = numpy.arange(xi, xf, step)
382 self.dataType = tmp
383 self.fileSizeByHeader = self.m_ProcessingHeader.dataBlocksPerFile * self.m_ProcessingHeader.blockSize + self.firstHeaderSize + self.basicHeaderSize*(self.m_ProcessingHeader.dataBlocksPerFile - 1)
384 self.ippSeconds = 2 * 1000 * self.m_RadarControllerHeader.ipp / self.c
520 385
386 self.getBlockDimension()
521 387
522 388 def __setNextFileOnline(self):
523 389 """
524 390 Busca el siguiente file que tenga suficiente data para ser leida, dentro de un folder especifico, si
525 391 no encuentra un file valido espera un tiempo determinado y luego busca en los posibles n files
526 392 siguientes.
527 393
528 394 Affected:
529 self.__flagNewFile
395 self.flagIsNewFile
530 396 self.filename
531 397 self.fileSize
532 self.__fp
533 self.__set
398 self.fp
399 self.set
534 400 self.flagNoMoreFiles
535 401
536 402 Return:
537 403 0 : si luego de una busqueda del siguiente file valido este no pudo ser encontrado
538 404 1 : si el file fue abierto con exito y esta listo a ser leido
539 405
540 406 Excepciones:
541 407 Si un determinado file no puede ser abierto
542 408 """
543 409 countFiles = 0
544 410 countTries = 0
545 411
546 412 notFirstTime_flag = False
547 413 fileOk_flag = False
548 414 changeDir_flag = False
549 self.__flagIsNewFile = 0
415 self.flagIsNewFile = 0
550 416
551 417 while( True ): #este loop permite llevar la cuenta de intentos, de files y carpetas,
552 418 #si no encuentra alguno sale del bucle
553 419 countFiles += 1
554 420
555 if countFiles > (self.__nFiles + 1):
421 if countFiles > (self.nFiles + 1):
556 422 break
557 423
558 self.__set += 1
424 self.set += 1
559 425
560 if countFiles > self.__nFiles: #si no encuentro el file buscado cambio de carpeta y busco en la siguiente carpeta
561 self.__set = 0
562 self.__doy += 1
426 if countFiles > self.nFiles: #si no encuentro el file buscado cambio de carpeta y busco en la siguiente carpeta
427 self.set = 0
428 self.doy += 1
563 429 changeDir_flag = True
564 430
565 431 file = None
566 432 filename = None
567 433 fileOk_flag = False
568 434
569 435 #busca el 1er file disponible
570 file, filename = checkForRealPath( self.__path, self.__year, self.__doy, self.__set, self.__ext )
436 file, filename = checkForRealPath( self.path, self.year, self.doy, self.set, self.ext )
571 437
572 438 if file == None:
573 439 if notFirstTime_flag: #si no es la primera vez que busca el file entonces no espera y busca for el siguiente file
574 440 print "\tsearching next \"%s\" file ..." % ( filename )
575 441 continue
576 else: #si es la primera vez que busca el file entonces espera self.__nTries veces hasta encontrarlo o no
577 for nTries in range( self.__nTries ):
442 else: #si es la primera vez que busca el file entonces espera self.nTries veces hasta encontrarlo o no
443 for nTries in range( self.nTries ):
578 444 print "\twaiting new \"%s\" file, try %03d ..." % ( filename, nTries+1 )
579 time.sleep( self.__delay )
445 time.sleep( self.delay )
580 446
581 file, filename = checkForRealPath( self.__path, self.__year, self.__doy, self.__set, self.__ext )
447 file, filename = checkForRealPath( self.path, self.year, self.doy, self.set, self.ext )
582 448 if file != None:
583 449 fileOk_flag = True
584 450 break
585 451
586 452 if not( fileOk_flag ): #no encontro ningun file valido a leer despues de haber esperado alguno
587 453 notFirstTime_flag = True
588 454 continue
589 455
590 456 #una vez que se obtuvo el 1er file valido se procede a checkear si si tamanho es suficiente para empezar a leerlo
591 457 currentSize = os.path.getsize( file )
592 458 neededSize = self.m_ProcessingHeader.blockSize + self.firstHeaderSize
593 459
594 460 #si el tamanho es suficiente entonces deja de buscar
595 461 if currentSize > neededSize:
596 462 fileOk_flag = True
597 463 break
598 464
599 465 fileOk_flag = False
600 466 #si el file no tiene el tamanho necesario se espera una cierta cantidad de tiempo
601 467 #por una cierta cantidad de veces hasta que el contenido del file sea valido
602 468 if changeDir_flag: #si al buscar un file cambie de directorio ya no espero y sigo con el siguiente file
603 469 print "\tsearching next \"%s\" file ..." % filename
604 470 changeDir_flag = False
605 471 continue
606 472
607 for nTries in range( self.__nTries ):
473 for nTries in range( self.nTries ):
608 474 print "\twaiting for the First Header block of \"%s\" file, try %03d ..." % ( filename, nTries+1 )
609 time.sleep( self.__delay )
475 time.sleep( self.delay )
610 476
611 477 currentSize = os.path.getsize( file )
612 478 neededSize = self.m_ProcessingHeader.blockSize + self.firstHeaderSize
613 479
614 480 if currentSize > neededSize:
615 481 fileOk_flag = True
616 482 break
617 483
618 484 if fileOk_flag: #si encontro un file valido sale del bucle y deja de buscar
619 485 break
620 486
621 487 print "Skipping the file \"%s\" due to this files is empty" % filename
622 488 countFiles = 0
623 489
624 490 if fileOk_flag:
625 491 self.fileSize = os.path.getsize( file )
626 492 self.filename = file
627 self.__flagIsNewFile = 1
628 if self.__fp != None: self.__fp.close()
629 self.__fp = open(file)
493 self.flagIsNewFile = 1
494 if self.fp != None: self.fp.close()
495 self.fp = open(file)
630 496 self.noMoreFiles = 0
631 497 print 'Setting the file: %s' % file
632 498 else:
633 499 self.fileSize = 0
634 500 self.filename = None
635 self.__fp = None
501 self.fp = None
636 502 self.noMoreFiles = 1
637 503 print 'No more Files'
638 504
639 505 return fileOk_flag
640 506
641 507
642 508 def __setNextFileOffline(self):
643 509 """
644 510 Busca el siguiente file dentro de un folder que tenga suficiente data para ser leida
645 511
646 512 Affected:
647 self.__flagIsNewFile
648 self.__fileIndex
513 self.flagIsNewFile
514 self.fileIndex
649 515 self.filename
650 516 self.fileSize
651 self.__fp
517 self.fp
652 518
653 519 Return:
654 520 0 : si un determinado file no puede ser abierto
655 521 1 : si el file fue abierto con exito
656 522
657 523 Excepciones:
658 524 Si un determinado file no puede ser abierto
659 525 """
660 idFile = self.__fileIndex
526 idFile = self.fileIndex
661 527 while(True):
662 528
663 529 idFile += 1
664 530
665 if not(idFile < len(self.__filenameList)):
531 if not(idFile < len(self.filenameList)):
666 532 self.flagNoMoreFiles = 1
667 533 print 'No more Files'
668 534 return 0
669 535
670 filename = self.__filenameList[idFile]
536 filename = self.filenameList[idFile]
671 537 fileSize = os.path.getsize(filename)
672 538
673 539 try:
674 540 fp = open(filename,'rb')
675 541 except:
676 542 raise IOError, "The file %s can't be opened" %filename
677 543
678 544 currentSize = fileSize - fp.tell()
679 545 neededSize = self.m_ProcessingHeader.blockSize + self.firstHeaderSize
680 546
681 547 if (currentSize < neededSize):
682 548 print "Skipping the file %s due to it hasn't enough data" %filename
683 549 continue
684 550
685 551 break
686 552
687 self.__flagNewFile = 1
688 self.__fileIndex = idFile
553 self.flagIsNewFile = 1
554 self.fileIndex = idFile
689 555 self.filename = filename
690 556 self.fileSize = fileSize
691 self.__fp = fp
557 self.fp = fp
692 558
693 559 print 'Setting the file: %s'%self.filename
694 560
695 561 return 1
696 562
697 563
698 564 def __setNextFile( self ):
699 565 """
700 566 Determina el siguiente file a leer y si hay uno disponible lee el First Header
701 567
702 568 Affected:
703 569 self.m_BasicHeader
704 570 self.m_SystemHeader
705 571 self.m_RadarControllerHeader
706 572 self.m_ProcessingHeader
707 573 self.firstHeaderSize
708 574
709 575 Return:
710 576 0 : Si no hay files disponibles
711 577 1 : Si hay mas files disponibles
712 578 """
713 if self.__fp != None:
714 self.__fp.close()
579 if self.fp != None:
580 self.fp.close()
715 581
716 582 if self.online:
717 583 newFile = self.__setNextFileOnline()
718 584 else:
719 585 newFile = self.__setNextFileOffline()
720 586
721 587 if self.noMoreFiles:
722 588 sys.exit(0)
723 589
724 590 if not(newFile):
725 591 return 0
726 592
727 593 self.__readFirstHeader()
728 594 self.nBlocks = 0
729 595 return 1
730 596
731 597
732 598 def __setNewBlock(self):
733 599 """
734 600 Lee el Basic Header y posiciona le file pointer en la posicion inicial del bloque a leer
735 601
736 602 Affected:
737 603 self.m_BasicHeader
738 604 self.flagNoContinuousBlock
739 605 self.ns
740 606
741 607 Return:
742 608 0 : Si el file no tiene un Basic Header que pueda ser leido
743 609 1 : Si se pudo leer el Basic Header
744 610 """
745 if self.__fp == None:
611 if self.fp == None:
746 612 return 0
747 613
748 if self.__flagIsNewFile:
614 if self.flagIsNewFile:
749 615 return 1
750 616
751 currentSize = self.fileSize - self.__fp.tell()
617 currentSize = self.fileSize - self.fp.tell()
752 618 neededSize = self.m_ProcessingHeader.blockSize + self.basicHeaderSize
753 619
754 620 #If there is enough data setting new data block
755 621 if ( currentSize >= neededSize ):
756 622 self.__rdBasicHeader()
757 623 return 1
758 624
759 625 #si es OnLine y ademas aun no se han leido un bloque completo entonces se espera por uno valido
760 626 elif (self.nBlocks != self.m_ProcessingHeader.dataBlocksPerFile) and self.online:
761 for nTries in range( self.__nTries ):
627 for nTries in range( self.nTries ):
762 628
763 fpointer = self.__fp.tell()
764 self.__fp.close()
629 fpointer = self.fp.tell()
630 self.fp.close()
765 631
766 632 print "\tWaiting for the next block, try %03d ..." % (nTries+1)
767 time.sleep( self.__delay )
633 time.sleep( self.delay )
768 634
769 self.__fp = open( self.filename, 'rb' )
770 self.__fp.seek( fpointer )
635 self.fp = open( self.filename, 'rb' )
636 self.fp.seek( fpointer )
771 637
772 638 self.fileSize = os.path.getsize( self.filename )
773 currentSize = self.fileSize - self.__fp.tell()
639 currentSize = self.fileSize - self.fp.tell()
774 640 neededSize = self.m_ProcessingHeader.blockSize + self.basicHeaderSize
775 641
776 642 if ( currentSize >= neededSize ):
777 self.__rdBasicHeader()
643 self.rdBasicHeader()
778 644 return 1
779 645
780 646 #Setting new file
781 647 if not( self.__setNextFile() ):
782 648 return 0
783 649
784 deltaTime = self.m_BasicHeader.utc - self.__lastUTTime # check this
650 deltaTime = self.m_BasicHeader.utc - self.lastUTTime # check this
785 651
786 652 self.flagResetProcessing = 0
787 653
788 if deltaTime > self.__maxTimeStep:
654 if deltaTime > self.maxTimeStep:
789 655 self.flagResetProcessing = 1
790 656 #self.nReadBlocks = 0
791 657
792 658 return 1
793
794 659
795 def __readBlockVoltage(self):
796 """
797 __readBlock lee el bloque de datos desde la posicion actual del puntero del archivo
798 (self.__fp) y actualiza todos los parametros relacionados al bloque de datos
799 (metadata + data). La data leida es almacenada en el buffer y el contador del buffer
800 es seteado a 0
801
802 Inputs:
803 None
804
805 Return:
806 None
807
808 Affected:
809 self.__datablockIndex
810 self.datablock
811 self.__flagIsNewFile
812 self.idProfile
813 self.flagIsNewBlock
814 self.nReadBlocks
815
816 Exceptions:
817 Si un bloque leido no es un bloque valido
818 """
819 blockOk_flag = False
820 fpointer = self.__fp.tell()
821
822 junk = numpy.fromfile( self.__fp, self.__dataType, self.__pts2read )
823
824 if self.online:
825 if junk.size != self.__blocksize:
826 for nTries in range( self.__nTries ):
827 print "\tWaiting for the next block, try %03d ..." % (nTries+1)
828 time.sleep( self.__delay )
829 self.__fp.seek( fpointer )
830 fpointer = self.__fp.tell()
831 junk = numpy.fromfile( self.__fp, self.__dataType, self.__pts2read )
832 if junk.size == self.__blocksize:
833 blockOk_flag = True
834 break
835
836 if not( blockOk_flag ):
837 return 0
838
839 try:
840 junk = junk.reshape( (self.m_ProcessingHeader.profilesPerBlock, self.m_ProcessingHeader.numHeights, self.m_SystemHeader.numChannels) )
841 except:
842 print "Data file %s is invalid" % self.filename
843 return 0
844
845 self.datablock = junk['real'] + junk['imag']*1j
846
847 self.__datablockIndex = 0
848 self.__flagIsNewFile = 0
849 self.idProfile = 0
850 self.flagIsNewBlock = 1
851
852 self.nReadBlocks += 1
853 self.nBlocks += 1
854
855 return 1
856
857
858 def __readBlockSpectra(self):
859 """
860 Lee el bloque de datos desde la posicion actual del puntero del archivo
861 (self.__fp) y actualiza todos los parametros relacionados al bloque de datos
862 (metadata + data). La data leida es almacenada en el buffer y el contador del buffer
863 es seteado a 0
864
865 Return: None
866
867 Variables afectadas:
868 self.__datablockIndex
869 self.__flagIsNewFile
870 self.flagIsNewBlock
871 self.nReadBlocks
872 self.__data_spc
873 self.__data_cspc
874 self.__data_dc
875
876 Exceptions:
877 Si un bloque leido no es un bloque valido
878 """
879 blockOk_flag = False
880 fpointer = self.__fp.tell()
881
882 spc = numpy.fromfile( self.__fp, self.__dataType[0], self.__pts2read_SelfSpectra )
883 cspc = numpy.fromfile( self.__fp, self.__dataType, self.__pts2read_CrossSpectra )
884 dc = numpy.fromfile( self.__fp, self.__dataType, self.__pts2read_DCchannels ) #int(self.m_ProcessingHeader.numHeights*self.m_SystemHeader.numChannels) )
885
886 if self.online:
887 if (spc.size + cspc.size + dc.size) != self.__blocksize:
888 for nTries in range( self.__nTries ):
889 #nTries = 0
890 #while( nTries < self.__nTries ):
891 #nTries += 1
892 print "\tWaiting for the next block, try %03d ..." % (nTries+1)
893 time.sleep( self.__delay )
894 self.__fp.seek( fpointer )
895 fpointer = self.__fp.tell()
896 spc = numpy.fromfile( self.__fp, self.__dataType[0], self.__pts2read_SelfSpectra )
897 cspc = numpy.fromfile( self.__fp, self.__dataType, self.__pts2read_CrossSpectra )
898 dc = numpy.fromfile( self.__fp, self.__dataType, self.__pts2read_DCchannels ) #int(self.m_ProcessingHeader.numHeights*self.m_SystemHeader.numChannels) )
899
900 if (spc.size + cspc.size + dc.size) == self.__blocksize:
901 blockOk_flag = True
902 break
903 #if (spc.size + cspc.size + dc.size) == self.__blocksize:
904 # nTries = 0
905 # break
906 if not( blockOk_flag ):
907 return 0
908 #if nTries > 0:
909 # return 0
660 def getBlockDimension(self):
910 661
911 try:
912 spc = spc.reshape( (self.nChannels, self.m_ProcessingHeader.numHeights, self.m_ProcessingHeader.profilesPerBlock) ) #transforma a un arreglo 3D
913 cspc = cspc.reshape( (self.nPairs, self.m_ProcessingHeader.numHeights, self.m_ProcessingHeader.profilesPerBlock) ) #transforma a un arreglo 3D
914 dc = dc.reshape( (self.m_SystemHeader.numChannels, self.m_ProcessingHeader.numHeights) ) #transforma a un arreglo 2D
915 except:
916 print "Data file %s is invalid" % self.filename
917 return 0
918
919 if not( self.m_ProcessingHeader.shif_fft ):
920 spc = numpy.roll( spc, self.m_ProcessingHeader.profilesPerBlock/2, axis=2 ) #desplaza a la derecha en el eje 2 determinadas posiciones
921 cspc = numpy.roll( cspc, self.m_ProcessingHeader.profilesPerBlock/2, axis=2 ) #desplaza a la derecha en el eje 2 determinadas posiciones
662 raise ValueError, "No implemented"
663
664 def hasNotDataInBuffer(self):
922 665
923 spc = numpy.transpose( spc, (0,2,1) )
924 cspc = numpy.transpose( cspc, (0,2,1) )
925 #dc = numpy.transpose(dc, (0,2,1))
926
927 self.__data_spc = spc
928 self.__data_cspc = cspc['real'] + cspc['imag']*1j
929 self.__data_dc = dc['real'] + dc['imag']*1j
930
931 self.datablock_id = 0
932 self.__flagIsNewFile = 0
933 self.flagIsNewBlock = 1
934
935 self.nReadBlocks += 1
936 self.nBlocks += 1
937
938 return 1
939
940
941 def __hasNotDataInBuffer(self):
942 if self.__format == "jicamarca":
943 if self.__datablockIndex >= self.m_ProcessingHeader.profilesPerBlock:
944 return 1
945 else: return 0
666 raise ValueError, "Not implemented"
946 667
947 return 1
948 668
949
950 def __searchFilesOnLine( self, path, startDateTime=None, ext = ".pdata" ):
669 def __searchFilesOnLine( self, path, startDateTime=None, endDateTime=None, expLabel = "", ext = ".pdata" ):
951 670 """
952 671 Busca el ultimo archivo de la ultima carpeta (determinada o no por startDateTime) y
953 672 devuelve el archivo encontrado ademas de otros datos.
954 673
955 674 Input:
956 675 path : carpeta donde estan contenidos los files que contiene data
957 676 startDateTime : punto especifico en el tiempo del cual se requiere la data
958 677 ext : extension de los files
959 678
960 679 Return:
961 680 year : el anho
962 681 doy : el numero de dia del anho
963 682 set : el set del archivo
964 683 filename : el ultimo file de una determinada carpeta
965 684 directory : eL directorio donde esta el file encontrado
966 685 """
967 686
968 print "Searching files ..."
969
687 print "Searching files ..."
688
970 689 dirList = []
971 directory = None
972
973 if startDateTime == None:
974 for thisPath in os.listdir(path):
975 if os.path.isdir( os.path.join(path,thisPath) ):
976 dirList.append( thisPath )
977
978 dirList = sorted( dirList, key=str.lower ) #para que quede ordenado al margen de si el nombre esta en mayusculas o minusculas, utilizo la funcion sorted
979 if len(dirList) > 0 :
980 directory = dirList[-1] #me quedo con el ultimo directorio de una carpeta
981 else:
982 year = startDateTime.timetuple().tm_year
983 doy = startDateTime.timetuple().tm_yday
690 for thisPath in os.listdir(path):
691 if os.path.isdir(os.path.join(path,thisPath)):
692 dirList.append(thisPath)
984 693
985 doyPath = "D%04d%03d" % (year,doy) #caso del nombre en mayusculas
986 if os.path.isdir( os.path.join(path,doyPath) ):
987 directory = doyPath
694 pathList = dirList
695
696 if startDateTime != None:
697 pathList = []
698 thisDateTime = startDateTime
699 if endDateTime == None: endDateTime = startDateTime
988 700
989 doyPath = doyPath.lower() #caso del nombre en minusculas
990 if os.path.isdir( os.path.join(path,doyPath) ):
991 directory = doyPath
701 while(thisDateTime <= endDateTime):
702 year = thisDateTime.timetuple().tm_year
703 doy = thisDateTime.timetuple().tm_yday
704
705 match = fnmatch.filter(dirList, '?' + '%4.4d%3.3d' % (year,doy))
706 if len(match) == 0:
707 thisDateTime += datetime.timedelta(1)
708 continue
709
710 pathList.append(os.path.join(path,match[0], expLabel))
711 thisDateTime += datetime.timedelta(1)
712
713
714 directory = pathList[-1]
992 715
993 716 if directory == None:
994 717 return 0, 0, 0, None, None
995 718
996 filename = getlastFileFromPath( os.listdir( os.path.join(path,directory) ), ext )
997
719
720 nTries = 0
721 while True:
722 if nTries >= self.nTries:
723 break
724 filename = getlastFileFromPath(directory, ext )
725
726 if filename != None:
727 break
728
729 print "Waiting %d seconds for the first file with extension (%s) on %s..." %(self.delay, ext, directory)
730 time.sleep(self.delay)
731 nTries += 1
732
998 733 if filename == None:
999 return 0, 0, 0, None, None
734 return None, None, None, None, None
1000 735
1001 year = int( directory[-7:-3] )
1002 doy = int( directory[-3:] )
1003 ln = len( ext )
1004 set = int( filename[-ln-3:-ln] )
736 if not(self.__verifyFile(os.path.join(directory, filename))):
737 print "The file %s hasn't enough data" % filename
738 return None, None, None, None, None
739
740 year = int( filename[1:5] )
741 doy = int( filename[5:8] )
742 set = int( filename[8:11] )
1005 743
1006 return year, doy, set, filename, directory
744 return directory, filename, year, doy, set
1007 745
1008 746
1009 747 def __searchFilesOffLine(self, path, startDateTime, endDateTime, set=None, expLabel = "", ext = ".r"):
1010 748 """
1011 749 Realiza una busqueda de los archivos que coincidan con los parametros
1012 750 especificados y se encuentren ubicados en el path indicado. Para realizar una busqueda
1013 751 correcta la estructura de directorios debe ser la siguiente:
1014 752
1015 753 ...path/D[yyyy][ddd]/expLabel/D[yyyy][ddd][sss].ext
1016 754
1017 755 [yyyy]: anio
1018 756 [ddd] : dia del anio
1019 757 [sss] : set del archivo
1020 758
1021 759 Inputs:
1022 760 path : Directorio de datos donde se realizara la busqueda. Todos los
1023 761 ficheros que concidan con el criterio de busqueda seran
1024 762 almacenados en una lista y luego retornados.
1025 763 startDateTime : Fecha inicial. Rechaza todos los archivos donde
1026 764 file end time < startDateTime (obejto datetime.datetime)
1027 765
1028 766 endDateTime : Fecha final. Rechaza todos los archivos donde
1029 767 file start time > endDateTime (obejto datetime.datetime)
1030 768
1031 769 set : Set del primer archivo a leer. Por defecto None
1032 770
1033 771 expLabel : Nombre del subdirectorio de datos. Por defecto ""
1034 772
1035 773 ext : Extension de los archivos a leer. Por defecto .r
1036 774
1037 775 Return:
1038 776
1039 777 (pathList, filenameList)
1040 778
1041 779 pathList : Lista de directorios donde se encontraron archivos dentro
1042 780 de los parametros especificados
1043 781 filenameList : Lista de archivos (ruta completa) que coincidieron con los
1044 782 parametros especificados.
1045 783
1046 784 Variables afectadas:
1047 785
1048 self.__filenameList: Lista de archivos (ruta completa) que la clase utiliza
786 self.filenameList: Lista de archivos (ruta completa) que la clase utiliza
1049 787 como fuente para leer los bloque de datos, si se termina
1050 788 de leer todos los bloques de datos de un determinado
1051 789 archivo se pasa al siguiente archivo de la lista.
1052 790
1053 791 Excepciones:
1054 792
1055 793 """
1056 794
1057 795 print "Searching files ..."
1058 796
1059 797 dirList = []
1060 798 for thisPath in os.listdir(path):
1061 799 if os.path.isdir(os.path.join(path,thisPath)):
1062 800 dirList.append(thisPath)
1063 801
1064 802 pathList = []
1065 803
1066 804 thisDateTime = startDateTime
1067 805
1068 806 while(thisDateTime <= endDateTime):
1069 807 year = thisDateTime.timetuple().tm_year
1070 808 doy = thisDateTime.timetuple().tm_yday
1071 809
1072 810 match = fnmatch.filter(dirList, '?' + '%4.4d%3.3d' % (year,doy))
1073 811 if len(match) == 0:
1074 812 thisDateTime += datetime.timedelta(1)
1075 813 continue
1076 814
1077 815 pathList.append(os.path.join(path,match[0],expLabel))
1078 816 thisDateTime += datetime.timedelta(1)
1079 817
1080 818 startUtSeconds = time.mktime(startDateTime.timetuple())
1081 819 endUtSeconds = time.mktime(endDateTime.timetuple())
1082 820
1083 821 filenameList = []
1084 822 for thisPath in pathList:
1085 823 fileList = glob.glob1(thisPath, "*%s" %ext)
1086 824 fileList.sort()
1087 825 for file in fileList:
1088 826 filename = os.path.join(thisPath,file)
1089 827 if isThisFileinRange(filename, startUtSeconds, endUtSeconds):
1090 828 filenameList.append(filename)
1091 829
1092 self.__filenameList = filenameList
830 self.filenameList = filenameList
1093 831
1094 832 return pathList, filenameList
1095 833
1096 834
1097 def __initFilesOnline( self, path, dirfilename, filename ):
835 def __verifyFile( self, filename ):
1098 836 """
1099 Verifica que el primer file tenga una data valida, para ello leo el 1er bloque
837 Verifica que el filename tenga data valida, para ello leo el 1er bloque
1100 838 del file, si no es un file valido espera una cierta cantidad de tiempo a que
1101 839 lo sea, si transcurrido el tiempo no logra validar el file entonces el metodo
1102 840 devuelve 0 caso contrario devuelve 1
1103 841
1104 842 Affected:
1105 843 m_BasicHeader
1106 844
1107 845 Return:
1108 846 0 : file no valido para ser leido
1109 847 1 : file valido para ser leido
1110 848 """
1111 849 m_BasicHeader = BasicHeader()
1112
1113 file = os.path.join( path, dirfilename, filename )
1114 850
1115 for nTries in range( self.__nTries+1 ):
851 for nTries in range( self.nTries+1 ):
1116 852 try:
1117 fp = open( file,'rb' ) #lectura binaria
853 fp = open( filename,'rb' ) #lectura binaria
1118 854 except:
1119 raise IOError, "The file %s can't be opened" % (file)
855 raise IOError, "The file %s can't be opened" % (filename)
1120 856
1121 857 try:
1122 858 m_BasicHeader.read(fp)
1123 859 except:
1124 860 print "The file %s is empty" % filename
1125 861
1126 862 fp.close()
1127 863
1128 864 if m_BasicHeader.size > 24:
1129 865 break
1130 866
1131 if nTries >= self.__nTries: #si ya espero la cantidad de veces necesarias entonces ya no vuelve a esperar
867 if nTries >= self.nTries: #si ya espero la cantidad de veces necesarias entonces ya no vuelve a esperar
1132 868 break
1133 869
1134 print '\twaiting for new block of file %s: try %02d' % ( file, nTries )
1135 time.sleep( self.__delay )
870 print '\twaiting for new block of file %s: try %02d' % ( filename, nTries )
871 time.sleep( self.delay )
1136 872
1137 873 if m_BasicHeader.size <= 24:
1138 874 return 0
1139 875
1140 876 return 1
1141 877
1142 878
1143 879 def setup(self, path, startDateTime, endDateTime=None, set=0, expLabel = "", ext = None, online = 0):
1144 880 """
1145 881 setup configura los parametros de lectura de la clase VoltageReader.
1146 882
1147 883 Si el modo de lectura es offline, primero se realiza una busqueda de todos los archivos
1148 884 que coincidan con los parametros especificados; esta lista de archivos son almacenados en
1149 self.__filenameList.
885 self.filenameList.
1150 886
1151 887 Input:
1152 888 path : Directorios donde se ubican los datos a leer. Dentro de este
1153 889 directorio deberia de estar subdirectorios de la forma:
1154 890
1155 891 path/D[yyyy][ddd]/expLabel/P[yyyy][ddd][sss][ext]
1156 892
1157 893 startDateTime : Fecha inicial. Rechaza todos los archivos donde
1158 894 file end time < startDatetime (obejto datetime.datetime)
1159 895
1160 896 endDateTime : Fecha final. Si no es None, rechaza todos los archivos donde
1161 897 file end time < startDatetime (obejto datetime.datetime)
1162 898
1163 899 set : Set del primer archivo a leer. Por defecto None
1164 900
1165 901 expLabel : Nombre del subdirectorio de datos. Por defecto ""
1166 902
1167 903 ext : Extension de los archivos a leer. Por defecto .r
1168 904
1169 905 online : Si es == a 0 entonces busca files que cumplan con las condiciones dadas
1170 906
1171 907 Return:
1172 908 0 : Si no encuentra files que cumplan con las condiciones dadas
1173 909 1 : Si encuentra files que cumplan con las condiciones dadas
1174 910
1175 911 Affected:
1176 912 self.startUTCSeconds
1177 913 self.endUTCSeconds
1178 914 self.startYear
1179 915 self.endYear
1180 916 self.startDoy
1181 917 self.endDoy
1182 self.__pathList
1183 self.__filenameList
918 self.pathList
919 self.filenameList
1184 920 self.online
1185 921 """
922
923 if ext == None:
924 ext = self.ext
925
1186 926 if online:
1187 fileOK_flag = False
1188 subfolder = "D%04d%03d" % ( startDateTime.timetuple().tm_year, startDateTime.timetuple().tm_yday )
1189 file = os.path.join( path, subfolder )
1190
1191 for nTries in range( self.__nTries+1 ): #espera por el 1er file
1192 year, doy, set, filename, dirfilename = self.__searchFilesOnLine( path, startDateTime, ext )
1193
1194 if filename != None:
1195 if isFileOK( os.path.join( path,dirfilename,filename ) ):
1196 fileOK_flag = True
1197 break
1198
1199 if nTries >= self.__nTries: #si ya espero la cantidad de veces necesarias entonces ya no vuelve a esperar
1200 break
1201
1202 print "Searching first file in \"%s\", try %03d ..." % ( file, nTries+1 )
1203 time.sleep( self.__delay )
1204
1205 if not( fileOK_flag ): #filename == None:
1206 print "No files on line or invalid first file"
927
928 doypath, file, year, doy, set = self.__searchFilesOnLine(path, startDateTime, endDateTime, expLabel, ext)
929
930 if doypath == None:
1207 931 return 0
1208
1209 if self.__initFilesOnline( path, dirfilename, filename ) == 0:
1210 print "The file %s hasn't enough data" % filename
1211 return 0
1212
1213 self.__year = year
1214 self.__doy = doy
1215 self.__set = set - 1
1216 self.__path = path
932
933 self.year = year
934 self.doy = doy
935 self.set = set - 1
936 self.path = path
1217 937
1218 938 else:
1219 pathList, filenameList = self.__searchFilesOffLine( path, startDateTime, endDateTime, set, expLabel, ext )
1220 self.__fileIndex = -1
1221 self.__pathList = pathList
939 pathList, filenameList = self.__searchFilesOffLine(path, startDateTime, endDateTime, set, expLabel, ext)
940 self.fileIndex = -1
941 self.pathList = pathList
1222 942 self.filenameList = filenameList
1223 943
1224 944 self.online = online
1225 self.__ext = ext
945 self.ext = ext
1226 946
1227 947 ext = ext.lower()
1228
1229 if ext == '.hdf5':
1230 print 'call hdf5 library'
1231 return 0
1232
1233 elif ext == '.r':
1234 self.__format = 'jicamarca'
1235
1236 elif ext == '.pdata':
1237 self.__format = 'pdata'
1238
1239 else:
1240 print 'unknow format !!!'
1241 return 0
1242 948
1243 949 if not( self.__setNextFile() ):
1244 950 if (startDateTime != None) and (endDateTime != None):
1245 951 print "No files in range: %s - %s" %(startDateTime.ctime(), endDateTime.ctime())
1246 952 elif startDateTime != None:
1247 953 print "No files in : %s" % startDateTime.ctime()
1248 954 else:
1249 955 print "No files"
1250 956 return 0
1251 957
1252 958 if startDateTime != None:
1253 959 self.startUTCSeconds = time.mktime(startDateTime.timetuple())
1254 960 self.startYear = startDateTime.timetuple().tm_year
1255 961 self.startDoy = startDateTime.timetuple().tm_yday
1256 962
1257 963 if endDateTime != None:
1258 964 self.endUTCSeconds = time.mktime(endDateTime.timetuple())
1259 965 self.endYear = endDateTime.timetuple().tm_year
1260 966 self.endDoy = endDateTime.timetuple().tm_yday
1261 967 #call fillHeaderValues() - to Data Object
1262 968
1263 969 self.m_DataObj.m_BasicHeader = self.m_BasicHeader.copy()
1264 970 self.m_DataObj.m_ProcessingHeader = self.m_ProcessingHeader.copy()
1265 971 self.m_DataObj.m_RadarControllerHeader = self.m_RadarControllerHeader.copy()
1266 972 self.m_DataObj.m_SystemHeader = self.m_SystemHeader.copy()
1267 self.m_DataObj.dataType = self.__dataType
973 self.m_DataObj.dataType = self.dataType
1268 974
1269 975 return 1
1270 976
1271 977
1272 978 def readNextBlock( self ):
1273 979 """
1274 980 Establece un nuevo bloque de datos a leer y los lee, si es que no existiese
1275 981 mas bloques disponibles en el archivo actual salta al siguiente.
1276 982
1277 983 Affected:
1278 self.__lastUTTime
984 self.lastUTTime
1279 985
1280 986 Return: None
1281 987 """
1282 988 if not(self.__setNewBlock()):
1283 989 return 0
1284
1285 if self.__format == "jicamarca":
1286 self.__readBlockVoltage()
1287
1288 elif self.__format == "pdata":
1289 self.__readBlockSpectra()
1290 990
1291 self.__lastUTTime = self.m_BasicHeader.utc
991 self.readBlock()
992
993 self.lastUTTime = self.m_BasicHeader.utc
1292 994
1293 995 return 1
1294 996
997 def readBlock(self):
998
999 raise ValueError, "This method has not been implemented"
1295 1000
1296 1001 def getData( self ):
1297 1002 """
1298 1003 getData obtiene una unidad de datos del buffer de lectura y la copia a la clase "Voltage"
1299 1004 con todos los parametros asociados a este (metadata). cuando no hay datos en el buffer de
1300 1005 lectura es necesario hacer una nueva lectura de los bloques de datos usando "readNextBlock"
1301 1006
1302 1007 Ademas incrementa el contador del buffer en 1.
1303 1008
1304 1009 Return:
1305 1010 data : retorna un perfil de voltages (alturas * canales) copiados desde el
1306 1011 buffer. Si no hay mas archivos a leer retorna None.
1307 1012
1308 1013 Variables afectadas:
1309 self.m_Voltage
1310 self.__datablockIndex
1014 self.m_DataObj
1015 self.datablockIndex
1311 1016
1312 1017 Affected:
1313 self.m_Voltage
1314 self.__datablockIndex
1018 self.m_DataObj
1019 self.datablockIndex
1315 1020 self.flagNoContinuousBlock
1316 self.__flagNewBlock
1021 self.flagNewBlock
1317 1022 """
1318 if self.noMoreFiles: return 0
1319
1320 self.flagResetProcessing = 0
1321 self.flagIsNewBlock = 0
1322
1323 if self.__hasNotDataInBuffer():
1324
1325 if not( self.readNextBlock() ):
1326 self.__setNextFile()
1327 return 0
1328
1329 self.m_DataObj.m_BasicHeader = self.m_BasicHeader.copy()
1330 self.m_DataObj.m_ProcessingHeader = self.m_ProcessingHeader.copy()
1331 self.m_DataObj.m_RadarControllerHeader = self.m_RadarControllerHeader.copy()
1332 self.m_DataObj.m_SystemHeader = self.m_SystemHeader.copy()
1333 self.m_DataObj.heights = self.__heights
1334 self.m_DataObj.dataType = self.__dataType
1335
1336 if self.noMoreFiles == 1:
1337 print 'Process finished'
1338 return 0
1339
1340 #data es un numpy array de 3 dmensiones (perfiles, alturas y canales)
1341 1023
1342 if self.__format == "jicamarca":
1343 if self.datablock == None:
1344 self.m_Voltage.flagNoData = True
1345 return 0
1346
1347 time = self.m_BasicHeader.utc + self.__datablockIndex * self.__ippSeconds
1348 self.__utc = time
1349 #self.m_DataObj.m_BasicHeader.utc = time
1350
1351 self.m_DataObj.flagNoData = False
1352 self.m_DataObj.flagResetProcessing = self.flagResetProcessing
1353
1354 self.m_DataObj.data = self.datablock[self.__datablockIndex,:,:]
1355 self.m_DataObj.idProfile = self.idProfile
1356
1357 self.__datablockIndex += 1
1358 self.idProfile += 1
1359
1360 elif self.__format == "pdata":
1361 if self.__data_dc == None:
1362 self.m_Voltage.flagNoData = True
1363 return 0
1364
1365 self.m_DataObj.flagNoData = False
1366 self.m_DataObj.flagResetProcessing = self.flagResetProcessing
1367
1368 self.m_DataObj.data_spc = self.__data_spc
1369 self.m_DataObj.data_cspc = self.__data_cspc
1370 self.m_DataObj.data_dc = self.__data_dc
1371
1372 else:
1373 return 0
1374
1375 return 1 #self.m_Voltage.data
1024 raise ValueError, "This method has not been implemented"
1376 1025
1377 1026
1378 1027 class JRODataWriter(DataWriter):
1379 1028 """
1380 1029 Esta clase permite escribir datos a archivos procesados (.r o ,pdata). La escritura
1381 1030 de los datos siempre se realiza por bloques.
1382 1031 """
1383 1032
1384 1033 def __init__(self):
1385 1034 """
1386 1035 Inicializador de la clase VoltageWriter para la escritura de datos de espectros.
1387 1036
1388 1037 Affected:
1389 self.m_Voltage
1038 self.m_DataObj
1390 1039 self.m_BasicHeader
1391 1040 self.m_SystemHeader
1392 1041 self.m_RadarControllerHeader
1393 1042 self.m_ProcessingHeader
1394 1043
1395 1044 Return: None
1396 1045 """
1397 1046 if m_Voltage == None:
1398 1047 m_Voltage = Voltage()
1399 1048
1400 self.m_Voltage = m_Voltage
1049 self.m_DataObj = m_Voltage
1401 1050
1402 self.__path = None
1051 self.path = None
1403 1052
1404 self.__fp = None
1053 self.fp = None
1405 1054
1406 self.__format = None
1055 self.format = None
1407 1056
1408 self.__blocksCounter = 0
1057 self.blocksCounter = 0
1409 1058
1410 self.__setFile = None
1059 self.setFile = None
1411 1060
1412 self.__flagIsNewFile = 1
1061 self.flagIsNewFile = 1
1413 1062
1414 self.__dataType = None
1063 self.dataType = None
1415 1064
1416 1065 self.datablock = None
1417 1066
1418 self.__datablockIndex = 0
1067 self.datablockIndex = 0
1419 1068
1420 self.__ext = None
1069 self.ext = None
1421 1070
1422 self.__shapeBuffer = None
1071 self.shapeBuffer = None
1423 1072
1424 self.__shape_spc_Buffer = None
1425 self.__shape_cspc_Buffer = None
1426 self.__shape_dc_Buffer = None
1073 self.shape_spc_Buffer = None
1074
1075 self.shape_cspc_Buffer = None
1076
1077 self.shape_dc_Buffer = None
1427 1078
1428 1079 self.nWriteBlocks = 0
1429 1080
1430 1081 self.flagIsNewBlock = 0
1431 1082
1432 1083 self.noMoreFiles = 0
1433 1084
1434 1085 self.filename = None
1435 1086
1436 1087 self.m_BasicHeader= BasicHeader()
1437 1088
1438 1089 self.m_SystemHeader = SystemHeader()
1439 1090
1440 1091 self.m_RadarControllerHeader = RadarControllerHeader()
1441 1092
1442 1093 self.m_ProcessingHeader = ProcessingHeader()
1443 1094
1444 self.__data_spc = None
1445 self.__data_cspc = None
1446 self.__data_dc = None
1095 self.data_spc = None
1096
1097 self.data_cspc = None
1098
1099 self.data_dc = None
1447 1100
1448 1101
1449 1102 def __writeFirstHeader(self):
1450 1103 """
1451 1104 Escribe el primer header del file es decir el Basic header y el Long header (SystemHeader, RadarControllerHeader, ProcessingHeader)
1452 1105
1453 1106 Affected:
1454 1107 __dataType
1455 1108
1456 1109 Return:
1457 1110 None
1458 1111 """
1459 1112 self.__writeBasicHeader()
1460 1113 self.__wrSystemHeader()
1461 1114 self.__wrRadarControllerHeader()
1462 1115 self.__wrProcessingHeader()
1463 self.__dataType = self.m_DataObj.dataType
1116 self.dataType = self.m_DataObj.dataType
1464 1117
1465 1118
1466 1119 def __writeBasicHeader(self, fp=None):
1467 1120 """
1468 1121 Escribe solo el Basic header en el file creado
1469 1122
1470 1123 Return:
1471 1124 None
1472 1125 """
1473 1126 if fp == None:
1474 fp = self.__fp
1127 fp = self.fp
1475 1128
1476 1129 self.m_BasicHeader.write(fp)
1477 1130
1478 1131
1479 1132 def __wrSystemHeader(self, fp=None):
1480 1133 """
1481 1134 Escribe solo el System header en el file creado
1482 1135
1483 1136 Return:
1484 1137 None
1485 1138 """
1486 1139 if fp == None:
1487 fp = self.__fp
1140 fp = self.fp
1488 1141
1489 1142 self.m_SystemHeader.write(fp)
1490 1143
1491 1144
1492 1145 def __wrRadarControllerHeader(self, fp=None):
1493 1146 """
1494 1147 Escribe solo el RadarController header en el file creado
1495 1148
1496 1149 Return:
1497 1150 None
1498 1151 """
1499 1152 if fp == None:
1500 fp = self.__fp
1153 fp = self.fp
1501 1154
1502 1155 self.m_RadarControllerHeader.write(fp)
1503 1156
1504 1157
1505 1158 def __wrProcessingHeader(self, fp=None):
1506 1159 """
1507 1160 Escribe solo el Processing header en el file creado
1508 1161
1509 1162 Return:
1510 1163 None
1511 1164 """
1512 1165 if fp == None:
1513 fp = self.__fp
1166 fp = self.fp
1514 1167
1515 1168 self.m_ProcessingHeader.write(fp)
1516 1169
1517 1170
1518 1171 def __setNextFile(self):
1519 1172 """
1520 1173 Determina el siguiente file que sera escrito
1521 1174
1522 1175 Affected:
1523 1176 self.filename
1524 self.__subfolder
1525 self.__fp
1526 self.__setFile
1527 self.__flagIsNewFile
1177 self.subfolder
1178 self.fp
1179 self.setFile
1180 self.flagIsNewFile
1528 1181
1529 1182 Return:
1530 1183 0 : Si el archivo no puede ser escrito
1531 1184 1 : Si el archivo esta listo para ser escrito
1532 1185 """
1533 ext = self.__ext
1534 path = self.__path
1186 ext = self.ext
1187 path = self.path
1535 1188
1536 if self.__fp != None:
1537 self.__fp.close()
1189 if self.fp != None:
1190 self.fp.close()
1538 1191
1539 1192 timeTuple = time.localtime( self.m_DataObj.m_BasicHeader.utc ) # utc from m_Voltage
1540 1193 subfolder = 'D%4.4d%3.3d' % (timeTuple.tm_year,timeTuple.tm_yday)
1541 1194
1542 1195 tmp = os.path.join( path, subfolder )
1543 1196 if not( os.path.exists(tmp) ):
1544 1197 os.mkdir(tmp)
1545 self.__setFile = -1 #inicializo mi contador de seteo
1198 self.setFile = -1 #inicializo mi contador de seteo
1546 1199 else:
1547 1200 filesList = os.listdir( tmp )
1548 1201 if len( filesList ) > 0:
1549 1202 filesList = sorted( filesList, key=str.lower )
1550 1203 filen = filesList[-1]
1551 1204 # el filename debera tener el siguiente formato
1552 1205 # 0 1234 567 89A BCDE (hex)
1553 1206 # D YYYY DDD SSS .ext
1554 1207 if isNumber( filen[8:11] ):
1555 self.__setFile = int( filen[8:11] ) #inicializo mi contador de seteo al seteo del ultimo file
1208 self.setFile = int( filen[8:11] ) #inicializo mi contador de seteo al seteo del ultimo file
1556 1209 else:
1557 self.__setFile = -1
1210 self.setFile = -1
1558 1211 else:
1559 self.__setFile = -1 #inicializo mi contador de seteo
1212 self.setFile = -1 #inicializo mi contador de seteo
1560 1213
1561 setFile = self.__setFile
1214 setFile = self.setFile
1562 1215 setFile += 1
1563
1564 if self.__format == "jicamarca":
1565 shead = "D"
1566 elif self.__format == "pdata":
1567 shead = "P"
1568 1216
1569 file = '%s%4.4d%3.3d%3.3d%s' % ( shead, timeTuple.tm_year, timeTuple.tm_yday, setFile, ext )
1217 file = '%s%4.4d%3.3d%3.3d%s' % (self.optchar,
1218 timeTuple.tm_year,
1219 timeTuple.tm_yday,
1220 setFile,
1221 ext )
1570 1222
1571 1223 filename = os.path.join( path, subfolder, file )
1572 1224
1573 1225 fp = open( filename,'wb' )
1574 1226
1575 self.__blocksCounter = 0
1227 self.blocksCounter = 0
1576 1228
1577 1229 #guardando atributos
1578 1230 self.filename = filename
1579 self.__subfolder = subfolder
1580 self.__fp = fp
1581 self.__setFile = setFile
1582 self.__flagIsNewFile = 1
1231 self.subfolder = subfolder
1232 self.fp = fp
1233 self.setFile = setFile
1234 self.flagIsNewFile = 1
1583 1235
1584 1236 print 'Writing the file: %s'%self.filename
1585 1237
1586 1238 self.__writeFirstHeader()
1587 1239
1588 1240 return 1
1589 1241
1590 1242
1591 1243 def __setNewBlock(self):
1592 1244 """
1593 1245 Si es un nuevo file escribe el First Header caso contrario escribe solo el Basic Header
1594 1246
1595 1247 Return:
1596 1248 0 : si no pudo escribir nada
1597 1249 1 : Si escribio el Basic el First Header
1598 1250 """
1599 if self.__fp == None:
1251 if self.fp == None:
1600 1252 self.__setNextFile()
1601 1253
1602 if self.__flagIsNewFile:
1254 if self.flagIsNewFile:
1603 1255 return 1
1604 1256
1605 if self.__blocksCounter < self.m_ProcessingHeader.dataBlocksPerFile:
1257 if self.blocksCounter < self.m_ProcessingHeader.dataBlocksPerFile:
1606 1258 self.__writeBasicHeader()
1607 1259 return 1
1608 1260
1609 1261 if not( self.__setNextFile() ):
1610 1262 return 0
1611 1263
1612 1264 return 1
1613 1265
1614 1266
1615 def __writeVoltageBlock(self):
1616 """
1617 Escribe el buffer en el file designado
1618
1619 Affected:
1620 self.__datablockIndex
1621 self.__flagIsNewFile
1622 self.flagIsNewBlock
1623 self.nWriteBlocks
1624 self.__blocksCounter
1625
1626 Return: None
1627 """
1628 data = numpy.zeros( self.__shapeBuffer, self.__dataType )
1629
1630 data['real'] = self.datablock.real
1631 data['imag'] = self.datablock.imag
1632
1633 data = data.reshape( (-1) )
1634
1635 data.tofile( self.__fp )
1636
1637 self.datablock.fill(0)
1638 self.__datablockIndex = 0
1639 self.__flagIsNewFile = 0
1640 self.flagIsNewBlock = 1
1641 self.nWriteBlocks += 1
1642 self.__blocksCounter += 1
1643
1644
1645 def __writeSpectraBlock(self):
1646 """
1647 Escribe el buffer en el file designado
1648
1649 Affected:
1650 self.__data_spc
1651 self.__data_cspc
1652 self.__data_dc
1653 self.__flagIsNewFile
1654 self.flagIsNewBlock
1655 self.nWriteBlocks
1656 self.__blocksCounter
1657
1658 Return: None
1659 """
1660 spc = numpy.transpose( self.__data_spc, (0,2,1) )
1661 if not( self.m_ProcessingHeader.shif_fft ):
1662 spc = numpy.roll( spc, self.m_ProcessingHeader.profilesPerBlock/2, axis=2 ) #desplaza a la derecha en el eje 2 determinadas posiciones
1663 data = spc.reshape((-1))
1664 data.tofile(self.__fp)
1665
1666 data = numpy.zeros( self.__shape_cspc_Buffer, self.__dataType )
1667 cspc = numpy.transpose( self.__data_cspc, (0,2,1) )
1668 if not( self.m_ProcessingHeader.shif_fft ):
1669 cspc = numpy.roll( cspc, self.m_ProcessingHeader.profilesPerBlock/2, axis=2 ) #desplaza a la derecha en el eje 2 determinadas posiciones
1670 data['real'] = cspc.real
1671 data['imag'] = cspc.imag
1672 data = data.reshape((-1))
1673 data.tofile(self.__fp)
1674
1675 data = numpy.zeros( self.__shape_dc_Buffer, self.__dataType )
1676 dc = self.__data_dc
1677 data['real'] = dc.real
1678 data['imag'] = dc.imag
1679 data = data.reshape((-1))
1680 data.tofile(self.__fp)
1681
1682 self.__data_spc.fill(0)
1683 self.__data_cspc.fill(0)
1684 self.__data_dc.fill(0)
1685
1686 self.__flagIsNewFile = 0
1687 self.flagIsNewBlock = 1
1688 self.nWriteBlocks += 1
1689 self.__blocksCounter += 1
1690
1691
1692 1267 def writeNextBlock(self):
1693 1268 """
1694 1269 Selecciona el bloque siguiente de datos y los escribe en un file
1695 1270
1696 1271 Return:
1697 1272 0 : Si no hizo pudo escribir el bloque de datos
1698 1273 1 : Si no pudo escribir el bloque de datos
1699 1274 """
1700 1275 if not( self.__setNewBlock() ):
1701 1276 return 0
1702 1277
1703 if self.__format == "jicamarca":
1704 self.__writeVoltageBlock()
1278 self.writeBlock()
1705 1279
1706 if self.__format == "pdata":
1707 self.__writeSpectraBlock()
1708
1709 return 1
1710
1711
1712 def __hasAllDataInBuffer(self):
1713 if self.__format == "jicamarca":
1714 if self.__datablockIndex >= self.m_ProcessingHeader.profilesPerBlock:
1715 return 1
1716 else: return 0
1717
1718 return 1
1719
1720
1721 def putData(self):
1722 """
1723 Setea un bloque de datos y luego los escribe en un file
1724
1725 Affected:
1726 self.flagIsNewBlock
1727 self.__datablockIndex
1728
1729 Return:
1730 0 : Si no hay data o no hay mas files que puedan escribirse
1731 1 : Si se escribio la data de un bloque en un file
1732 """
1733 self.flagIsNewBlock = 0
1734
1735 if self.m_DataObj.flagNoData:
1736 return 0
1737
1738 if self.m_DataObj.flagResetProcessing:
1739 if self.__format == "jicamarca":
1740 self.datablock.fill(0)
1741 self.__datablockIndex = 0
1742
1743 elif self.__format == "pdata":
1744 self.__data_spc.fill(0)
1745 self.__data_cspc.fill(0)
1746 self.__data_dc.fill(0)
1747
1748 self.__setNextFile()
1749
1750 if self.__format == "jicamarca":
1751 self.datablock[self.__datablockIndex,:,:] = self.m_Voltage.data
1752
1753 elif self.__format == "pdata":
1754 self.__data_spc = self.m_Spectra.data_spc
1755 self.__data_cspc = self.m_Spectra.data_cspc
1756 self.__data_dc = self.m_Spectra.data_dc
1757
1758 self.__datablockIndex += 1
1759
1760 if self.__hasAllDataInBuffer():
1761 self.__getHeader()
1762 self.writeNextBlock()
1763
1764 if self.noMoreFiles:
1765 #print 'Process finished'
1766 return 0
1767
1768 1280 return 1
1769 1281
1770
1771 def __getHeader(self):
1282 def getHeader(self):
1772 1283 """
1773 1284 Obtiene una copia del First Header
1774 1285
1775 1286 Affected:
1776 1287 self.m_BasicHeader
1777 1288 self.m_SystemHeader
1778 1289 self.m_RadarControllerHeader
1779 1290 self.m_ProcessingHeader
1780 self.__dataType
1291 self.dataType
1781 1292
1782 1293 Return:
1783 1294 None
1784 1295 """
1785 1296 self.m_BasicHeader = self.m_DataObj.m_BasicHeader.copy()
1786 1297 self.m_SystemHeader = self.m_DataObj.m_SystemHeader.copy()
1787 1298 self.m_RadarControllerHeader = self.m_DataObj.m_RadarControllerHeader.copy()
1788 1299 self.m_ProcessingHeader = self.m_DataObj.m_ProcessingHeader.copy()
1789 self.__dataType = self.m_DataObj.dataType
1790
1791
1792 def setup(self, path, set=0, ext='.pdata'):
1300 self.dataType = self.m_DataObj.dataType
1301
1302 def setup(self, path, set=0, ext=None):
1793 1303 """
1794 1304 Setea el tipo de formato en la cual sera guardada la data y escribe el First Header
1795 1305
1796 1306 Inputs:
1797 1307 path : el path destino en el cual se escribiran los files a crear
1798 1308 format : formato en el cual sera salvado un file
1799 1309 set : el setebo del file
1800 1310
1801 1311 Return:
1802 1312 0 : Si no realizo un buen seteo
1803 1313 1 : Si realizo un buen seteo
1804 1314 """
1805
1806 ext = ext.lower()
1807 1315
1808 if ext == '.hdf5':
1809 print 'call hdf5 library'
1810 return 0
1316 if ext == None:
1317 ext = self.ext
1811 1318
1812 elif ext == '.r':
1813 format = 'jicamarca'
1319 ext = ext.lower()
1320
1321 self.path = path
1322 self.setFile = set - 1
1323 self.ext = ext
1324 self.format = format
1325 self.getHeader()
1814 1326
1815 elif ext == '.pdata':
1816 format = 'pdata'
1327 self.setBlockDimension()
1817 1328
1818 else:
1819 print 'unknow format !!!'
1329 if not( self.__setNextFile() ):
1330 print "There isn't a next file"
1820 1331 return 0
1821 1332
1822 self.__path = path
1823 self.__setFile = set - 1
1824 self.__ext = ext
1825 self.__format = format
1826 self.__getHeader()
1333 return 1
1827 1334
1828 if self.__format == "jicamarca":
1829 self.__shapeBuffer = (self.m_ProcessingHeader.profilesPerBlock,
1830 self.m_ProcessingHeader.numHeights,
1831 self.m_SystemHeader.numChannels )
1832
1833 self.datablock = numpy.zeros(self.__shapeBuffer, numpy.dtype('complex'))
1335 def hasAllDataInBuffer(self):
1336
1337 raise ValueError, "Not implemented"
1834 1338
1835 elif self.__format == "pdata":
1836 self.__shape_spc_Buffer = ( self.m_Spectra.nChannels,
1837 self.m_ProcessingHeader.numHeights,
1838 self.m_ProcessingHeader.profilesPerBlock
1839 )
1339 def setBlockDimension(self):
1340
1341 raise ValueError, "Not implemented"
1342
1343 def writeBlock(self):
1344
1345 raise ValueError, "No implemented"
1840 1346
1841 self.__shape_cspc_Buffer = ( self.m_Spectra.nPairs,
1842 self.m_ProcessingHeader.numHeights,
1843 self.m_ProcessingHeader.profilesPerBlock
1844 )
1347 def putData(self):
1348 """
1349 Setea un bloque de datos y luego los escribe en un file
1845 1350
1846 self.__shape_dc_Buffer = ( self.m_SystemHeader.numChannels,
1847 self.m_ProcessingHeader.numHeights
1848 )
1849
1850 if not( self.__setNextFile() ):
1851 print "There isn't a next file"
1852 return 0
1351 Affected:
1352 self.flagIsNewBlock
1353 self.datablockIndex
1853 1354
1854 return 1
1355 Return:
1356 0 : Si no hay data o no hay mas files que puedan escribirse
1357 1 : Si se escribio la data de un bloque en un file
1358 """
1359
1360 raise ValueError, "No implemented" No newline at end of file
This diff has been collapsed as it changes many lines, (1546 lines changed) Show them Hide them
@@ -1,1758 +1,502
1 1 '''
2 2 File: SpectraIO.py
3 3 Created on 20/02/2012
4 4
5 5 @author $Author$
6 6 @version $Id$
7 7 '''
8 8
9 9 import os, sys
10 10 import numpy
11 11 import glob
12 12 import fnmatch
13 13 import time, datetime
14 14
15 15 path = os.path.split(os.getcwd())[0]
16 16 sys.path.append(path)
17 17
18 18 from Model.JROHeader import *
19 19 from Model.Spectra import Spectra
20 20
21 21 from DataIO import JRODataReader
22 22 from DataIO import JRODataWriter
23
24 def isFileOK(filename):
25 """
26 Determina si la cabecera de un archivo es valido o no, si lo es entonces seria un archivo que podria contener data,
27 si no seria un archivo invalido
28
29 Return:
30 True : si es un archivo valido
31 False : si no es un archivo valido
32
33 Exceptions:
34 Si al leer la cabecera esta no coincide con el tipo de las variables que la contienen entonces se dispara
35 una exception
36 """
37 m_BasicHeader = BasicHeader()
38 m_ProcessingHeader = ProcessingHeader()
39 m_RadarControllerHeader = RadarControllerHeader()
40 m_SystemHeader = SystemHeader()
41 fp = None
42
43 try:
44 fp = open( filename,'rb' ) #lectura binaria
45 m_BasicHeader.read(fp)
46 m_SystemHeader.read(fp)
47 m_RadarControllerHeader.read(fp)
48 m_ProcessingHeader.read(fp)
49 fp.close()
50 except:
51 if fp != None: fp.close()
52 return False
53
54 return True
55
56
57 def getlastFileFromPath(pathList,ext):
58 """
59 Depura el pathList dejando solo los que cumplan el formato de "PYYYYDDDSSS.ext"
60 al final de la depuracion devuelve el ultimo file de la lista que quedo.
61
62 Input:
63 pathList : lista conteniendo todos los filename completos que componen una determinada carpeta
64 ext : extension de los files contenidos en una carpeta
65
66 Return:
67 El ultimo file de una determinada carpeta
68 """
69
70 filesList = []
71 filename = None
72
73 # 0 1234 567 89A BCDE
74 # P YYYY DDD SSS .ext
75
76 for filename in pathList:
77 year = filename[1:5]
78 doy = filename[5:8]
79 leng = len( ext )
80
81 if ( filename[-leng:].upper() != ext.upper() ) : continue
82 if not( isNumber( year ) ) : continue
83 if not( isNumber( doy ) ) : continue
84
85 filesList.append(filename)
86
87 if len( filesList ) > 0:
88 filesList = sorted( filesList, key=str.lower )
89 filename = filesList[-1]
90
91 return filename
92
93
94 def checkForRealPath(path,year,doy,set,ext):
95 """
96 Por ser Linux Case Sensitive entonces checkForRealPath encuentra el nombre correcto de un path,
97 Prueba por varias combinaciones de nombres entre mayusculas y minusculas para determinar
98 el path exacto de un determinado file.
99
100 Example :
101 nombre correcto del file es ../RAWDATA/D2009307/P2009307367
102
103 Entonces la funcion prueba con las siguientes combinaciones
104 ../RAWDATA/d2009307/p2009307367
105 ../RAWDATA/d2009307/P2009307367
106 ../RAWDATA/D2009307/p2009307367
107 ../RAWDATA/D2009307/P2009307367
108 siendo para este caso, la ultima combinacion de letras, identica al file buscado
109
110 Return:
111 Si encuentra la cobinacion adecuada devuelve el path completo y el nombre del file
112 caso contrario devuelve None como path y el la ultima combinacion de nombre en mayusculas
113 para el filename
114 """
115 filepath = None
116 find_flag = False
117 filename = None
118
119 for dir in "dD": #barrido por las dos combinaciones posibles de "D"
120 for fil in "pP": #barrido por las dos combinaciones posibles de "D"
121 doypath = "%s%04d%03d" % ( dir, year, doy ) #formo el nombre del directorio xYYYYDDD (x=d o x=D)
122 filename = "%s%04d%03d%03d%s" % ( fil, year, doy, set, ext ) #formo el nombre del file xYYYYDDDSSS.ext (p=d o p=D)
123 filepath = os.path.join( path, doypath, filename ) #formo el path completo
124 if os.path.exists( filepath ): #verifico que exista
125 find_flag = True
126 break
127 if find_flag:
128 break
129
130 if not(find_flag):
131 return None, filename
132
133 return filepath, filename
134
135 def isNumber(str):
136 """
137 Chequea si el conjunto de caracteres que componen un string puede ser convertidos a un numero.
138
139 Excepciones:
140 Si un determinado string no puede ser convertido a numero
141 Input:
142 str, string al cual se le analiza para determinar si convertible a un numero o no
143
144 Return:
145 True : si el string es uno numerico
146 False : no es un string numerico
147 """
148 try:
149 float( str )
150 return True
151 except:
152 return False
153
154
155
156 def isThisFileinRange(filename,startUTSeconds,endUTSeconds):
157 """
158 Esta funcion determina si un archivo de datos en formato Jicamarca(.r) se encuentra
159 o no dentro del rango de fecha especificado.
160
161 Inputs:
162 filename : nombre completo del archivo de datos en formato Jicamarca (.r)
163
164 startUTSeconds : fecha inicial del rango seleccionado. La fecha esta dada en
165 segundos contados desde 01/01/1970.
166
167 endUTSeconds : fecha final del rango seleccionado. La fecha esta dada en
168 segundos contados desde 01/01/1970.
169
170 Return:
171 Boolean : Retorna True si el archivo de datos contiene datos en el rango de
172 fecha especificado, de lo contrario retorna False.
173
174 Excepciones:
175 Si el archivo no existe o no puede ser abierto
176 Si la cabecera no puede ser leida.
177 """
178 m_BasicHeader = BasicHeader()
179
180 try:
181 fp = open( filename,'rb' ) #lectura binaria
182 except:
183 raise IOError, "The file %s can't be opened" %(filename)
184
185 if not(m_BasicHeader.read(fp)):
186 raise IOError, "The file %s has not a valid header" %(filename)
187
188 fp.close()
189
190 if not ((startUTSeconds <= m_BasicHeader.utc) and (endUTSeconds >= m_BasicHeader.utc)):
191 return 0
192
193 return 1
23 from DataIO import isNumber
194 24
195 25
196 26 class SpectraReader( JRODataReader ):
197 27 """
198 28 Esta clase permite leer datos de espectros desde archivos procesados (.pdata). La lectura
199 29 de los datos siempre se realiza por bloques. Los datos leidos (array de 3 dimensiones)
200 30 son almacenados en tres buffer's para el Self Spectra, el Cross Spectra y el DC Channel.
201 31
202 32 Esta clase contiene instancias (objetos) de las clases BasicHeader, SystemHeader,
203 33 RadarControllerHeader y Spectra. Los tres primeros se usan para almacenar informacion de la
204 34 cabecera de datos (metadata), y el cuarto (Spectra) para obtener y almacenar un bloque de
205 35 datos desde el "buffer" cada vez que se ejecute el metodo "getData".
206 36
207 37 Example:
208 38 dpath = "/home/myuser/data"
209 39
210 40 startTime = datetime.datetime(2010,1,20,0,0,0,0,0,0)
211 41
212 42 endTime = datetime.datetime(2010,1,21,23,59,59,0,0,0)
213 43
214 44 readerObj = SpectraReader()
215 45
216 46 readerObj.setup(dpath, startTime, endTime)
217 47
218 48 while(True):
219 49
220 50 readerObj.getData()
221 51
222 52 print readerObj.m_Spectra.data
223 53
224 54 if readerObj.noMoreFiles:
225 55 break
226 56
227 57 """
228 58
229 #speed of light
230 __c = 3E8
231
232 59
233 60 def __init__(self,m_Spectra=None):
234 61 """
235 62 Inicializador de la clase SpectraReader para la lectura de datos de espectros.
236 63
237 64 Inputs:
238 65 m_Spectra : Objeto de la clase Spectra. Este objeto sera utilizado para
239 66 almacenar un perfil de datos cada vez que se haga un requerimiento
240 67 (getData). El perfil sera obtenido a partir del buffer de datos,
241 68 si el buffer esta vacio se hara un nuevo proceso de lectura de un
242 69 bloque de datos.
243 70 Si este parametro no es pasado se creara uno internamente.
244 71
245 72 Affected:
246 self.m_Spectra
73 self.m_DataObj
247 74 self.m_BasicHeader
248 75 self.m_SystemHeader
249 76 self.m_RadarControllerHeader
250 77 self.m_ProcessingHeader
251 78
252 79 Return : None
253 80 """
254 81 if m_Spectra == None:
255 82 m_Spectra = Spectra()
256 83
257 84 if not( isinstance(m_Spectra, Spectra) ):
258 85 raise ValueError, "in SpectraReader, m_Spectra must be an Spectra class object"
259 86
260 self.m_Spectra = m_Spectra
87 self.m_DataObj = m_Spectra
261 88
262 89 self.m_BasicHeader = BasicHeader()
263 90
264 91 self.m_SystemHeader = SystemHeader()
265 92
266 93 self.m_RadarControllerHeader = RadarControllerHeader()
267 94
268 95 self.m_ProcessingHeader = ProcessingHeader()
269 96
270 self.__fp = None
97 self.fp = None
271 98
272 self.__idFile = None
99 self.idFile = None
273 100
274 self.__startDateTime = None
101 self.startDateTime = None
275 102
276 self.__endDateTime = None
103 self.endDateTime = None
277 104
278 self.__dataType = None
105 self.dataType = None
279 106
280 self.__fileSizeByHeader = 0
107 self.fileSizeByHeader = 0
281 108
282 self.__pathList = []
109 self.pathList = []
283 110
284 111 self.filenameList = []
285 112
286 self.__lastUTTime = 0
113 self.lastUTTime = 0
287 114
288 self.__maxTimeStep = 30
115 self.maxTimeStep = 30
289 116
290 self.__flagIsNewFile = 0
117 self.flagIsNewFile = 0
291 118
292 119 self.flagResetProcessing = 0
293 120
294 121 self.flagIsNewBlock = 0
295 122
296 123 self.noMoreFiles = 0
297 124
298 125 self.nReadBlocks = 0
299 126
300 127 self.online = 0
301 128
302 129 self.firstHeaderSize = 0
303 130
304 131 self.basicHeaderSize = 24
305 132
306 133 self.filename = None
307 134
308 135 self.fileSize = None
309 136
310 self.__data_spc = None
311 self.__data_cspc = None
312 self.__data_dc = None
137 self.data_spc = None
138 self.data_cspc = None
139 self.data_dc = None
313 140
314 141 self.nChannels = 0
315 142 self.nPairs = 0
316 143
317 self.__pts2read_SelfSpectra = 0
318 self.__pts2read_CrossSpectra = 0
319 self.__pts2read_DCchannels = 0
320 self.__blocksize = 0
144 self.pts2read_SelfSpectra = 0
145 self.pts2read_CrossSpectra = 0
146 self.pts2read_DCchannels = 0
147 self.blocksize = 0
321 148
322 self.__datablockIndex = 0
149 self.datablockIndex = 0
323 150
324 self.__ippSeconds = 0
151 self.ippSeconds = 0
325 152
326 153 self.nSelfChannels = 0
327 154
328 155 self.nCrossPairs = 0
329 156
330 157 self.datablock_id = 9999
331 158
332 self.__delay = 2 #seconds
333 self.__nTries = 3 #quantity tries
334 self.__nFiles = 3 #number of files for searching
335 self.__year = 0
336 self.__doy = 0
337 self.__set = 0
338 self.__ext = None
339 self.__path = None
159 self.delay = 2 #seconds
160 self.nTries = 3 #quantity tries
161 self.nFiles = 3 #number of files for searching
162 self.year = 0
163 self.doy = 0
164 self.set = 0
165 self.ext = ".pdata"
166 self.path = None
167 self.optchar = "P"
340 168 self.nBlocks = 0
341
342 def __rdSystemHeader(self,fp=None):
343 """
344 Lectura del System Header
345
346 Inputs:
347 fp : file pointer
348
349 Affected:
350 self.m_SystemHeader
351
352 Return: None
353 """
354 if fp == None:
355 fp = self.__fp
356
357 self.m_SystemHeader.read( fp )
358
359
360
361 def __rdRadarControllerHeader(self,fp=None):
362 """
363 Lectura del Radar Controller Header
364
365 Inputs:
366 fp : file pointer
367
368 Affected:
369 self.m_RadarControllerHeader
370
371 Return: None
372 """
373 if fp == None:
374 fp = self.__fp
375
376 self.m_RadarControllerHeader.read(fp)
377
378
379 def __rdProcessingHeader(self,fp=None):
380 """
381 Lectura del Processing Header
382
383 Inputs:
384 fp : file pointer
385
386 Affected:
387 self.m_ProcessingHeader
388
389 Return: None
390 """
391 if fp == None:
392 fp = self.__fp
393
394 self.m_ProcessingHeader.read(fp)
395
396
397 def __rdBasicHeader(self,fp=None):
398 """
399 Lectura del Basic Header
400 169
401 Inputs:
402 fp : file pointer
403
404 Affected:
405 self.m_BasicHeader
406
407 Return: None
408 """
409 if fp == None:
410 fp = self.__fp
411
412 self.m_BasicHeader.read(fp)
170 def hasNotDataInBuffer(self):
171 return 1
413 172
414
415 def __readFirstHeader(self):
416 """
417 Lectura del First Header, es decir el Basic Header y el Long Header
418
419 Affected:
420 self.m_BasicHeader
421 self.m_SystemHeader
422 self.m_RadarControllerHeader
423 self.m_ProcessingHeader
424 self.firstHeaderSize
425 self.__heights
426 self.__dataType
427 self.__fileSizeByHeader
428 self.__ippSeconds
429 self.nChannels
430 self.nPairs
431 self.__pts2read_SelfSpectra
432 self.__pts2read_CrossSpectra
433
434 Return: None
435 """
436 self.__rdBasicHeader()
437 self.__rdSystemHeader()
438 self.__rdRadarControllerHeader()
439 self.__rdProcessingHeader()
440 self.firstHeaderSize = self.m_BasicHeader.size
441
442 data_type = int( numpy.log2((self.m_ProcessingHeader.processFlags & PROCFLAG.DATATYPE_MASK))-numpy.log2(PROCFLAG.DATATYPE_CHAR) )
443 if data_type == 0:
444 tmp = numpy.dtype([('real','<i1'),('imag','<i1')])
445
446 elif data_type == 1:
447 tmp = numpy.dtype([('real','<i2'),('imag','<i2')])
448
449 elif data_type == 2:
450 tmp = numpy.dtype([('real','<i4'),('imag','<i4')])
451
452 elif data_type == 3:
453 tmp = numpy.dtype([('real','<i8'),('imag','<i8')])
454
455 elif data_type == 4:
456 tmp = numpy.dtype([('real','<f4'),('imag','<f4')])
457
458 elif data_type == 5:
459 tmp = numpy.dtype([('real','<f8'),('imag','<f8')])
460
461 else:
462 raise ValueError, 'Data type was not defined'
463
464 xi = self.m_ProcessingHeader.firstHeight
465 step = self.m_ProcessingHeader.deltaHeight
466 xf = xi + self.m_ProcessingHeader.numHeights*step
467
468 self.__heights = numpy.arange(xi, xf, step)
469
470 self.__dataType = tmp
471 self.__fileSizeByHeader = self.m_ProcessingHeader.dataBlocksPerFile * self.m_ProcessingHeader.blockSize + self.firstHeaderSize + self.basicHeaderSize*(self.m_ProcessingHeader.dataBlocksPerFile - 1)
472 self.__ippSeconds = 2 * 1000 * self.m_RadarControllerHeader.ipp / self.__c
173 def getBlockDimension(self):
473 174
474 175 self.nChannels = 0
475 176 self.nPairs = 0
476 177
477 178 for i in range( 0, self.m_ProcessingHeader.totalSpectra*2, 2 ):
478 179 if self.m_ProcessingHeader.spectraComb[i] == self.m_ProcessingHeader.spectraComb[i+1]:
479 180 self.nChannels = self.nChannels + 1
480 181 else:
481 182 self.nPairs = self.nPairs + 1
482 183
483 184 pts2read = self.m_ProcessingHeader.profilesPerBlock * self.m_ProcessingHeader.numHeights
484 self.__pts2read_SelfSpectra = int( pts2read * self.nChannels )
485 self.__pts2read_CrossSpectra = int( pts2read * self.nPairs )
486 self.__pts2read_DCchannels = int( self.m_ProcessingHeader.numHeights * self.m_SystemHeader.numChannels )
487
488 self.__blocksize = self.__pts2read_SelfSpectra + self.__pts2read_CrossSpectra + self.__pts2read_DCchannels
489
490 self.m_Spectra.nChannels = self.nChannels
491 self.m_Spectra.nPairs = self.nPairs
492
493
494 def __setNextFileOnline(self):
495 """
496 Busca el siguiente file que tenga suficiente data para ser leida, dentro de un folder especifico, si
497 no encuentra un file valido espera un tiempo determinado y luego busca en los posibles n files
498 siguientes.
499
500 Affected:
501 self.__flagIsNewFile
502 self.filename
503 self.fileSize
504 self.__fp
505 self.__set
506 self.noMoreFiles
507
508 Return:
509 0 : si luego de una busqueda del siguiente file valido este no pudo ser encontrado
510 1 : si el file fue abierto con exito y esta listo a ser leido
511
512 Excepciones:
513 Si un determinado file no puede ser abierto
514 """
515 countFiles = 0
516 countTries = 0
517
518 #fileStatus = 0
519 notFirstTime_flag = False
520 fileOk_flag = False
521 changeDir_flag = False
522
523 fileSize = 0
524 fp = None
525
526 self.__flagIsNewFile = 0
527
528 while(True): #este loop permite llevar la cuenta de intentos, de files y carpetas,
529 #si no encuentra alguno sale del bucle
530
531 countFiles += 1
532
533 if countFiles > (self.__nFiles + 1):
534 break
535
536 self.__set += 1
537
538 if countFiles > self.__nFiles: #si no encuentro el file buscado cambio de carpeta y busco en la siguiente carpeta
539 self.__set = 0
540 self.__doy += 1
541 changeDir_flag = True
542
543 file = None
544 filename = None
545 fileOk_flag = False
546
547 #busca el 1er file disponible
548 file, filename = checkForRealPath( self.__path, self.__year, self.__doy, self.__set, self.__ext )
549
550 if file == None:
551 if notFirstTime_flag: #si no es la primera vez que busca el file entonces no espera y busca for el siguiente file
552 print "\tsearching next \"%s\" file ..." % ( filename )
553 continue
554 else: #si es la primera vez que busca el file entonces espera self.__nTries veces hasta encontrarlo o no
555 for nTries in range( self.__nTries ):
556 print "\twaiting new \"%s\" file, try %03d ..." % ( filename, nTries+1 )
557 time.sleep( self.__delay )
558
559 file, filename = checkForRealPath( self.__path, self.__year, self.__doy, self.__set, self.__ext )
560 if file != None:
561 fileOk_flag = True
562 break
563
564 if not( fileOk_flag ): #no encontro ningun file valido a leer
565 notFirstTime_flag = True
566 continue
567
568
569 """countTries = 0
570
571 #espero hasta encontrar el 1er file disponible
572 while( True ):
573
574 countTries += 1
575 if( countTries >= self.__nTries ): #checkeo que no haya ido mas alla de la cantidad de intentos
576 break
577
578 file, filename = checkForRealPath( self.__path, self.__year, self.__doy, self.__set, self.__ext )
579 if file != None:
580 break
581
582 if notFirstTime_flag: #este flag me sirve solo para esperar por el 1er file, en lo siguientes no espera solo checkea si existe o no
583 countTries = self.__nTries
584 print "\tsearching next \"%s\" file ..." % filename
585 break
586
587 print "\twaiting new \"%s\" file ..." % filename
588 time.sleep( self.__delay )
589
590 if countTries >= self.__nTries: #se realizaron n intentos y no hubo un file nuevo
591 notFirstTime_flag = True
592 continue #vuelvo al inico del while principal
593 """
594
595 #una vez que se obtuvo el 1er file valido se procede a checkear si si tamanho es suficiente para empezar a leerlo
596 currentSize = os.path.getsize( file )
597 neededSize = self.m_ProcessingHeader.blockSize + self.firstHeaderSize
598
599 #si el tamanho es suficiente entonces deja de buscar
600 if currentSize > neededSize:
601 fileOk_flag = True
602 break
603
604 fileOk_flag = False
605 #si el file no tiene el tamanho necesario se espera una cierta cantidad de tiempo
606 #por una cierta cantidad de veces hasta que el contenido del file sea valido
607 if changeDir_flag: #si al buscar un file cambie de directorio ya no espero y sigo con el siguiente file
608 print "\tsearching next \"%s\" file ..." % filename
609 changeDir_flag = False
610 continue
611
612 for nTries in range( self.__nTries ):
613 print "\twaiting for the First Header block of \"%s\" file, try %03d ..." % ( filename, nTries+1 )
614 time.sleep( self.__delay )
615
616 currentSize = os.path.getsize( file )
617 neededSize = self.m_ProcessingHeader.blockSize + self.firstHeaderSize
618
619 if currentSize > neededSize:
620 fileOk_flag = True
621 break
622
623 if fileOk_flag: #si encontro un file valido sale del bucle y deja de buscar
624 break
625
626 print "Skipping the file \"%s\" due to this files is empty" % filename
627 countFiles = 0
628
629 if fileOk_flag:
630 self.fileSize = os.path.getsize( file ) #fileSize
631 self.filename = file#name
632 self.__flagIsNewFile = 1
633 self.__fp = open(file)
634 self.noMoreFiles = 0
635 print 'Setting the file: %s' % file #name
636 else:
637 self.fileSize = 0
638 self.filename = None
639 self.__fp = None
640 self.noMoreFiles = 1
641 print 'No more Files'
642
643 return fileOk_flag
644
645
646 def __setNextFileOffline( self ):
647 """
648 Busca el siguiente file dentro de un folder que tenga suficiente data para ser leida
649
650 Affected:
651 self.__flagIsNewFile
652 self.__idFile
653 self.filename
654 self.fileSize
655 self.__fp
656
657 Return:
658 0 : si un determinado file no puede ser abierto
659 1 : si el file fue abierto con exito
660
661 Excepciones:
662 Si un determinado file no puede ser abierto
663 """
664 idFile = self.__idFile
665 self.__flagIsNewFile = 0
666
667 while(True):
668 idFile += 1
669
670 if not( idFile < len(self.filenameList) ):
671 self.noMoreFiles = 1
672 print 'No more Files'
673 return 0
674
675 filename = self.filenameList[idFile]
676 fileSize = os.path.getsize(filename)
677
678 try:
679 fp = open( filename, 'rb' )
680 except:
681 raise IOError, "The file %s can't be opened" %filename
682
683 currentSize = fileSize - fp.tell()
684 neededSize = self.m_ProcessingHeader.blockSize + self.firstHeaderSize
685
686 if (currentSize < neededSize):
687 print "Skipping the file %s due to it hasn't enough data" %filename
688 fp.close()
689 continue
690
691 break
692
693 self.__flagIsNewFile = 1
694 self.__idFile = idFile
695 self.filename = filename
696 self.fileSize = fileSize
697 self.__fp = fp
698
699 print 'Setting the file: %s'%self.filename
185 self.pts2read_SelfSpectra = int( pts2read * self.nChannels )
186 self.pts2read_CrossSpectra = int( pts2read * self.nPairs )
187 self.pts2read_DCchannels = int( self.m_ProcessingHeader.numHeights * self.m_SystemHeader.numChannels )
700 188
701 return 1
702
703
704 def __setNextFile( self ):
705 """
706 Determina el siguiente file a leer y si hay uno disponible lee el First Header
707
708 Affected:
709 self.m_BasicHeader
710 self.m_SystemHeader
711 self.m_RadarControllerHeader
712 self.m_ProcessingHeader
713 self.firstHeaderSize
714
715 Return:
716 0 : Si no hay files disponibles
717 1 : Si hay mas files disponibles
718 """
719 if self.__fp != None:
720 self.__fp.close()
721
722 if self.online:
723 newFile = self.__setNextFileOnline()
724 else:
725 newFile = self.__setNextFileOffline()
726
727 if self.noMoreFiles:
728 sys.exit(0)
729
730 if not(newFile):
731 return 0
732
733 self.__readFirstHeader()
734 self.nBlocks = 0
735 return 1
736
737
738 def __setNewBlock(self):
739 """
740 Lee el Basic Header y posiciona le file pointer en la posicion inicial del bloque a leer
741
742 Affected:
743 self.m_BasicHeader
744 self.flagResetProcessing
745 self.ns
746
747 Return:
748 0 : Si el file no tiene un Basic Header que pueda ser leido
749 1 : Si se pudo leer el Basic Header
750 """
751 if self.__fp == None:
752 return 0
753
754 if self.__flagIsNewFile:
755 return 1
756
757 currentSize = self.fileSize - self.__fp.tell()
758 neededSize = self.m_ProcessingHeader.blockSize + self.basicHeaderSize
759
760 #If there is enough data setting new data block
761 if ( currentSize >= neededSize ):
762 self.__rdBasicHeader()
763 return 1
764
765 #si es OnLine y ademas aun no se han leido un bloque completo entonces se espera por uno valido
766 elif (self.nBlocks != self.m_ProcessingHeader.dataBlocksPerFile) and self.online:
767 for nTries in range( self.__nTries ):
768
769 fpointer = self.__fp.tell()
770 self.__fp.close()
771
772 print "\tWaiting for the next block, try %03d ..." % (nTries+1)
773 time.sleep( self.__delay )
774
775 self.__fp = open( self.filename, 'rb' )
776 self.__fp.seek( fpointer )
777
778 self.fileSize = os.path.getsize( self.filename )
779 currentSize = self.fileSize - self.__fp.tell()
780 neededSize = self.m_ProcessingHeader.blockSize + self.basicHeaderSize
781
782 if ( currentSize >= neededSize ):
783 self.__rdBasicHeader()
784 return 1
785
786 #Setting new file
787 if not( self.__setNextFile() ):
788 return 0
189 self.blocksize = self.pts2read_SelfSpectra + self.pts2read_CrossSpectra + self.pts2read_DCchannels
789 190
790 deltaTime = self.m_BasicHeader.utc - self.__lastUTTime # check this
791
792 self.flagResetProcessing = 0
793
794 if deltaTime > self.__maxTimeStep:
795 self.flagResetProcessing = 1
796 #self.nReadBlocks = 0
191 self.m_DataObj.nChannels = self.nChannels
192 self.m_DataObj.nPairs = self.nPairs
797 193
798 return 1
799
800
801 def __readBlock(self):
194 def readBlock(self):
802 195 """
803 196 Lee el bloque de datos desde la posicion actual del puntero del archivo
804 (self.__fp) y actualiza todos los parametros relacionados al bloque de datos
197 (self.fp) y actualiza todos los parametros relacionados al bloque de datos
805 198 (metadata + data). La data leida es almacenada en el buffer y el contador del buffer
806 199 es seteado a 0
807 200
808 201 Return: None
809 202
810 203 Variables afectadas:
811 self.__datablockIndex
812 self.__flagIsNewFile
204 self.datablockIndex
205 self.flagIsNewFile
813 206 self.flagIsNewBlock
814 207 self.nReadBlocks
815 self.__data_spc
816 self.__data_cspc
817 self.__data_dc
208 self.data_spc
209 self.data_cspc
210 self.data_dc
818 211
819 212 Exceptions:
820 213 Si un bloque leido no es un bloque valido
821 214 """
822 215 #self.datablock_id = 0
823 #self.__flagIsNewFile = 0
216 #self.flagIsNewFile = 0
824 217 #self.flagIsNewBlock = 1
825 218
826 219 blockOk_flag = False
827 fpointer = self.__fp.tell()
220 fpointer = self.fp.tell()
828 221
829 spc = numpy.fromfile( self.__fp, self.__dataType[0], self.__pts2read_SelfSpectra )
830 cspc = numpy.fromfile( self.__fp, self.__dataType, self.__pts2read_CrossSpectra )
831 dc = numpy.fromfile( self.__fp, self.__dataType, self.__pts2read_DCchannels ) #int(self.m_ProcessingHeader.numHeights*self.m_SystemHeader.numChannels) )
222 spc = numpy.fromfile( self.fp, self.dataType[0], self.pts2read_SelfSpectra )
223 cspc = numpy.fromfile( self.fp, self.dataType, self.pts2read_CrossSpectra )
224 dc = numpy.fromfile( self.fp, self.dataType, self.pts2read_DCchannels ) #int(self.m_ProcessingHeader.numHeights*self.m_SystemHeader.numChannels) )
832 225
833 226 if self.online:
834 if (spc.size + cspc.size + dc.size) != self.__blocksize:
835 for nTries in range( self.__nTries ):
227 if (spc.size + cspc.size + dc.size) != self.blocksize:
228 for nTries in range( self.nTries ):
836 229 #nTries = 0
837 #while( nTries < self.__nTries ):
230 #while( nTries < self.nTries ):
838 231 #nTries += 1
839 232 print "\tWaiting for the next block, try %03d ..." % (nTries+1)
840 time.sleep( self.__delay )
841 self.__fp.seek( fpointer )
842 fpointer = self.__fp.tell()
843 spc = numpy.fromfile( self.__fp, self.__dataType[0], self.__pts2read_SelfSpectra )
844 cspc = numpy.fromfile( self.__fp, self.__dataType, self.__pts2read_CrossSpectra )
845 dc = numpy.fromfile( self.__fp, self.__dataType, self.__pts2read_DCchannels ) #int(self.m_ProcessingHeader.numHeights*self.m_SystemHeader.numChannels) )
233 time.sleep( self.delay )
234 self.fp.seek( fpointer )
235 fpointer = self.fp.tell()
236 spc = numpy.fromfile( self.fp, self.dataType[0], self.pts2read_SelfSpectra )
237 cspc = numpy.fromfile( self.fp, self.dataType, self.pts2read_CrossSpectra )
238 dc = numpy.fromfile( self.fp, self.dataType, self.pts2read_DCchannels ) #int(self.m_ProcessingHeader.numHeights*self.m_SystemHeader.numChannels) )
846 239
847 if (spc.size + cspc.size + dc.size) == self.__blocksize:
240 if (spc.size + cspc.size + dc.size) == self.blocksize:
848 241 blockOk_flag = True
849 242 break
850 #if (spc.size + cspc.size + dc.size) == self.__blocksize:
243 #if (spc.size + cspc.size + dc.size) == self.blocksize:
851 244 # nTries = 0
852 245 # break
853 246 if not( blockOk_flag ):
854 247 return 0
855 248 #if nTries > 0:
856 249 # return 0
857 250
858 251 try:
859 252 spc = spc.reshape( (self.nChannels, self.m_ProcessingHeader.numHeights, self.m_ProcessingHeader.profilesPerBlock) ) #transforma a un arreglo 3D
860 253 cspc = cspc.reshape( (self.nPairs, self.m_ProcessingHeader.numHeights, self.m_ProcessingHeader.profilesPerBlock) ) #transforma a un arreglo 3D
861 254 dc = dc.reshape( (self.m_SystemHeader.numChannels, self.m_ProcessingHeader.numHeights) ) #transforma a un arreglo 2D
862 255 except:
863 256 print "Data file %s is invalid" % self.filename
864 257 return 0
865 258
866 259 if not( self.m_ProcessingHeader.shif_fft ):
867 260 spc = numpy.roll( spc, self.m_ProcessingHeader.profilesPerBlock/2, axis=2 ) #desplaza a la derecha en el eje 2 determinadas posiciones
868 261 cspc = numpy.roll( cspc, self.m_ProcessingHeader.profilesPerBlock/2, axis=2 ) #desplaza a la derecha en el eje 2 determinadas posiciones
869 262
870 263 spc = numpy.transpose( spc, (0,2,1) )
871 264 cspc = numpy.transpose( cspc, (0,2,1) )
872 265 #dc = numpy.transpose(dc, (0,2,1))
873 266
874 self.__data_spc = spc
875 self.__data_cspc = cspc['real'] + cspc['imag']*1j
876 self.__data_dc = dc['real'] + dc['imag']*1j
267 self.data_spc = spc
268 self.data_cspc = cspc['real'] + cspc['imag']*1j
269 self.data_dc = dc['real'] + dc['imag']*1j
877 270
878 271 self.datablock_id = 0
879 self.__flagIsNewFile = 0
272 self.flagIsNewFile = 0
880 273 self.flagIsNewBlock = 1
881 274
882 275 self.nReadBlocks += 1
883 276 self.nBlocks += 1
884 277
885 278 return 1
886
887
888 def __hasNotDataInBuffer(self):
889 #if self.datablock_id >= self.m_ProcessingHeader.profilesPerBlock:
890 return 1
891
892
893 def __searchFilesOnLine( self, path, startDateTime=None, ext = ".pdata" ):
894 """
895 Busca el ultimo archivo de la ultima carpeta (determinada o no por startDateTime) y
896 devuelve el archivo encontrado ademas de otros datos.
897
898 Input:
899 path : carpeta donde estan contenidos los files que contiene data
900 startDateTime : punto especifico en el tiempo del cual se requiere la data
901 ext : extension de los files
902
903 Return:
904 year : el anho
905 doy : el numero de dia del anho
906 set : el set del archivo
907 filename : el ultimo file de una determinada carpeta
908 directory : eL directorio donde esta el file encontrado
909 """
910 print "Searching files ..."
911
912 dirList = []
913 directory = None
914
915 if startDateTime == None:
916 for thisPath in os.listdir(path):
917 if os.path.isdir( os.path.join(path,thisPath) ):
918 dirList.append( thisPath )
919
920 dirList = sorted( dirList, key=str.lower ) #para que quede ordenado al margen de si el nombre esta en mayusculas o minusculas, utilizo la funcion sorted
921 if len(dirList) > 0 :
922 directory = dirList[-1] #me quedo con el ultimo directorio de una carpeta
923 else:
924 year = startDateTime.timetuple().tm_year
925 doy = startDateTime.timetuple().tm_yday
926
927 doyPath = "D%04d%03d" % (year,doy) #caso del nombre en mayusculas
928 if os.path.isdir( os.path.join(path,doyPath) ):
929 directory = doyPath
930
931 doyPath = doyPath.lower() #caso del nombre en minusculas
932 if os.path.isdir( os.path.join(path,doyPath) ):
933 directory = doyPath
934
935 if directory == None:
936 return 0, 0, 0, None, None
937
938 filename = getlastFileFromPath( os.listdir( os.path.join(path,directory) ), ext )
939
940 if filename == None:
941 return 0, 0, 0, None, None
942
943 year = int( directory[-7:-3] )
944 doy = int( directory[-3:] )
945 ln = len( ext )
946 set = int( filename[-ln-3:-ln] )
947
948 return year, doy, set, filename, directory
949
950
951 def __searchFilesOffLine( self, path, startDateTime, endDateTime, set=None, expLabel = "", ext = ".pdata" ):
952 """
953 Realiza una busqueda de los archivos que coincidan con los parametros
954 especificados y se encuentren ubicados en el path indicado. Para realizar una busqueda
955 correcta la estructura de directorios debe ser la siguiente:
956
957 ...path/D[yyyy][ddd]/expLabel/D[yyyy][ddd][sss].ext
958
959 [yyyy]: anio
960 [ddd] : dia del anio
961 [sss] : set del archivo
962
963 Inputs:
964 path : Directorio de datos donde se realizara la busqueda. Todos los
965 ficheros que concidan con el criterio de busqueda seran
966 almacenados en una lista y luego retornados.
967 startDateTime : Fecha inicial. Rechaza todos los archivos donde
968 file end time < startDateTime (objeto datetime.datetime)
969
970 endDateTime : Fecha final. Rechaza todos los archivos donde
971 file start time > endDateTime (obejto datetime.datetime)
972
973 set : Set del primer archivo a leer. Por defecto None
974
975 expLabel : Nombre del subdirectorio de datos. Por defecto ""
976
977 ext : Extension de los archivos a leer. Por defecto .r
978
979 Return:
980
981 (pathList, filenameList)
982
983 pathList : Lista de directorios donde se encontraron archivos dentro
984 de los parametros especificados
985 filenameList : Lista de archivos (ruta completa) que coincidieron con los
986 parametros especificados.
987
988 Variables afectadas:
989
990 self.filenameList: Lista de archivos (ruta completa) que la clase utiliza
991 como fuente para leer los bloque de datos, si se termina
992 de leer todos los bloques de datos de un determinado
993 archivo se pasa al siguiente archivo de la lista.
994 """
995 print "Searching files ..."
996
997 dirList = []
998 for thisPath in os.listdir(path):
999 if os.path.isdir(os.path.join(path,thisPath)):
1000 dirList.append(thisPath)
1001
1002 pathList = []
1003
1004 thisDateTime = startDateTime
1005
1006 while(thisDateTime <= endDateTime):
1007 year = thisDateTime.timetuple().tm_year
1008 doy = thisDateTime.timetuple().tm_yday
1009
1010 match = fnmatch.filter(dirList, '?' + '%4.4d%3.3d' % (year,doy))
1011 if len(match) == 0:
1012 thisDateTime += datetime.timedelta(1)
1013 continue
1014
1015 pathList.append(os.path.join(path,match[0],expLabel))
1016 thisDateTime += datetime.timedelta(1)
1017
1018 startUtSeconds = time.mktime(startDateTime.timetuple())
1019 endUtSeconds = time.mktime(endDateTime.timetuple())
1020
1021 filenameList = []
1022 for thisPath in pathList:
1023 fileList = glob.glob1(thisPath, "*%s" %ext)
1024 fileList.sort()
1025 for file in fileList:
1026 filename = os.path.join(thisPath,file)
1027 if isThisFileinRange(filename, startUtSeconds, endUtSeconds):
1028 filenameList.append(filename)
1029
1030 self.filenameList = filenameList
1031
1032 return pathList, filenameList
1033
1034
1035 def __initFilesOnline( self, path, dirfilename, filename ):
1036 """
1037 Verifica que el primer file tenga una data valida, para ello leo el 1er bloque
1038 del file, si no es un file valido espera una cierta cantidad de tiempo a que
1039 lo sea, si transcurrido el tiempo no logra validar el file entonces el metodo
1040 devuelve 0 caso contrario devuelve 1
1041
1042 Affected:
1043 m_BasicHeader
1044
1045 Return:
1046 0 : file no valido para ser leido
1047 1 : file valido para ser leido
1048 """
1049 m_BasicHeader = BasicHeader()
1050
1051 file = os.path.join( path, dirfilename, filename )
1052
1053 for nTries in range( self.__nTries+1 ):
1054 try:
1055 fp = open( file,'rb' ) #lectura binaria
1056 except:
1057 raise IOError, "The file %s can't be opened" %(file)
1058
1059 try:
1060 m_BasicHeader.read(fp)
1061 except:
1062 print "The file %s is empty" % filename
1063
1064 fp.close()
1065
1066 if m_BasicHeader.size > 24:
1067 break
1068
1069 if nTries >= self.__nTries: #si ya espero la cantidad de veces necesarias entonces ya no vuelve a esperar
1070 break
1071
1072 print '\twaiting for new block of file %s: try %02d' % ( file, nTries )
1073 time.sleep( self.__delay)
1074
1075 if m_BasicHeader.size <= 24:
1076 return 0
1077
1078 return 1
1079
1080
1081 def setup( self, path, startDateTime=None, endDateTime=None, set=None, expLabel = "", ext = ".pdata", online = 0 ):
1082 """
1083 setup configura los parametros de lectura de la clase SpectraReader.
1084
1085 Si el modo de lectura es offline, primero se realiza una busqueda de todos los archivos
1086 que coincidan con los parametros especificados; esta lista de archivos son almacenados en
1087 self.filenameList.
1088
1089 Input:
1090 path : Directorios donde se ubican los datos a leer. Dentro de este
1091 directorio deberia de estar subdirectorios de la forma:
1092
1093 path/D[yyyy][ddd]/expLabel/P[yyyy][ddd][sss][ext]
1094
1095 startDateTime : Fecha inicial. Rechaza todos los archivos donde
1096 file end time < startDatetime (objeto datetime.datetime)
1097
1098 endDateTime : Fecha final. Si no es None, rechaza todos los archivos donde
1099 file end time < startDatetime (objeto datetime.datetime)
1100
1101 set : Set del primer archivo a leer. Por defecto None
1102
1103 expLabel : Nombre del subdirectorio de datos. Por defecto ""
1104
1105 ext : Extension de los archivos a leer. Por defecto .pdata
1106
1107 online : Si es == a 0 entonces busca files que cumplan con las condiciones dadas
1108
1109 Return:
1110 0 : Si no encuentra files que cumplan con las condiciones dadas
1111 1 : Si encuentra files que cumplan con las condiciones dadas
1112
1113 Affected:
1114 self.startUTCSeconds
1115 self.endUTCSeconds
1116 self.startYear
1117 self.endYear
1118 self.startDoy
1119 self.endDoy
1120 self.__pathList
1121 self.filenameList
1122 self.online
1123 """
1124 if online:
1125 fileOK_flag = False
1126 subfolder = "D%04d%03d" % ( startDateTime.timetuple().tm_year, startDateTime.timetuple().tm_yday )
1127 file = os.path.join( path, subfolder )
1128
1129 for nTries in range( self.__nTries+1 ): #espera por el 1er file
1130 year, doy, set, filename, dirfilename = self.__searchFilesOnLine( path, startDateTime, ext )
1131
1132 if filename != None:
1133 if isFileOK( os.path.join( path,dirfilename,filename ) ):
1134 fileOK_flag = True
1135 break
1136
1137 if nTries >= self.__nTries: #si ya espero la cantidad de veces necesarias entonces ya no vuelve a esperar
1138 break
1139
1140 print "Searching first file in \"%s\", try %03d ..." % ( file, nTries+1 )
1141 time.sleep( self.__delay )
1142
1143 if not( fileOK_flag ): #filename == None:
1144 print "No files on line or invalid first file"
1145 return 0
1146
1147 if self.__initFilesOnline( path, dirfilename, filename ) == 0:
1148 print "The file %s hasn't enough data" % filename
1149 return 0
1150
1151 self.__year = year
1152 self.__doy = doy
1153 self.__set = set - 1
1154 self.__path = path
1155
1156 else:
1157 pathList, filenameList = self.__searchFilesOffLine( path, startDateTime, endDateTime, set, expLabel, ext )
1158 self.__idFile = -1
1159 self.__pathList = pathList
1160 self.filenameList = filenameList
1161
1162 self.online = online
1163 self.__ext = ext
1164
1165 if not( self.__setNextFile() ):
1166 if (startDateTime != None) and (endDateTime != None):
1167 print "No files in range: %s - %s" %(startDateTime.ctime(), endDateTime.ctime())
1168 elif startDateTime != None:
1169 print "No files in : %s" % startDateTime.ctime()
1170 else:
1171 print "No files"
1172 return 0
1173
1174 if startDateTime != None:
1175 self.startUTCSeconds = time.mktime(startDateTime.timetuple())
1176 self.startYear = startDateTime.timetuple().tm_year
1177 self.startDoy = startDateTime.timetuple().tm_yday
1178
1179 if endDateTime != None:
1180 self.endUTCSeconds = time.mktime(endDateTime.timetuple())
1181 self.endYear = endDateTime.timetuple().tm_year
1182 self.endDoy = endDateTime.timetuple().tm_yday
1183 #call fillHeaderValues() - to Data Object
1184
1185 self.m_Spectra.m_BasicHeader = self.m_BasicHeader.copy()
1186 self.m_Spectra.m_ProcessingHeader = self.m_ProcessingHeader.copy()
1187 self.m_Spectra.m_RadarControllerHeader = self.m_RadarControllerHeader.copy()
1188 self.m_Spectra.m_SystemHeader = self.m_SystemHeader.copy()
1189 self.m_Spectra.dataType = self.__dataType
1190
1191 return 1
1192 279
1193
1194 def readNextBlock( self ):
1195 """
1196 Establece un nuevo bloque de datos a leer y los lee, si es que no existiese
1197 mas bloques disponibles en el archivo actual salta al siguiente.
1198
1199 Affected:
1200 self.__lastUTTime
1201
1202 Return: None
1203 """
1204
1205 if not( self.__setNewBlock() ):
1206 return 0
1207
1208 if not( self.__readBlock() ):
1209 return 0
1210
1211 self.__lastUTTime = self.m_BasicHeader.utc
1212
1213 return 1
1214
1215
1216 280 def getData(self):
1217 281 """
1218 282 Copia el buffer de lectura a la clase "Spectra",
1219 283 con todos los parametros asociados a este (metadata). cuando no hay datos en el buffer de
1220 284 lectura es necesario hacer una nueva lectura de los bloques de datos usando "readNextBlock"
1221 285
1222 286 Return:
1223 287 0 : Si no hay mas archivos disponibles
1224 288 1 : Si hizo una buena copia del buffer
1225 289
1226 290 Affected:
1227 self.m_Spectra
1228 self.__datablockIndex
291 self.m_DataObj
292 self.datablockIndex
1229 293 self.flagResetProcessing
1230 294 self.flagIsNewBlock
1231 295 """
1232 296
1233 297 self.flagResetProcessing = 0
1234 298 self.flagIsNewBlock = 0
1235 299
1236 if self.__hasNotDataInBuffer():
300 if self.hasNotDataInBuffer():
1237 301
1238 302 if not( self.readNextBlock() ):
1239 self.__setNextFile()
303 self.setNextFile()
1240 304 return 0
1241 305
1242 self.m_Spectra.m_BasicHeader = self.m_BasicHeader.copy()
1243 self.m_Spectra.m_ProcessingHeader = self.m_ProcessingHeader.copy()
1244 self.m_Spectra.m_RadarControllerHeader = self.m_RadarControllerHeader.copy()
1245 self.m_Spectra.m_SystemHeader = self.m_SystemHeader.copy()
1246 self.m_Spectra.heights = self.__heights
1247 self.m_Spectra.dataType = self.__dataType
306 self.m_DataObj.m_BasicHeader = self.m_BasicHeader.copy()
307 self.m_DataObj.m_ProcessingHeader = self.m_ProcessingHeader.copy()
308 self.m_DataObj.m_RadarControllerHeader = self.m_RadarControllerHeader.copy()
309 self.m_DataObj.m_SystemHeader = self.m_SystemHeader.copy()
310 self.m_DataObj.heights = self.heights
311 self.m_DataObj.dataType = self.dataType
1248 312
1249 313 if self.noMoreFiles == 1:
1250 314 print 'Process finished'
1251 315 return 0
1252 316
1253 317 #data es un numpy array de 3 dmensiones (perfiles, alturas y canales)
1254 318
1255 if self.__data_dc == None:
319 if self.data_dc == None:
1256 320 self.m_Voltage.flagNoData = True
1257 321 return 0
1258 322
1259 self.m_Spectra.flagNoData = False
1260 self.m_Spectra.flagResetProcessing = self.flagResetProcessing
323 self.m_DataObj.flagNoData = False
324 self.m_DataObj.flagResetProcessing = self.flagResetProcessing
1261 325
1262 self.m_Spectra.data_spc = self.__data_spc
1263 self.m_Spectra.data_cspc = self.__data_cspc
1264 self.m_Spectra.data_dc = self.__data_dc
326 self.m_DataObj.data_spc = self.data_spc
327 self.m_DataObj.data_cspc = self.data_cspc
328 self.m_DataObj.data_dc = self.data_dc
1265 329
1266 330 #call setData - to Data Object
1267 331 #self.datablock_id += 1
1268 332 #self.idProfile += 1
1269 333
1270 334 return 1
1271 335
1272 336 class SpectraWriter( JRODataWriter ):
1273 337 """
1274 338 Esta clase permite escribir datos de espectros a archivos procesados (.pdata). La escritura
1275 339 de los datos siempre se realiza por bloques.
1276 340 """
1277 341
1278 342 def __init__(self,m_Spectra=None):
1279 343 """
1280 344 Inicializador de la clase SpectraWriter para la escritura de datos de espectros.
1281 345
1282 346 Affected:
1283 self.m_Spectra
347 self.m_DataObj
1284 348 self.m_BasicHeader
1285 349 self.m_SystemHeader
1286 350 self.m_RadarControllerHeader
1287 351 self.m_ProcessingHeader
1288 352
1289 353 Return: None
1290 354 """
1291 355
1292 356 if m_Spectra == None:
1293 357 m_Spectra = Spectra()
1294 358
1295 self.m_Spectra = m_Spectra
1296
1297 self.__path = None
359 self.m_DataObj = m_Spectra
1298 360
1299 self.__fp = None
361 self.fp = None
1300 362
1301 self.__format = None
363 self.format = None
1302 364
1303 self.__blocksCounter = 0
365 self.blocksCounter = 0
1304 366
1305 self.__setFile = None
367 self.setFile = None
1306 368
1307 self.__flagIsNewFile = 1
369 self.flagIsNewFile = 1
1308 370
1309 self.__dataType = None
371 self.dataType = None
1310 372
1311 self.__ext = None
373 self.ext = ".pdata"
1312 374
1313 self.__shape_spc_Buffer = None
1314 self.__shape_cspc_Buffer = None
1315 self.__shape_dc_Buffer = None
375 self.path = None
376
377 self.optchar = "P"
378
379 self.shape_spc_Buffer = None
380 self.shape_cspc_Buffer = None
381 self.shape_dc_Buffer = None
1316 382
1317 383 self.nWriteBlocks = 0
1318 384
1319 385 self.flagIsNewBlock = 0
1320 386
1321 387 self.noMoreFiles = 0
1322 388
1323 389 self.filename = None
1324 390
1325 391 self.m_BasicHeader= BasicHeader()
1326 392
1327 393 self.m_SystemHeader = SystemHeader()
1328 394
1329 395 self.m_RadarControllerHeader = RadarControllerHeader()
1330 396
1331 397 self.m_ProcessingHeader = ProcessingHeader()
1332 398
1333 self.__data_spc = None
1334 self.__data_cspc = None
1335 self.__data_dc = None
1336
1337 def __writeFirstHeader(self):
1338 """
1339 Escribe el primer header del file es decir el Basic header y el Long header (SystemHeader, RadarControllerHeader, ProcessingHeader)
1340
1341 Affected:
1342 __dataType
1343
1344 Return:
1345 None
1346 """
1347 self.__writeBasicHeader()
1348 self.__wrSystemHeader()
1349 self.__wrRadarControllerHeader()
1350 self.__wrProcessingHeader()
1351 self.__dataType = self.m_Spectra.dataType
1352
1353
1354 def __writeBasicHeader(self, fp=None):
1355 """
1356 Escribe solo el Basic header en el file creado
1357
1358 Return:
1359 None
1360 """
1361 if fp == None:
1362 fp = self.__fp
1363
1364 self.m_BasicHeader.write(fp)
1365
1366
1367 def __wrSystemHeader(self,fp=None):
1368 """
1369 Escribe solo el System header en el file creado
1370
1371 Return:
1372 None
1373 """
1374 if fp == None:
1375 fp = self.__fp
1376
1377 self.m_SystemHeader.write(fp)
1378
1379
1380 def __wrRadarControllerHeader(self,fp=None):
1381 """
1382 Escribe solo el RadarController header en el file creado
1383
1384 Return:
1385 None
1386 """
1387 if fp == None:
1388 fp = self.__fp
1389
1390 self.m_RadarControllerHeader.write(fp)
1391
1392
1393 def __wrProcessingHeader(self,fp=None):
1394 """
1395 Escribe solo el Processing header en el file creado
1396
1397 Return:
1398 None
1399 """
1400 if fp == None:
1401 fp = self.__fp
1402
1403 self.m_ProcessingHeader.write(fp)
399 self.data_spc = None
400 self.data_cspc = None
401 self.data_dc = None
1404 402
403 def hasAllDataInBuffer(self):
404 return 1
1405 405
1406 def __setNextFile(self):
1407 """
1408 Determina el siguiente file que sera escrito
406 def setBlockDimension(self):
1409 407
1410 Affected:
1411 self.filename
1412 self.__subfolder
1413 self.__fp
1414 self.__setFile
1415 self.__flagIsNewFile
408 self.shape_spc_Buffer = (self.m_DataObj.nChannels,
409 self.m_ProcessingHeader.numHeights,
410 self.m_ProcessingHeader.profilesPerBlock)
1416 411
1417 Return:
1418 0 : Si el archivo no puede ser escrito
1419 1 : Si el archivo esta listo para ser escrito
1420 """
1421 ext = self.__ext
1422 path = self.__path
412 self.shape_cspc_Buffer = (self.m_DataObj.nPairs,
413 self.m_ProcessingHeader.numHeights,
414 self.m_ProcessingHeader.profilesPerBlock)
1423 415
1424 if self.__fp != None:
1425 self.__fp.close()
1426
1427 #if self.m_BasicHeader.size <= 24: return 0 #no existe la suficiente data para ser escrita
1428
1429 timeTuple = time.localtime(self.m_Spectra.m_BasicHeader.utc) # utc from m_Spectra
1430 subfolder = 'D%4.4d%3.3d' % (timeTuple.tm_year,timeTuple.tm_yday)
416 self.shape_dc_Buffer = (self.m_SystemHeader.numChannels,
417 self.m_ProcessingHeader.numHeights)
1431 418
1432 tmp = os.path.join( path, subfolder )
1433 if not( os.path.exists(tmp) ):
1434 os.mkdir(tmp)
1435 self.__setFile = -1 #inicializo mi contador de seteo
1436 else:
1437 filesList = os.listdir( tmp )
1438 if len( filesList ) > 0:
1439 filesList = sorted( filesList, key=str.lower )
1440 filen = filesList[-1]
1441 # el filename debera tener el siguiente formato
1442 # 0 1234 567 89A BCDE (hex)
1443 # P YYYY DDD SSS .ext
1444 if isNumber( filen[8:11] ):
1445 self.__setFile = int( filen[8:11] ) #inicializo mi contador de seteo al seteo del ultimo file
1446 else:
1447 self.__setFile = -1
1448 else:
1449 self.__setFile = -1 #inicializo mi contador de seteo
1450
1451 setFile = self.__setFile
1452 setFile += 1
1453 file = 'P%4.4d%3.3d%3.3d%s' % ( timeTuple.tm_year, timeTuple.tm_yday, setFile, ext )
1454
1455 filename = os.path.join( path, subfolder, file )
1456
1457 fp = open(filename,'wb')
1458
1459 self.__blocksCounter = 0
1460
1461 #guardando atributos
1462 self.filename = filename
1463 self.__subfolder = subfolder
1464 self.__fp = fp
1465 self.__setFile = setFile
1466 self.__flagIsNewFile = 1
1467
1468 print 'Writing the file: %s'%self.filename
1469
1470 self.__writeFirstHeader()
1471
1472 return 1
1473
1474
1475 def __setNewBlock(self):
1476 """
1477 Si es un nuevo file escribe el First Header caso contrario escribe solo el Basic Header
1478
1479 Return:
1480 0 : si no pudo escribir nada
1481 1 : Si escribio el Basic el First Header
1482 """
1483 if self.__fp == None:
1484 self.__setNextFile()
1485
1486 if self.__flagIsNewFile:
1487 return 1
1488
1489 if self.__blocksCounter < self.m_ProcessingHeader.dataBlocksPerFile:
1490 self.__writeBasicHeader()
1491 return 1
1492
1493 if not( self.__setNextFile() ):
1494 return 0
1495
1496 return 1
1497
1498 419
1499 def __writeBlock(self):
420 def writeBlock(self):
1500 421 """
1501 422 Escribe el buffer en el file designado
1502 423
1503 424 Affected:
1504 self.__data_spc
1505 self.__data_cspc
1506 self.__data_dc
1507 self.__flagIsNewFile
425 self.data_spc
426 self.data_cspc
427 self.data_dc
428 self.flagIsNewFile
1508 429 self.flagIsNewBlock
1509 430 self.nWriteBlocks
1510 self.__blocksCounter
431 self.blocksCounter
1511 432
1512 433 Return: None
1513 434 """
1514 spc = numpy.transpose( self.__data_spc, (0,2,1) )
435 spc = numpy.transpose( self.data_spc, (0,2,1) )
1515 436 if not( self.m_ProcessingHeader.shif_fft ):
1516 437 spc = numpy.roll( spc, self.m_ProcessingHeader.profilesPerBlock/2, axis=2 ) #desplaza a la derecha en el eje 2 determinadas posiciones
1517 438 data = spc.reshape((-1))
1518 data.tofile(self.__fp)
439 data.tofile(self.fp)
1519 440
1520 data = numpy.zeros( self.__shape_cspc_Buffer, self.__dataType )
1521 cspc = numpy.transpose( self.__data_cspc, (0,2,1) )
441 data = numpy.zeros( self.shape_cspc_Buffer, self.dataType )
442 cspc = numpy.transpose( self.data_cspc, (0,2,1) )
1522 443 if not( self.m_ProcessingHeader.shif_fft ):
1523 444 cspc = numpy.roll( cspc, self.m_ProcessingHeader.profilesPerBlock/2, axis=2 ) #desplaza a la derecha en el eje 2 determinadas posiciones
1524 445 data['real'] = cspc.real
1525 446 data['imag'] = cspc.imag
1526 447 data = data.reshape((-1))
1527 data.tofile(self.__fp)
448 data.tofile(self.fp)
1528 449
1529 data = numpy.zeros( self.__shape_dc_Buffer, self.__dataType )
1530 dc = self.__data_dc
450 data = numpy.zeros( self.shape_dc_Buffer, self.dataType )
451 dc = self.data_dc
1531 452 data['real'] = dc.real
1532 453 data['imag'] = dc.imag
1533 454 data = data.reshape((-1))
1534 data.tofile(self.__fp)
455 data.tofile(self.fp)
1535 456
1536 self.__data_spc.fill(0)
1537 self.__data_cspc.fill(0)
1538 self.__data_dc.fill(0)
457 self.data_spc.fill(0)
458 self.data_cspc.fill(0)
459 self.data_dc.fill(0)
1539 460
1540 self.__flagIsNewFile = 0
461 self.flagIsNewFile = 0
1541 462 self.flagIsNewBlock = 1
1542 463 self.nWriteBlocks += 1
1543 self.__blocksCounter += 1
1544
1545
1546 def writeNextBlock(self):
1547 """
1548 Selecciona el bloque siguiente de datos y los escribe en un file
1549
1550 Return:
1551 0 : Si no hizo pudo escribir el bloque de datos
1552 1 : Si no pudo escribir el bloque de datos
1553 """
1554 if not( self.__setNewBlock() ):
1555 return 0
464 self.blocksCounter += 1
1556 465
1557 self.__writeBlock()
1558 return 1
1559
1560
1561 def __hasAllDataInBuffer(self):
1562 return 1
1563
1564
1565 466 def putData(self):
1566 467 """
1567 468 Setea un bloque de datos y luego los escribe en un file
1568 469
1569 470 Affected:
1570 self.__data_spc
1571 self.__data_cspc
1572 self.__data_dc
471 self.data_spc
472 self.data_cspc
473 self.data_dc
1573 474
1574 475 Return:
1575 476 0 : Si no hay data o no hay mas files que puedan escribirse
1576 477 1 : Si se escribio la data de un bloque en un file
1577 478 """
1578 479 self.flagIsNewBlock = 0
1579 480
1580 if self.m_Spectra.flagNoData:
481 if self.m_DataObj.flagNoData:
1581 482 return 0
1582 483
1583 if self.m_Spectra.flagResetProcessing:
1584 self.__data_spc.fill(0)
1585 self.__data_cspc.fill(0)
1586 self.__data_dc.fill(0)
1587 self.__setNextFile()
484 if self.m_DataObj.flagResetProcessing:
485 self.data_spc.fill(0)
486 self.data_cspc.fill(0)
487 self.data_dc.fill(0)
488 self.setNextFile()
1588 489
1589 self.__data_spc = self.m_Spectra.data_spc
1590 self.__data_cspc = self.m_Spectra.data_cspc
1591 self.__data_dc = self.m_Spectra.data_dc
490 self.data_spc = self.m_DataObj.data_spc
491 self.data_cspc = self.m_DataObj.data_cspc
492 self.data_dc = self.m_DataObj.data_dc
1592 493
1593 494 if True:
1594 self.__getHeader()
495 self.getHeader()
1595 496 self.writeNextBlock()
1596 497
1597 498 if self.noMoreFiles:
1598 499 #print 'Process finished'
1599 500 return 0
1600 501
1601 return 1
1602
1603 def __getHeader(self):
1604 """
1605 Obtiene una copia del First Header
1606
1607 Affected:
1608 self.m_BasicHeader
1609 self.m_SystemHeader
1610 self.m_RadarControllerHeader
1611 self.m_ProcessingHeader
1612 self.__dataType
1613
1614 Return:
1615 None
1616 """
1617 self.m_BasicHeader = self.m_Spectra.m_BasicHeader.copy()
1618 self.m_SystemHeader = self.m_Spectra.m_SystemHeader.copy()
1619 self.m_RadarControllerHeader = self.m_Spectra.m_RadarControllerHeader.copy()
1620 self.m_ProcessingHeader = self.m_Spectra.m_ProcessingHeader.copy()
1621 self.__dataType = self.m_Spectra.dataType
1622
1623
1624 def __setHeaderByFile(self):
1625
1626 format = self.__format
1627 header = ['Basic','System','RadarController','Processing']
1628
1629 fmtFromFile = None
1630 headerFromFile = None
1631
1632
1633 fileTable = self.__configHeaderFile
1634
1635 if os.access(fileTable, os.R_OK):
1636 import re, string
1637
1638 f = open(fileTable,'r')
1639 lines = f.read()
1640 f.close()
1641
1642 #Delete comments into expConfig
1643 while 1:
1644
1645 startComment = string.find(lines.lower(),'#')
1646 if startComment == -1:
1647 break
1648 endComment = string.find(lines.lower(),'\n',startComment)
1649 lines = string.replace(lines,lines[startComment:endComment+1],'', 1)
1650
1651 while expFromFile == None:
1652
1653 currFmt = string.find(lines.lower(),'format="%s"' %(expName))
1654 nextFmt = string.find(lines.lower(),'format',currFmt+10)
1655
1656 if currFmt == -1:
1657 break
1658 if nextFmt == -1:
1659 nextFmt = len(lines)-1
1660
1661 fmtTable = lines[currFmt:nextFmt]
1662 lines = lines[nextFmt:]
1663
1664 fmtRead = self.__getValueFromArg(fmtTable,'format')
1665 if fmtRead != format:
1666 continue
1667 fmtFromFile = fmtRead
1668
1669 lines2 = fmtTable
1670
1671 while headerFromFile == None:
1672
1673 currHeader = string.find(lines2.lower(),'header="%s"' %(header))
1674 nextHeader = string.find(lines2.lower(),'header',currHeader+10)
1675
1676 if currHeader == -1:
1677 break
1678 if nextHeader == -1:
1679 nextHeader = len(lines2)-1
1680
1681 headerTable = lines2[currHeader:nextHeader]
1682 lines2 = lines2[nextHeader:]
1683
1684 headerRead = self.__getValueFromArg(headerTable,'site')
1685 if not(headerRead in header):
1686 continue
1687 headerFromFile = headerRead
1688
1689 if headerRead == 'Basic':
1690 self.m_BasicHeader.size = self.__getValueFromArg(headerTable,'size',lower=False)
1691 self.m_BasicHeader.version = self.__getValueFromArg(headerTable,'version',lower=False)
1692 self.m_BasicHeader.dataBlock = self.__getValueFromArg(headerTable,'dataBlock',lower=False)
1693 self.m_BasicHeader.utc = self.__getValueFromArg(headerTable,'utc',lower=False)
1694 self.m_BasicHeader.miliSecond = self.__getValueFromArg(headerTable,'miliSecond',lower=False)
1695 self.m_BasicHeader.timeZone = self.__getValueFromArg(headerTable,'timeZone',lower=False)
1696 self.m_BasicHeader.dstFlag = self.__getValueFromArg(headerTable,'dstFlag',lower=False)
1697 self.m_BasicHeader.errorCount = self.__getValueFromArg(headerTable,'errorCount',lower=False)
1698
1699 else:
1700 print "file access denied:%s"%fileTable
1701 sys.exit(0)
1702
1703
1704 def setup(self,path,format='pdata'):
1705 """
1706 Setea el tipo de formato en la cual sera guardada la data y escribe el First Header
1707
1708 Inputs:
1709 path : el path destino en el cual se escribiran los files a crear
1710 format : formato en el cual sera salvado un file
1711
1712 Return:
1713 0 : Si no realizo un buen seteo
1714 1 : Si realizo un buen seteo
1715 """
1716 if format == 'hdf5':
1717 ext = '.hdf5'
1718 format = 'hdf5'
1719 print 'call hdf5 library'
1720 return 0
1721
1722 if format == 'rawdata':
1723 ext = '.r'
1724 format = 'Jicamarca'
1725
1726 if format == 'pdata':
1727 ext = '.pdata'
1728 format = 'pdata'
1729
1730 #call to config_headers
1731 #self.__setHeaderByFile()
1732
1733 self.__path = path
1734 self.__setFile = -1
1735 self.__ext = ext
1736 self.__format = format
1737
1738 self.__getHeader()
1739
1740 self.__shape_spc_Buffer = ( self.m_Spectra.nChannels,
1741 self.m_ProcessingHeader.numHeights,
1742 self.m_ProcessingHeader.profilesPerBlock
1743 )
1744
1745 self.__shape_cspc_Buffer = ( self.m_Spectra.nPairs,
1746 self.m_ProcessingHeader.numHeights,
1747 self.m_ProcessingHeader.profilesPerBlock
1748 )
1749
1750 self.__shape_dc_Buffer = ( self.m_SystemHeader.numChannels,
1751 self.m_ProcessingHeader.numHeights
1752 )
1753
1754 if not( self.__setNextFile() ):
1755 print "There isn't a next file" #"zzzzzzzzzzzz"
1756 return 0
1757
1758 502 return 1 No newline at end of file
This diff has been collapsed as it changes many lines, (1391 lines changed) Show them Hide them
@@ -1,1631 +1,464
1 1 '''
2 2 Created on 23/01/2012
3 3
4 4 @author $Author$
5 5 @version $Id$
6 6 '''
7 7
8 8 import os, sys
9 9 import numpy
10 10 import glob
11 11 import fnmatch
12 12 import time, datetime
13 13
14 14 path = os.path.split(os.getcwd())[0]
15 15 sys.path.append(path)
16 16
17 17 from Model.JROHeader import *
18 18 from Model.Voltage import Voltage
19 19
20 20 from IO.DataIO import JRODataReader
21 21 from IO.DataIO import JRODataWriter
22 22
23 def isFileOK(filename):
24 """
25 Determina si la cabecera de un archivo es valido o no, si lo es entonces seria un archivo que podria contener data,
26 si no seria un archivo invalido
27
28 Return:
29 True : si es un archivo valido
30 False : si no es un archivo valido
31
32 Exceptions:
33 Si al leer la cabecera esta no coincide con el tipo de las variables que la contienen entonces se dispara
34 una exception
35 """
36 m_BasicHeader = BasicHeader()
37 m_ProcessingHeader = ProcessingHeader()
38 m_RadarControllerHeader = RadarControllerHeader()
39 m_SystemHeader = SystemHeader()
40 fp = None
41
42 try:
43 fp = open( filename,'rb' ) #lectura binaria
44 m_BasicHeader.read(fp)
45 m_SystemHeader.read(fp)
46 m_RadarControllerHeader.read(fp)
47 m_ProcessingHeader.read(fp)
48 fp.close()
49 except:
50 if fp != None: fp.close()
51 return False
52
53 return True
54
55
56 def getlastFileFromPath(pathList,ext):
57 """
58 Depura el pathList dejando solo los que cumplan el formato de "PYYYYDDDSSS.ext"
59 al final de la depuracion devuelve el ultimo file de la lista que quedo.
60
61 Input:
62 pathList : lista conteniendo todos los filename completos que componen una determinada carpeta
63 ext : extension de los files contenidos en una carpeta
64
65 Return:
66 El ultimo file de una determinada carpeta
67 """
68
69 filesList = []
70 filename = None
71
72 # 0 1234 567 89A BCDE
73 # D YYYY DDD SSS .ext
74
75 for filename in pathList:
76 year = filename[1:5]
77 doy = filename[5:8]
78 leng = len( ext )
79
80 if ( filename[-leng:].upper() != ext.upper() ) : continue
81 if not( isNumber( year ) ) : continue
82 if not( isNumber( doy ) ) : continue
83
84 filesList.append(filename)
85
86 if len( filesList ) > 0:
87 filesList = sorted( filesList, key=str.lower )
88 filename = filesList[-1]
89
90 return filename
91
92
93 def checkForRealPath(path,year,doy,set,ext):
94 """
95 Por ser Linux Case Sensitive la funcion checkForRealPath encuentra el nombre correcto de un path,
96 Prueba por varias combinaciones de nombres entre mayusculas y minusculas para determinar
97 el path exacto de un determinado file.
98
99 Example :
100 nombre correcto del file es ../RAWDATA/D2009307/P2009307367
101
102 Entonces la funcion prueba con las siguientes combinaciones
103 ../.../d2009307/d2009307367
104 ../.../d2009307/D2009307367
105 ../.../D2009307/d2009307367
106 ../.../D2009307/D2009307367
107 siendo para este caso, la ultima combinacion de letras, identica al file buscado
108
109 Return:
110 Si encuentra la combinacion adecuada devuelve el path completo y el nombre del file
111 caso contrario devuelve None como path y el la ultima combinacion de nombre en mayusculas
112 para el filename
113 """
114 filepath = None
115 find_flag = False
116 filename = None
117
118 for dir in "dD": #barrido por las dos combinaciones posibles de "D"
119 for fil in "dD": #barrido por las dos combinaciones posibles de "D"
120 doypath = "%s%04d%03d" % ( dir, year, doy ) #formo el nombre del directorio xYYYYDDD (x=d o x=D)
121 filename = "%s%04d%03d%03d%s" % ( fil, year, doy, set, ext ) #formo el nombre del file xYYYYDDDSSS.ext (p=d o p=D)
122 filepath = os.path.join( path, doypath, filename ) #formo el path completo
123 if os.path.exists( filepath ): #verifico que exista
124 find_flag = True
125 break
126 if find_flag:
127 break
128
129 if not(find_flag):
130 return None, filename
131
132 return filepath, filename
133
134
135 def isNumber(str):
136 """
137 Chequea si el conjunto de caracteres que componen un string puede ser convertidos a un numero.
138
139 Excepciones:
140 Si un determinado string no puede ser convertido a numero
141 Input:
142 str, string al cual se le analiza para determinar si convertible a un numero o no
143
144 Return:
145 True : si el string es uno numerico
146 False : no es un string numerico
147 """
148 try:
149 float( str )
150 return True
151 except:
152 return False
153
154
155 def isThisFileinRange(filename,startUTSeconds,endUTSeconds):
156 """
157 Esta funcion determina si un archivo de datos en formato Jicamarca(.r) se encuentra
158 o no dentro del rango de fecha especificado.
159
160 Inputs:
161 filename : nombre completo del archivo de datos en formato Jicamarca (.r)
162
163 startUTSeconds : fecha inicial del rango seleccionado. La fecha esta dada en
164 segundos contados desde 01/01/1970.
165 endUTSeconds : fecha final del rango seleccionado. La fecha esta dada en
166 segundos contados desde 01/01/1970.
167
168 Return:
169 Boolean : Retorna True si el archivo de datos contiene datos en el rango de
170 fecha especificado, de lo contrario retorna False.
171
172 Excepciones:
173 Si el archivo no existe o no puede ser abierto
174 Si la cabecera no puede ser leida.
175
176 """
177 m_BasicHeader = BasicHeader()
178
179 try:
180 fp = open(filename,'rb')
181 except:
182 raise IOError, "The file %s can't be opened" %(filename)
183
184 if not(m_BasicHeader.read(fp)):
185 raise IOError, "The file %s has not a valid header" %(filename)
186
187 fp.close()
188
189 if not ((startUTSeconds <= m_BasicHeader.utc) and (endUTSeconds >= m_BasicHeader.utc)):
190 return 0
191
192 return 1
193
194 23 class VoltageReader(JRODataReader):
195 24 """
196 25 Esta clase permite leer datos de voltage desde archivos en formato rawdata (.r). La lectura
197 26 de los datos siempre se realiza por bloques. Los datos leidos (array de 3 dimensiones:
198 27 perfiles*alturas*canales) son almacenados en la variable "buffer".
199 28
200 29 Esta clase contiene instancias (objetos) de las clases BasicHeader, SystemHeader,
201 30 RadarControllerHeader y Voltage. Los tres primeros se usan para almacenar informacion de la
202 31 cabecera de datos (metadata), y el cuarto (Voltage) para obtener y almacenar un perfil de
203 32 datos desde el "buffer" cada vez que se ejecute el metodo "getData".
204 33
205 34 Example:
206 35
207 36 dpath = "/home/myuser/data"
208 37
209 38 startTime = datetime.datetime(2010,1,20,0,0,0,0,0,0)
210 39
211 40 endTime = datetime.datetime(2010,1,21,23,59,59,0,0,0)
212 41
213 42 readerObj = VoltageReader()
214 43
215 44 readerObj.setup(dpath, startTime, endTime)
216 45
217 46 while(True):
218 47
219 48 #to get one profile
220 49 profile = readerObj.getData()
221 50
222 51 #print the profile
223 52 print profile
224 53
225 54 #If you want to see all datablock
226 55 print readerObj.datablock
227 56
228 57 if readerObj.noMoreFiles:
229 58 break
230 59
231 60 """
232
233 #speed of light
234 __c = 3E8
235 61
236 62
237 63 def __init__(self,m_Voltage=None):
238 64 """
239 65 Inicializador de la clase VoltageReader para la lectura de datos de voltage.
240 66
241 67 Input:
242 68 m_Voltage : Objeto de la clase Voltage. Este objeto sera utilizado para
243 69 almacenar un perfil de datos cada vez que se haga un requerimiento
244 70 (getData). El perfil sera obtenido a partir del buffer de datos,
245 71 si el buffer esta vacio se hara un nuevo proceso de lectura de un
246 72 bloque de datos.
247 73 Si este parametro no es pasado se creara uno internamente.
248 74
249 75 Variables afectadas:
250 self.m_Voltage
76 self.m_DataObj
251 77 self.m_BasicHeader
252 78 self.m_SystemHeader
253 79 self.m_RadarControllerHeader
254 80 self.m_ProcessingHeader
255 81
256 82
257 83 Return:
258 84 Void
259 85
260 86 """
261 87 if m_Voltage == None:
262 88 m_Voltage = Voltage()
263 89
264 90 if not(isinstance(m_Voltage, Voltage)):
265 91 raise ValueError, "in VoltageReader, m_Voltage must be an Voltage class object"
266 92
267 self.m_Voltage = m_Voltage
93 self.m_DataObj = m_Voltage
268 94
269 95 self.m_BasicHeader = BasicHeader()
270 96
271 97 self.m_SystemHeader = SystemHeader()
272 98
273 99 self.m_RadarControllerHeader = RadarControllerHeader()
274 100
275 101 self.m_ProcessingHeader = ProcessingHeader()
276 102
277 self.__fp = None
103 self.fp = None
278 104
279 self.__idFile = None
105 self.idFile = None
280 106
281 self.__startDateTime = None
107 self.startDateTime = None
282 108
283 self.__endDateTime = None
109 self.endDateTime = None
284 110
285 self.__dataType = None
111 self.dataType = None
286 112
287 self.__fileSizeByHeader = 0
113 self.fileSizeByHeader = 0
288 114
289 self.__pathList = []
115 self.pathList = []
290 116
291 117 self.filenameList = []
292 118
293 self.__lastUTTime = 0
119 self.lastUTTime = 0
294 120
295 self.__maxTimeStep = 30
121 self.maxTimeStep = 30
296 122
297 self.__flagIsNewFile = 0
123 self.flagIsNewFile = 0
298 124
299 self.__ippSeconds = 0
125 self.ippSeconds = 0
300 126
301 127 self.flagResetProcessing = 0
302 128
303 129 self.flagIsNewBlock = 0
304 130
305 131 self.noMoreFiles = 0
306 132
307 133 self.nReadBlocks = 0
308 134
309 135 self.online = 0
310 136
311 137 self.filename = None
312 138
313 139 self.fileSize = None
314 140
315 141 self.firstHeaderSize = 0
316 142
317 143 self.basicHeaderSize = 24
318 144
319 145 self.idProfile = 0
320 146
321 147 self.datablock = None
322 148
323 self.__datablockIndex = 9999
324
325 self.__delay = 7 #seconds
326 self.__nTries = 3 #quantity tries
327 self.__nFiles = 3 #number of files for searching
328 self.__year = 0
329 self.__doy = 0
330 self.__set = 0
331 self.__ext = None
332 self.__path = None
333 self.__pts2read = 0
334 self.__blocksize = 0
335 self.__utc = 0
336 self.nBlocks = 0
337
338
339 def __rdSystemHeader(self,fp=None):
340 if fp == None:
341 fp = self.__fp
342
343 self.m_SystemHeader.read(fp)
344
345
346 def __rdRadarControllerHeader(self,fp=None):
347 if fp == None:
348 fp = self.__fp
349
350 self.m_RadarControllerHeader.read(fp)
351
352
353 def __rdProcessingHeader(self,fp=None):
354 if fp == None:
355 fp = self.__fp
356
357 self.m_ProcessingHeader.read(fp)
149 self.datablockIndex = 9999
358 150
359
360 def __rdBasicHeader(self,fp=None):
151 self.delay = 7 #seconds
361 152
362 if fp == None:
363 fp = self.__fp
364
365 self.m_BasicHeader.read(fp)
366
367
368 def __readFirstHeader(self):
369 """
370 Lectura del First Header, es decir el Basic Header y el Long Header
371
372 Affected:
373 self.m_BasicHeader
374 self.m_SystemHeader
375 self.m_RadarControllerHeader
376 self.m_ProcessingHeader
377 self.firstHeaderSize
378 self.__heights
379 self.__dataType
380 self.__fileSizeByHeader
381 self.__ippSeconds
382 self.__blocksize
383 self.__pts2read
384
385 Return: None
386 """
387 self.__rdBasicHeader()
388 self.__rdSystemHeader()
389 self.__rdRadarControllerHeader()
390 self.__rdProcessingHeader()
391 self.firstHeaderSize = self.m_BasicHeader.size
392
393 data_type=int(numpy.log2((self.m_ProcessingHeader.processFlags & PROCFLAG.DATATYPE_MASK))-numpy.log2(PROCFLAG.DATATYPE_CHAR))
394 if data_type == 0:
395 tmp = numpy.dtype([('real','<i1'),('imag','<i1')])
396
397 elif data_type == 1:
398 tmp = numpy.dtype([('real','<i2'),('imag','<i2')])
399
400 elif data_type == 2:
401 tmp = numpy.dtype([('real','<i4'),('imag','<i4')])
402
403 elif data_type == 3:
404 tmp = numpy.dtype([('real','<i8'),('imag','<i8')])
405
406 elif data_type == 4:
407 tmp = numpy.dtype([('real','<f4'),('imag','<f4')])
408
409 elif data_type == 5:
410 tmp = numpy.dtype([('real','<f8'),('imag','<f8')])
411
412 else:
413 raise ValueError, 'Data type was not defined'
153 self.nTries = 3 #quantity tries
414 154
415 xi = self.m_ProcessingHeader.firstHeight
416 step = self.m_ProcessingHeader.deltaHeight
417 xf = xi + self.m_ProcessingHeader.numHeights*step
155 self.nFiles = 3 #number of files for searching
418 156
419 self.__heights = numpy.arange(xi, xf, step)
420 self.__dataType = tmp
421 self.__fileSizeByHeader = self.m_ProcessingHeader.dataBlocksPerFile * self.m_ProcessingHeader.blockSize + self.firstHeaderSize + self.basicHeaderSize*(self.m_ProcessingHeader.dataBlocksPerFile - 1)
422 self.__ippSeconds = 2*1000*self.m_RadarControllerHeader.ipp/self.__c
423
424 self.__pts2read = self.m_ProcessingHeader.profilesPerBlock * self.m_ProcessingHeader.numHeights * self.m_SystemHeader.numChannels
425 self.__blocksize = self.__pts2read
426
157 self.year = 0
427 158
428 def __setNextFileOnline(self):
429 """
430 Busca el siguiente file que tenga suficiente data para ser leida, dentro de un folder especifico, si
431 no encuentra un file valido espera un tiempo determinado y luego busca en los posibles n files
432 siguientes.
433
434 Affected:
435 self.__flagIsNewFile
436 self.filename
437 self.fileSize
438 self.__fp
439 self.__set
440 self.noMoreFiles
441
442 Return:
443 0 : si luego de una busqueda del siguiente file valido este no pudo ser encontrado
444 1 : si el file fue abierto con exito y esta listo a ser leido
159 self.doy = 0
445 160
446 Excepciones:
447 Si un determinado file no puede ser abierto
448 """
449 countFiles = 0
450 countTries = 0
451
452 notFirstTime_flag = False
453 fileOk_flag = False
454 changeDir_flag = False
161 self.set = 0
455 162
456 self.__flagIsNewFile = 0
163 self.ext = ".r"
457 164
458 while( True ): #este loop permite llevar la cuenta de intentos, de files y carpetas,
459 #si no encuentra alguno sale del bucle
460 countFiles += 1
461
462 if countFiles > (self.__nFiles + 1):
463 break
464
465 self.__set += 1
466
467 if countFiles > self.__nFiles: #si no encuentro el file buscado cambio de carpeta y busco en la siguiente carpeta
468 self.__set = 0
469 self.__doy += 1
470 changeDir_flag = True
471
472 file = None
473 filename = None
474 fileOk_flag = False
475
476 #busca el 1er file disponible
477 file, filename = checkForRealPath( self.__path, self.__year, self.__doy, self.__set, self.__ext )
478
479 if file == None:
480 if notFirstTime_flag: #si no es la primera vez que busca el file entonces no espera y busca for el siguiente file
481 print "\tsearching next \"%s\" file ..." % ( filename )
482 continue
483 else: #si es la primera vez que busca el file entonces espera self.__nTries veces hasta encontrarlo o no
484 for nTries in range( self.__nTries ):
485 print "\twaiting new \"%s\" file, try %03d ..." % ( filename, nTries+1 )
486 time.sleep( self.__delay )
487
488 file, filename = checkForRealPath( self.__path, self.__year, self.__doy, self.__set, self.__ext )
489 if file != None:
490 fileOk_flag = True
491 break
492
493 if not( fileOk_flag ): #no encontro ningun file valido a leer despues de haber esperado alguno
494 notFirstTime_flag = True
495 continue
496
497 #una vez que se obtuvo el 1er file valido se procede a checkear si si tamanho es suficiente para empezar a leerlo
498 currentSize = os.path.getsize( file )
499 neededSize = self.m_ProcessingHeader.blockSize + self.firstHeaderSize
500
501 #si el tamanho es suficiente entonces deja de buscar
502 if currentSize > neededSize:# and (neededSize != 0):
503 fileOk_flag = True
504 break
505
506 fileOk_flag = False
507 #si el file no tiene el tamanho necesario se espera una cierta cantidad de tiempo
508 #por una cierta cantidad de veces hasta que el contenido del file sea valido
509 if changeDir_flag: #si al buscar un file cambie de directorio ya no espero y sigo con el siguiente file
510 print "\tsearching next \"%s\" file ..." % filename
511 changeDir_flag = False
512 continue
513
514 for nTries in range( self.__nTries ):
515 print "\twaiting for the First Header block of \"%s\" file, try %03d ..." % ( filename, nTries+1 )
516 time.sleep( self.__delay )
517
518 currentSize = os.path.getsize( file )
519 neededSize = self.m_ProcessingHeader.blockSize + self.firstHeaderSize
520
521 if currentSize > neededSize:
522 fileOk_flag = True
523 break
524
525 if fileOk_flag: #si encontro un file valido sale del bucle y deja de buscar
526 break
527
528 print "Skipping the file \"%s\" due to this files is empty" % filename
529 countFiles = 0
530
531 if fileOk_flag:
532 self.fileSize = os.path.getsize( file ) #fileSize
533 self.filename = file
534 self.__flagIsNewFile = 1
535 if self.__fp != None: self.__fp.close()
536 self.__fp = open(file)
537 self.noMoreFiles = 0
538 print 'Setting the file: %s' % file
539 else:
540 self.fileSize = 0
541 self.filename = None
542 self.__fp = None
543 self.noMoreFiles = 1
544 print 'No more Files'
545
546 return fileOk_flag
547
548
549 def __setNextFileOffline(self):
165 self.path = None
550 166
551 idFile = self.__idFile
552 while(True):
553
554 idFile += 1
555
556 if not(idFile < len(self.filenameList)):
557 self.noMoreFiles = 1
558 print 'No more Files'
559 return 0
560
561 filename = self.filenameList[idFile]
562 fileSize = os.path.getsize(filename)
563
564 try:
565 fp = open(filename,'rb')
566 except:
567 raise IOError, "The file %s can't be opened" %filename
568
569 currentSize = fileSize - fp.tell()
570 neededSize = self.m_ProcessingHeader.blockSize + self.firstHeaderSize
571
572 if (currentSize < neededSize):
573 print "Skipping the file %s due to it hasn't enough data" %filename
574 continue
575
576 break
167 self.optchar = "D"
577 168
578 self.__flagIsNewFile = 1
579 self.__idFile = idFile
580 self.filename = filename
581 self.fileSize = fileSize
582 self.__fp = fp
169 self.pts2read = 0
583 170
584 print 'Setting the file: %s'%self.filename
171 self.blocksize = 0
585 172
586 return 1
587
588
589 def __setNextFile(self):
590 """
591 Determina el siguiente file a leer y si hay uno disponible lee el First Header
592
593 Affected:
594 self.m_BasicHeader
595 self.m_SystemHeader
596 self.m_RadarControllerHeader
597 self.m_ProcessingHeader
598 self.firstHeaderSize
599
600 Return:
601 0 : Si no hay files disponibles
602 1 : Si hay mas files disponibles
603 """
604 if self.__fp != None:
605 self.__fp.close()
606
607 if self.online:
608 newFile = self.__setNextFileOnline()
609 else:
610 newFile = self.__setNextFileOffline()
173 self.utc = 0
611 174
612 if self.noMoreFiles:
613 sys.exit(0)
614
615 if not(newFile):
616 return 0
617
618 self.__readFirstHeader()
619 175 self.nBlocks = 0
620 return 1
621
622 176
623 def __setNewBlock(self):
624 """
625 Lee el Basic Header y posiciona le file pointer en la posicion inicial del bloque a leer
626
627 Affected:
628 self.m_BasicHeader
629 self.flagResetProcessing
630 self.ns
631
632 Return:
633 0 : Si el file no tiene un Basic Header que pueda ser leido
634 1 : Si se pudo leer el Basic Header
635 """
636 if self.__fp == None:
637 return 0
638
639 if self.__flagIsNewFile:
640 return 1
641
642 currentSize = self.fileSize - self.__fp.tell()
643 neededSize = self.m_ProcessingHeader.blockSize + self.basicHeaderSize
644
645 #If there is enough data setting new data block
646 if ( currentSize >= neededSize ):
647 self.__rdBasicHeader()
177 def hasNotDataInBuffer(self):
178 if self.datablockIndex >= self.m_ProcessingHeader.profilesPerBlock:
648 179 return 1
649
650 #si es OnLine y ademas aun no se han leido un bloque completo entonces se espera por uno valido
651 elif (self.nBlocks != self.m_ProcessingHeader.dataBlocksPerFile) and self.online:
652 for nTries in range( self.__nTries ):
653
654 fpointer = self.__fp.tell()
655 self.__fp.close()
656
657 print "\tWaiting for the next block, try %03d ..." % (nTries+1)
658 time.sleep( self.__delay )
659
660 self.__fp = open( self.filename, 'rb' )
661 self.__fp.seek( fpointer )
662
663 self.fileSize = os.path.getsize( self.filename )
664 currentSize = self.fileSize - self.__fp.tell()
665 neededSize = self.m_ProcessingHeader.blockSize + self.basicHeaderSize
180 return 0
666 181
667 if ( currentSize >= neededSize ):
668 self.__rdBasicHeader()
669 return 1
670
671 #Setting new file
672 if not( self.__setNextFile() ):
673 return 0
182 def getBlockDimension(self):
674 183
675 deltaTime = self.m_BasicHeader.utc - self.__lastUTTime # check this
676
677 self.flagResetProcessing = 0
678
679 if deltaTime > self.__maxTimeStep:
680 self.flagResetProcessing = 1
681 #self.nReadBlocks = 0
184 self.pts2read = self.m_ProcessingHeader.profilesPerBlock * self.m_ProcessingHeader.numHeights * self.m_SystemHeader.numChannels
185 self.blocksize = self.pts2read
682 186
683 return 1
684
685
686 def __readBlock(self):
187 def readBlock(self):
687 188 """
688 __readBlock lee el bloque de datos desde la posicion actual del puntero del archivo
689 (self.__fp) y actualiza todos los parametros relacionados al bloque de datos
189 readBlock lee el bloque de datos desde la posicion actual del puntero del archivo
190 (self.fp) y actualiza todos los parametros relacionados al bloque de datos
690 191 (metadata + data). La data leida es almacenada en el buffer y el contador del buffer
691 192 es seteado a 0
692 193
693 194 Inputs:
694 195 None
695 196
696 197 Return:
697 198 None
698 199
699 200 Affected:
700 self.__datablockIndex
201 self.datablockIndex
701 202 self.datablock
702 self.__flagIsNewFile
203 self.flagIsNewFile
703 204 self.idProfile
704 205 self.flagIsNewBlock
705 206 self.nReadBlocks
706 207
707 208 Exceptions:
708 209 Si un bloque leido no es un bloque valido
709 210 """
710 211 blockOk_flag = False
711 fpointer = self.__fp.tell()
212 fpointer = self.fp.tell()
712 213
713 junk = numpy.fromfile( self.__fp, self.__dataType, self.__pts2read )
214 junk = numpy.fromfile( self.fp, self.dataType, self.pts2read )
714 215
715 216 if self.online:
716 if junk.size != self.__blocksize:
717 for nTries in range( self.__nTries ):
217 if junk.size != self.blocksize:
218 for nTries in range( self.nTries ):
718 219 print "\tWaiting for the next block, try %03d ..." % (nTries+1)
719 time.sleep( self.__delay )
720 self.__fp.seek( fpointer )
721 fpointer = self.__fp.tell()
722 junk = numpy.fromfile( self.__fp, self.__dataType, self.__pts2read )
723 if junk.size == self.__blocksize:
220 time.sleep( self.delay )
221 self.fp.seek( fpointer )
222 fpointer = self.fp.tell()
223 junk = numpy.fromfile( self.fp, self.dataType, self.pts2read )
224 if junk.size == self.blocksize:
724 225 blockOk_flag = True
725 226 break
726 227
727 228 if not( blockOk_flag ):
728 229 return 0
729 230
730 231 try:
731 232 junk = junk.reshape( (self.m_ProcessingHeader.profilesPerBlock, self.m_ProcessingHeader.numHeights, self.m_SystemHeader.numChannels) )
732 233 except:
733 234 print "Data file %s is invalid" % self.filename
734 235 return 0
735 236
736 237 #data = junk['real'] + junk['imag']*1j
737 238 self.datablock = junk['real'] + junk['imag']*1j
738 239
739 self.__datablockIndex = 0
740 self.__flagIsNewFile = 0
240 self.datablockIndex = 0
241 self.flagIsNewFile = 0
741 242 self.idProfile = 0
742 243 self.flagIsNewBlock = 1
743 244
744 245 self.nReadBlocks += 1
745 246 self.nBlocks += 1
746 247
747 248 return 1
748 249
749
750 def __hasNotDataInBuffer(self):
751 if self.__datablockIndex >= self.m_ProcessingHeader.profilesPerBlock:
752 return 1
753 return 0
754
755
756 def __searchFilesOnLine(self, path, startDateTime=None, ext = ".r"):
757 """
758 Busca el ultimo archivo de la ultima carpeta (determinada o no por startDateTime) y
759 devuelve el archivo encontrado ademas de otros datos.
760
761 Input:
762 path : carpeta donde estan contenidos los files que contiene data
763 startDateTime : punto especifico en el tiempo del cual se requiere la data
764 ext : extension de los files
765
766 Return:
767 year : el anho
768 doy : el numero de dia del anho
769 set : el set del archivo
770 filename : el ultimo file de una determinada carpeta
771 directory : eL directorio donde esta el file encontrado
772 """
773 print "Searching files ..."
774
775 dirList = []
776 directory = None
777
778 if startDateTime == None:
779 for thisPath in os.listdir(path):
780 if os.path.isdir( os.path.join(path,thisPath) ):
781 dirList.append( thisPath )
782
783 dirList = sorted( dirList, key=str.lower ) #para que quede ordenado al margen de si el nombre esta en mayusculas o minusculas, utilizo la funcion sorted
784 if len(dirList) > 0 :
785 directory = dirList[-1] #me quedo con el ultimo directorio de una carpeta
786 else:
787 year = startDateTime.timetuple().tm_year
788 doy = startDateTime.timetuple().tm_yday
789
790 doyPath = "D%04d%03d" % (year,doy) #caso del nombre en mayusculas
791 if os.path.isdir( os.path.join(path,doyPath) ):
792 directory = doyPath
793
794 doyPath = doyPath.lower() #caso del nombre en minusculas
795 if os.path.isdir( os.path.join(path,doyPath) ):
796 directory = doyPath
797
798 if directory == None:
799 return 0, 0, 0, None, None
800
801 filename = getlastFileFromPath( os.listdir( os.path.join(path,directory) ), ext )
802
803 if filename == None:
804 return 0, 0, 0, None, None
805
806 year = int( directory[-7:-3] )
807 doy = int( directory[-3:] )
808 ln = len( ext )
809 set = int( filename[-ln-3:-ln] )
810
811 return year, doy, set, filename, directory
812
813
814 def __searchFilesOffLine(self, path, startDateTime, endDateTime, set=None, expLabel = "", ext = ".r"):
815 """
816 Realiza una busqueda de los archivos que coincidan con los parametros
817 especificados y se encuentren ubicados en el path indicado. Para realizar una busqueda
818 correcta la estructura de directorios debe ser la siguiente:
819
820 ...path/D[yyyy][ddd]/expLabel/D[yyyy][ddd][sss].ext
821
822 [yyyy]: anio
823 [ddd] : dia del anio
824 [sss] : set del archivo
825
826 Inputs:
827 path : Directorio de datos donde se realizara la busqueda. Todos los
828 ficheros que concidan con el criterio de busqueda seran
829 almacenados en una lista y luego retornados.
830 startDateTime : Fecha inicial. Rechaza todos los archivos donde
831 file end time < startDateTime (obejto datetime.datetime)
832
833 endDateTime : Fecha final. Rechaza todos los archivos donde
834 file start time > endDateTime (obejto datetime.datetime)
835
836 set : Set del primer archivo a leer. Por defecto None
837
838 expLabel : Nombre del subdirectorio de datos. Por defecto ""
839
840 ext : Extension de los archivos a leer. Por defecto .r
841
842 Return:
843
844 (pathList, filenameList)
845
846 pathList : Lista de directorios donde se encontraron archivos dentro
847 de los parametros especificados
848 filenameList : Lista de archivos (ruta completa) que coincidieron con los
849 parametros especificados.
850
851 Variables afectadas:
852
853 self.filenameList: Lista de archivos (ruta completa) que la clase utiliza
854 como fuente para leer los bloque de datos, si se termina
855 de leer todos los bloques de datos de un determinado
856 archivo se pasa al siguiente archivo de la lista.
857
858 Excepciones:
859
860 """
861 print "Searching files ..."
862
863 dirList = []
864 for thisPath in os.listdir(path):
865 if os.path.isdir(os.path.join(path,thisPath)):
866 dirList.append(thisPath)
867
868 pathList = []
869
870 thisDateTime = startDateTime
871
872 while(thisDateTime <= endDateTime):
873 year = thisDateTime.timetuple().tm_year
874 doy = thisDateTime.timetuple().tm_yday
875
876 match = fnmatch.filter(dirList, '?' + '%4.4d%3.3d' % (year,doy))
877 if len(match) == 0:
878 thisDateTime += datetime.timedelta(1)
879 continue
880
881 pathList.append(os.path.join(path,match[0],expLabel))
882 thisDateTime += datetime.timedelta(1)
883
884 startUtSeconds = time.mktime(startDateTime.timetuple())
885 endUtSeconds = time.mktime(endDateTime.timetuple())
886
887 filenameList = []
888 for thisPath in pathList:
889 fileList = glob.glob1(thisPath, "*%s" %ext)
890 fileList.sort()
891 for file in fileList:
892 filename = os.path.join(thisPath,file)
893 if isThisFileinRange(filename, startUtSeconds, endUtSeconds):
894 filenameList.append(filename)
895
896 self.filenameList = filenameList
897
898 return pathList, filenameList
899
900
901 def __initFilesOnline( self, path, dirfilename, filename ):
902 """
903 Verifica que el primer file tenga una data valida, para ello leo el 1er bloque
904 del file, si no es un file valido espera una cierta cantidad de tiempo a que
905 lo sea, si transcurrido el tiempo no logra validar el file entonces el metodo
906 devuelve 0 caso contrario devuelve 1
907
908 Affected:
909 m_BasicHeader
910
911 Return:
912 0 : file no valido para ser leido
913 1 : file valido para ser leido
914 """
915 m_BasicHeader = BasicHeader()
916
917 file = os.path.join( path, dirfilename, filename )
918
919 for nTries in range( self.__nTries+1 ):
920 try:
921 fp = open( file,'rb' ) #lectura binaria
922 except:
923 raise IOError, "The file %s can't be opened" % (file)
924
925 try:
926 m_BasicHeader.read(fp)
927 except:
928 print "The file %s is empty" % filename
929
930 fp.close()
931 fp = None
932
933 if m_BasicHeader.size > 24:
934 break
935
936 if nTries >= self.__nTries: #si ya espero la cantidad de veces necesarias entonces ya no vuelve a esperar
937 break
938
939 print '\twaiting for new block: try %02d' % ( nTries )
940 time.sleep( self.__delay )
941
942 if m_BasicHeader.size <= 24:
943 return 0
944
945 return 1
946
947
948 def setup(self, path, startDateTime, endDateTime=None, set=None, expLabel = "", ext = ".r", online = 0):
949 """
950 setup configura los parametros de lectura de la clase VoltageReader.
951
952 Si el modo de lectura es offline, primero se realiza una busqueda de todos los archivos
953 que coincidan con los parametros especificados; esta lista de archivos son almacenados en
954 self.filenameList.
955
956 Input:
957 path : Directorios donde se ubican los datos a leer. Dentro de este
958 directorio deberia de estar subdirectorios de la forma:
959
960 path/D[yyyy][ddd]/expLabel/P[yyyy][ddd][sss][ext]
961
962 startDateTime : Fecha inicial. Rechaza todos los archivos donde
963 file end time < startDatetime (obejto datetime.datetime)
964
965 endDateTime : Fecha final. Si no es None, rechaza todos los archivos donde
966 file end time < startDatetime (obejto datetime.datetime)
967
968 set : Set del primer archivo a leer. Por defecto None
969
970 expLabel : Nombre del subdirectorio de datos. Por defecto ""
971
972 ext : Extension de los archivos a leer. Por defecto .r
973
974 online : Si es == a 0 entonces busca files que cumplan con las condiciones dadas
975
976 Return:
977 0 : Si no encuentra files que cumplan con las condiciones dadas
978 1 : Si encuentra files que cumplan con las condiciones dadas
979
980 Affected:
981 self.startUTCSeconds
982 self.endUTCSeconds
983 self.startYear
984 self.endYear
985 self.startDoy
986 self.endDoy
987 self.__pathList
988 self.filenameList
989 self.online
990 """
991 if online:
992 fileOK_flag = False
993 subfolder = "D%04d%03d" % ( startDateTime.timetuple().tm_year, startDateTime.timetuple().tm_yday )
994 file = os.path.join( path, subfolder )
995
996 for nTries in range( self.__nTries+1 ): #espera por el 1er file
997 year, doy, set, filename, dirfilename = self.__searchFilesOnLine( path, startDateTime, ext )
998
999 if filename != None:
1000 if isFileOK( os.path.join( path,dirfilename,filename ) ):
1001 fileOK_flag = True
1002 break
1003
1004 if nTries >= self.__nTries: #si ya espero la cantidad de veces necesarias entonces ya no vuelve a esperar
1005 break
1006
1007 print "Searching first file in \"%s\", try %03d ..." % ( file, nTries+1 )
1008 time.sleep( self.__delay )
1009
1010 if not( fileOK_flag ): #filename == None:
1011 print "No files on line or invalid first file"
1012 return 0
1013
1014 if self.__initFilesOnline( path, dirfilename, filename ) == 0:
1015 print "The file %s hasn't enough data" % filename
1016 return 0
1017
1018 self.__year = year
1019 self.__doy = doy
1020 self.__set = set - 1
1021 self.__path = path
1022
1023 else:
1024 pathList, filenameList = self.__searchFilesOffLine( path, startDateTime, endDateTime, set, expLabel, ext )
1025 self.__idFile = -1
1026 self.__pathList = pathList
1027 self.filenameList = filenameList
1028
1029 self.online = online
1030 self.__ext = ext
1031
1032 if not( self.__setNextFile() ):
1033 if (startDateTime != None) and (endDateTime != None):
1034 print "No files in range: %s - %s" %(startDateTime.ctime(), endDateTime.ctime())
1035 elif startDateTime != None:
1036 print "No files in : %s" % startDateTime.ctime()
1037 else:
1038 print "No files"
1039 return 0
1040
1041 if startDateTime != None:
1042 self.startUTCSeconds = time.mktime(startDateTime.timetuple())
1043 self.startYear = startDateTime.timetuple().tm_year
1044 self.startDoy = startDateTime.timetuple().tm_yday
1045
1046 if endDateTime != None:
1047 self.endUTCSeconds = time.mktime(endDateTime.timetuple())
1048 self.endYear = endDateTime.timetuple().tm_year
1049 self.endDoy = endDateTime.timetuple().tm_yday
1050 #call fillHeaderValues() - to Data Object
1051
1052 self.m_Voltage.m_BasicHeader = self.m_BasicHeader.copy()
1053 self.m_Voltage.m_ProcessingHeader = self.m_ProcessingHeader.copy()
1054 self.m_Voltage.m_RadarControllerHeader = self.m_RadarControllerHeader.copy()
1055 self.m_Voltage.m_SystemHeader = self.m_SystemHeader.copy()
1056 self.m_Voltage.dataType = self.__dataType
1057
1058 return 1
1059
1060
1061 def readNextBlock(self):
1062 """
1063 Establece un nuevo bloque de datos a leer y los lee, si es que no existiese
1064 mas bloques disponibles en el archivo actual salta al siguiente.
1065
1066 Affected:
1067 self.__lastUTTime
1068
1069 Return: None
1070 """
1071 if not(self.__setNewBlock()):
1072 return 0
1073
1074 if not( self.__readBlock() ):
1075 return 0
1076
1077 self.__lastUTTime = self.m_BasicHeader.utc
1078
1079 return 1
1080
1081
1082 250 def getData(self):
1083 251 """
1084 252 getData obtiene una unidad de datos del buffer de lectura y la copia a la clase "Voltage"
1085 253 con todos los parametros asociados a este (metadata). cuando no hay datos en el buffer de
1086 254 lectura es necesario hacer una nueva lectura de los bloques de datos usando "readNextBlock"
1087 255
1088 256 Ademas incrementa el contador del buffer en 1.
1089 257
1090 258 Return:
1091 259 data : retorna un perfil de voltages (alturas * canales) copiados desde el
1092 260 buffer. Si no hay mas archivos a leer retorna None.
1093 261
1094 262 Variables afectadas:
1095 self.m_Voltage
1096 self.__datablockIndex
263 self.m_DataObj
264 self.datablockIndex
1097 265 self.idProfile
1098 266
1099 267 Affected:
1100 self.m_Voltage
1101 self.__datablockIndex
268 self.m_DataObj
269 self.datablockIndex
1102 270 self.flagResetProcessing
1103 271 self.flagIsNewBlock
1104 272 self.idProfile
1105 273 """
1106 274 if self.noMoreFiles: return 0
1107 275
1108 276 self.flagResetProcessing = 0
1109 277 self.flagIsNewBlock = 0
1110 278
1111 if self.__hasNotDataInBuffer():
279 if self.hasNotDataInBuffer():
1112 280
1113 281 if not( self.readNextBlock() ):
1114 self.__setNextFile()
282 self.setNextFile()
1115 283 return 0
1116 284
1117 self.m_Voltage.m_BasicHeader = self.m_BasicHeader.copy()
1118 self.m_Voltage.m_ProcessingHeader = self.m_ProcessingHeader.copy()
1119 self.m_Voltage.m_RadarControllerHeader = self.m_RadarControllerHeader.copy()
1120 self.m_Voltage.m_SystemHeader = self.m_SystemHeader.copy()
1121 self.m_Voltage.heights = self.__heights
1122 self.m_Voltage.dataType = self.__dataType
285 self.m_DataObj.m_BasicHeader = self.m_BasicHeader.copy()
286 self.m_DataObj.m_ProcessingHeader = self.m_ProcessingHeader.copy()
287 self.m_DataObj.m_RadarControllerHeader = self.m_RadarControllerHeader.copy()
288 self.m_DataObj.m_SystemHeader = self.m_SystemHeader.copy()
289 self.m_DataObj.heights = self.heights
290 self.m_DataObj.dataType = self.dataType
1123 291
1124 292 if self.noMoreFiles == 1:
1125 293 print 'Process finished'
1126 294 return 0
1127 295
1128 296 #data es un numpy array de 3 dmensiones (perfiles, alturas y canales)
1129 297
1130 298 if self.datablock == None:
1131 self.m_Voltage.flagNoData = True
299 self.m_DataObj.flagNoData = True
1132 300 return 0
1133 301
1134 time = self.m_BasicHeader.utc + self.__datablockIndex * self.__ippSeconds
1135 self.__utc = time
1136 #self.m_Voltage.m_BasicHeader.utc = time
302 time = self.m_BasicHeader.utc + self.datablockIndex * self.ippSeconds
303 self.utc = time
304 #self.m_DataObj.m_BasicHeader.utc = time
1137 305
1138 self.m_Voltage.flagNoData = False
1139 self.m_Voltage.flagResetProcessing = self.flagResetProcessing
306 self.m_DataObj.flagNoData = False
307 self.m_DataObj.flagResetProcessing = self.flagResetProcessing
1140 308
1141 self.m_Voltage.data = self.datablock[self.__datablockIndex,:,:]
1142 self.m_Voltage.idProfile = self.idProfile
309 self.m_DataObj.data = self.datablock[self.datablockIndex,:,:]
310 self.m_DataObj.idProfile = self.idProfile
1143 311
1144 self.__datablockIndex += 1
312 self.datablockIndex += 1
1145 313 self.idProfile += 1
1146 314
1147 315 #call setData - to Data Object
1148 316
1149 return 1 #self.m_Voltage.data
317 return 1 #self.m_DataObj.data
1150 318
1151 319 class VoltageWriter( JRODataWriter ):
1152 320 """
1153 321 Esta clase permite escribir datos de voltajes a archivos procesados (.r). La escritura
1154 322 de los datos siempre se realiza por bloques.
1155 323 """
1156 324 __configHeaderFile = 'wrSetHeadet.txt'
1157 325
1158 326 def __init__(self,m_Voltage=None):
1159 327 """
1160 328 Inicializador de la clase VoltageWriter para la escritura de datos de espectros.
1161 329
1162 330 Affected:
1163 self.m_Voltage
331 self.m_DataObj
1164 332 self.m_BasicHeader
1165 333 self.m_SystemHeader
1166 334 self.m_RadarControllerHeader
1167 335 self.m_ProcessingHeader
1168 336
1169 337 Return: None
1170 338 """
1171 339 if m_Voltage == None:
1172 340 m_Voltage = Voltage()
1173 341
1174 self.m_Voltage = m_Voltage
1175
1176 self.__path = None
342 self.m_DataObj = m_Voltage
1177 343
1178 self.__fp = None
344 self.fp = None
1179 345
1180 self.__format = None
346 self.format = None
1181 347
1182 self.__blocksCounter = 0
348 self.blocksCounter = 0
1183 349
1184 self.__setFile = None
350 self.setFile = None
1185 351
1186 self.__flagIsNewFile = 1
352 self.flagIsNewFile = 1
1187 353
1188 354 self.datablock = None
1189 355
1190 self.__datablockIndex = 0
356 self.datablockIndex = 0
357
358 self.dataType = None
359
360 self.ext = ".r"
1191 361
1192 self.__dataType = None
362 self.path = None
1193 363
1194 self.__ext = None
364 self.optchar = "D"
1195 365
1196 self.__shapeBuffer = None
366 self.shapeBuffer = None
1197 367
1198 368 self.nWriteBlocks = 0
1199 369
1200 370 self.flagIsNewBlock = 0
1201 371
1202 372 self.noMoreFiles = 0
1203 373
1204 374 self.filename = None
1205 375
1206 376 self.m_BasicHeader= BasicHeader()
1207 377
1208 378 self.m_SystemHeader = SystemHeader()
1209 379
1210 380 self.m_RadarControllerHeader = RadarControllerHeader()
1211 381
1212 382 self.m_ProcessingHeader = ProcessingHeader()
1213 383
1214
1215 def __writeFirstHeader(self):
1216 """
1217 Escribe el primer header del file es decir el Basic header y el Long header (SystemHeader, RadarControllerHeader, ProcessingHeader)
1218
1219 Affected:
1220 __dataType
1221
1222 Return:
1223 None
1224 """
1225 self.__writeBasicHeader()
1226 self.__wrSystemHeader()
1227 self.__wrRadarControllerHeader()
1228 self.__wrProcessingHeader()
1229 self.__dataType = self.m_Voltage.dataType
1230
1231
1232 def __writeBasicHeader(self,fp=None):
1233 """
1234 Escribe solo el Basic header en el file creado
1235
1236 Return:
1237 None
1238 """
1239 if fp == None:
1240 fp = self.__fp
1241
1242 self.m_BasicHeader.write(fp)
1243
1244
1245 def __wrSystemHeader(self,fp=None):
1246 """
1247 Escribe solo el System header en el file creado
1248
1249 Return:
1250 None
1251 """
1252 if fp == None:
1253 fp = self.__fp
1254
1255 self.m_SystemHeader.write(fp)
1256
1257
1258 def __wrRadarControllerHeader(self,fp=None):
1259 """
1260 Escribe solo el RadarController header en el file creado
1261
1262 Return:
1263 None
1264 """
1265 if fp == None:
1266 fp = self.__fp
1267
1268 self.m_RadarControllerHeader.write(fp)
384 def hasAllDataInBuffer(self):
385 if self.datablockIndex >= self.m_ProcessingHeader.profilesPerBlock:
386 return 1
387 return 0
1269 388
389 def setBlockDimension(self):
1270 390
1271 def __wrProcessingHeader(self,fp=None):
1272 """
1273 Escribe solo el Processing header en el file creado
1274
1275 Return:
1276 None
1277 """
1278 if fp == None:
1279 fp = self.__fp
391 self.shapeBuffer = (self.m_ProcessingHeader.profilesPerBlock,
392 self.m_ProcessingHeader.numHeights,
393 self.m_SystemHeader.numChannels )
1280 394
1281 self.m_ProcessingHeader.write(fp)
1282
1283
1284 def __setNextFile(self):
1285 """
1286 Determina el siguiente file que sera escrito
1287
1288 Affected:
1289 self.filename
1290 self.__subfolder
1291 self.__fp
1292 self.__setFile
1293 self.__flagIsNewFile
1294
1295 Return:
1296 0 : Si el archivo no puede ser escrito
1297 1 : Si el archivo esta listo para ser escrito
1298 """
1299 #setFile = self.__setFile
1300 ext = self.__ext
1301 path = self.__path
395 self.datablock = numpy.zeros(self.shapeBuffer, numpy.dtype('complex'))
1302 396
1303 #setFile += 1
1304
1305 if self.__fp != None:
1306 self.__fp.close()
1307
1308 """
1309 timeTuple = time.localtime(self.m_Voltage.m_BasicHeader.utc) # utc from m_Voltage
1310 file = 'D%4.4d%3.3d%3.3d%s' % (timeTuple.tm_year,timeTuple.tm_yday,setFile,ext)
1311 subfolder = 'D%4.4d%3.3d' % (timeTuple.tm_year,timeTuple.tm_yday)
1312 tmp = os.path.join(path,subfolder)
1313 if not(os.path.exists(tmp)):
1314 os.mkdir(tmp)
1315 """
1316 ##################################
1317 """
1318 if self.m_BasicHeader.size <= 24:
1319 self.__fp.close()
1320 self.__fp = None
1321 return 0 #no existe la suficiente data para ser escrita
1322 """
1323
1324 timeTuple = time.localtime( self.m_Voltage.m_BasicHeader.utc ) # utc from m_Voltage
1325 subfolder = 'D%4.4d%3.3d' % (timeTuple.tm_year,timeTuple.tm_yday)
1326
1327 tmp = os.path.join( path, subfolder )
1328 if not( os.path.exists(tmp) ):
1329 os.mkdir(tmp)
1330 self.__setFile = -1 #inicializo mi contador de seteo
1331 else:
1332 filesList = os.listdir( tmp )
1333 if len( filesList ) > 0:
1334 filesList = sorted( filesList, key=str.lower )
1335 filen = filesList[-1]
1336 # el filename debera tener el siguiente formato
1337 # 0 1234 567 89A BCDE (hex)
1338 # D YYYY DDD SSS .ext
1339 if isNumber( filen[8:11] ):
1340 self.__setFile = int( filen[8:11] ) #inicializo mi contador de seteo al seteo del ultimo file
1341 else:
1342 self.__setFile = -1
1343 else:
1344 self.__setFile = -1 #inicializo mi contador de seteo
1345
1346 setFile = self.__setFile
1347 setFile += 1
1348 file = 'D%4.4d%3.3d%3.3d%s' % ( timeTuple.tm_year, timeTuple.tm_yday, setFile, ext )
1349 ##################################
1350
1351 filename = os.path.join( path, subfolder, file )
1352
1353 fp = open( filename,'wb' )
1354
1355 self.__blocksCounter = 0
1356
1357 #guardando atributos
1358 self.filename = filename
1359 self.__subfolder = subfolder
1360 self.__fp = fp
1361 self.__setFile = setFile
1362 self.__flagIsNewFile = 1
1363
1364 print 'Writing the file: %s'%self.filename
1365
1366 self.__writeFirstHeader()
1367
1368 return 1
1369
1370
1371 def __setNewBlock(self):
1372 """
1373 Si es un nuevo file escribe el First Header caso contrario escribe solo el Basic Header
1374
1375 Return:
1376 0 : si no pudo escribir nada
1377 1 : Si escribio el Basic el First Header
1378 """
1379 if self.__fp == None:
1380 self.__setNextFile()
1381
1382 if self.__flagIsNewFile:
1383 return 1
1384
1385 if self.__blocksCounter < self.m_ProcessingHeader.dataBlocksPerFile:
1386 self.__writeBasicHeader()
1387 return 1
1388
1389 if not( self.__setNextFile() ):
1390 return 0
1391
1392 return 1
1393
1394
1395 def __writeBlock(self):
397 def writeBlock(self):
1396 398 """
1397 399 Escribe el buffer en el file designado
1398 400
1399 401 Affected:
1400 self.__datablockIndex
1401 self.__flagIsNewFile
402 self.datablockIndex
403 self.flagIsNewFile
1402 404 self.flagIsNewBlock
1403 405 self.nWriteBlocks
1404 self.__blocksCounter
406 self.blocksCounter
1405 407
1406 408 Return: None
1407 409 """
1408 data = numpy.zeros( self.__shapeBuffer, self.__dataType )
410 data = numpy.zeros( self.shapeBuffer, self.dataType )
1409 411
1410 412 data['real'] = self.datablock.real
1411 413 data['imag'] = self.datablock.imag
1412 414
1413 415 data = data.reshape( (-1) )
1414 416
1415 data.tofile( self.__fp )
417 data.tofile( self.fp )
1416 418
1417 419 self.datablock.fill(0)
1418 self.__datablockIndex = 0
1419 self.__flagIsNewFile = 0
420 self.datablockIndex = 0
421 self.flagIsNewFile = 0
1420 422 self.flagIsNewBlock = 1
1421 423 self.nWriteBlocks += 1
1422 self.__blocksCounter += 1
1423
1424
1425 def writeNextBlock(self):
1426 """
1427 Selecciona el bloque siguiente de datos y los escribe en un file
1428
1429 Return:
1430 0 : Si no hizo pudo escribir el bloque de datos
1431 1 : Si no pudo escribir el bloque de datos
1432 """
1433 if not(self.__setNewBlock()):
1434 return 0
424 self.blocksCounter += 1
1435 425
1436 self.__writeBlock()
1437 return 1
1438
1439
1440 def __hasAllDataInBuffer(self):
1441 if self.__datablockIndex >= self.m_ProcessingHeader.profilesPerBlock:
1442 return 1
1443 return 0
1444
1445
1446 426 def putData(self):
1447 427 """
1448 428 Setea un bloque de datos y luego los escribe en un file
1449 429
1450 430 Affected:
1451 431 self.flagIsNewBlock
1452 self.__datablockIndex
432 self.datablockIndex
1453 433
1454 434 Return:
1455 435 0 : Si no hay data o no hay mas files que puedan escribirse
1456 436 1 : Si se escribio la data de un bloque en un file
1457 437 """
1458 438 self.flagIsNewBlock = 0
1459 439
1460 if self.m_Voltage.flagNoData:
440 if self.m_DataObj.flagNoData:
1461 441 return 0
1462 442
1463 if self.m_Voltage.flagResetProcessing:
443 if self.m_DataObj.flagResetProcessing:
1464 444
1465 445 self.datablock.fill(0)
1466 self.__datablockIndex = 0
1467 self.__setNextFile()
446 self.datablockIndex = 0
447 self.setNextFile()
1468 448
1469 self.datablock[self.__datablockIndex,:,:] = self.m_Voltage.data
449 self.datablock[self.datablockIndex,:,:] = self.m_DataObj.data
1470 450
1471 self.__datablockIndex += 1
451 self.datablockIndex += 1
1472 452
1473 if self.__hasAllDataInBuffer():
1474 self.__getHeader()
453 if self.hasAllDataInBuffer():
454 self.getHeader()
1475 455 self.writeNextBlock()
1476 456
1477 457 if self.noMoreFiles:
1478 458 #print 'Process finished'
1479 459 return 0
1480 460
1481 461 return 1
1482
1483
1484 def __getHeader(self):
1485 """
1486 Obtiene una copia del First Header
1487
1488 Affected:
1489 self.m_BasicHeader
1490 self.m_SystemHeader
1491 self.m_RadarControllerHeader
1492 self.m_ProcessingHeader
1493 self.__dataType
1494
1495 Return:
1496 None
1497 """
1498 self.m_BasicHeader = self.m_Voltage.m_BasicHeader.copy()
1499 self.m_SystemHeader = self.m_Voltage.m_SystemHeader.copy()
1500 self.m_RadarControllerHeader = self.m_Voltage.m_RadarControllerHeader.copy()
1501 self.m_ProcessingHeader = self.m_Voltage.m_ProcessingHeader.copy()
1502 self.__dataType = self.m_Voltage.dataType
1503
1504
1505 def __setHeaderByFile(self):
1506
1507 format = self.__format
1508 header = ['Basic','System','RadarController','Processing']
1509
1510 fmtFromFile = None
1511 headerFromFile = None
1512
1513
1514 fileTable = self.__configHeaderFile
1515
1516 if os.access(fileTable, os.R_OK):
1517 import re, string
1518
1519 f = open(fileTable,'r')
1520 lines = f.read()
1521 f.close()
1522
1523 #Delete comments into expConfig
1524 while 1:
1525
1526 startComment = string.find(lines.lower(),'#')
1527 if startComment == -1:
1528 break
1529 endComment = string.find(lines.lower(),'\n',startComment)
1530 lines = string.replace(lines,lines[startComment:endComment+1],'', 1)
1531
1532 while expFromFile == None:
1533
1534 currFmt = string.find(lines.lower(),'format="%s"' %(expName))
1535 nextFmt = string.find(lines.lower(),'format',currFmt+10)
1536
1537 if currFmt == -1:
1538 break
1539 if nextFmt == -1:
1540 nextFmt = len(lines)-1
1541
1542 fmtTable = lines[currFmt:nextFmt]
1543 lines = lines[nextFmt:]
1544
1545 fmtRead = self.__getValueFromArg(fmtTable,'format')
1546 if fmtRead != format:
1547 continue
1548 fmtFromFile = fmtRead
1549
1550 lines2 = fmtTable
1551
1552 while headerFromFile == None:
1553
1554 currHeader = string.find(lines2.lower(),'header="%s"' %(header))
1555 nextHeader = string.find(lines2.lower(),'header',currHeader+10)
1556
1557 if currHeader == -1:
1558 break
1559 if nextHeader == -1:
1560 nextHeader = len(lines2)-1
1561
1562 headerTable = lines2[currHeader:nextHeader]
1563 lines2 = lines2[nextHeader:]
1564
1565 headerRead = self.__getValueFromArg(headerTable,'site')
1566 if not(headerRead in header):
1567 continue
1568 headerFromFile = headerRead
1569
1570 if headerRead == 'Basic':
1571 self.m_BasicHeader.size = self.__getValueFromArg(headerTable,'size',lower=False)
1572 self.m_BasicHeader.version = self.__getValueFromArg(headerTable,'version',lower=False)
1573 self.m_BasicHeader.dataBlock = self.__getValueFromArg(headerTable,'dataBlock',lower=False)
1574 self.m_BasicHeader.utc = self.__getValueFromArg(headerTable,'utc',lower=False)
1575 self.m_BasicHeader.miliSecond = self.__getValueFromArg(headerTable,'miliSecond',lower=False)
1576 self.m_BasicHeader.timeZone = self.__getValueFromArg(headerTable,'timeZone',lower=False)
1577 self.m_BasicHeader.dstFlag = self.__getValueFromArg(headerTable,'dstFlag',lower=False)
1578 self.m_BasicHeader.errorCount = self.__getValueFromArg(headerTable,'errorCount',lower=False)
1579
1580 else:
1581 print "file access denied:%s"%fileTable
1582 sys.exit(0)
1583
1584
1585 def setup(self,path,set=0,format='rawdata'):
1586 """
1587 Setea el tipo de formato en la cual sera guardada la data y escribe el First Header
1588
1589 Inputs:
1590 path : el path destino en el cual se escribiran los files a crear
1591 format : formato en el cual sera salvado un file
1592 set : el setebo del file
1593
1594 Return:
1595 0 : Si no realizo un buen seteo
1596 1 : Si realizo un buen seteo
1597 """
1598 if format == 'hdf5':
1599 ext = '.hdf5'
1600 format = 'hdf5'
1601 print 'call hdf5 library'
1602 return 0
1603
1604 if format == 'rawdata':
1605 ext = '.r'
1606 format = 'Jicamarca'
1607
1608 #call to config_headers
1609 #self.__setHeaderByFile()
1610
1611 self.__path = path
1612 self.__setFile = set - 1
1613 self.__ext = ext
1614 self.__format = format
1615
1616 self.__getHeader()
1617 self.__shapeBuffer = (self.m_ProcessingHeader.profilesPerBlock,
1618 self.m_ProcessingHeader.numHeights,
1619 self.m_SystemHeader.numChannels )
1620
1621 self.datablock = numpy.zeros(self.__shapeBuffer, numpy.dtype('complex'))
1622
1623 if not( self.__setNextFile() ):
1624 return 0
1625
1626 return 1
1627
1628
1629 462
1630 463
1631 464 No newline at end of file
General Comments 0
You need to be logged in to leave comments. Login now