diff --git a/.env b/.env index 22839f9..e69820b 100644 --- a/.env +++ b/.env @@ -11,6 +11,9 @@ TXA_SITE= TXB_SITE= SIRM_MAX_UPLOAD_SIZE_MB=20 +#PEDESTAL - AZ OFFSET +AZ_OFFSET=26.27 + #Postgres settings POSTGRES_PORT_5432_TCP_ADDR=sirm-postgres POSTGRES_PORT_5432_TCP_PORT=5432 diff --git a/.gitignore b/.gitignore index 43bfecc..db1760f 100644 --- a/.gitignore +++ b/.gitignore @@ -4,7 +4,10 @@ volumes/certs volumes/sirm/static_files/* volumes/cam volumes/sirm/.gitkeep +volumes/sirm/log.log +volumes/schain/schain migrations *.pyc *initial.py -.DS_Store \ No newline at end of file +.DS_Store +.env \ No newline at end of file diff --git a/docker-compose.yml b/docker-compose.yml index cabd36f..ba19e9b 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -101,14 +101,39 @@ services: - SIRM_USER=${SIRM_USER} - SIRM_PASSWORD=${SIRM_PASSWORD} - SIRM_EMAIL=${SIRM_EMAIL} + - AZ_OFFSET=${AZ_OFFSET} - VIRTUAL_HOST=${SIRM_SITE} volumes: - 'sirm_web:/workspace/sirm' + - 'sirm_nas:/data' depends_on: - sirm-postgres networks: - frontend_sirm - backend_sirm + labels: + ofelia.enabled: "true" + ofelia.job-exec.datecron.schedule: "@every 5s" + ofelia.job-exec.datecron.command: "python manage.py reset_exp" + logging: + driver: "json-file" + options: + max-size: "12m" + + sirm-job: + container_name: 'sirm-job' + image: mcuadros/ofelia:latest + depends_on: + - sirm-web + networks: + - frontend_sirm + - backend_sirm + command: daemon --docker + volumes: + - /var/run/docker.sock:/var/run/docker.sock:ro + labels: + ofelia.job-local.my-test-job.schedule: "@every 5s" + ofelia.job-local.my-test-job.command: "date" logging: driver: "json-file" options: @@ -148,6 +173,7 @@ services: - SOPHY_TOPIC=${SOPHY_TOPIC} - TXA_SITE=${TXA_SITE} - TXB_SITE=${TXB_SITE} + - SCHAIN_SITE=${SCHAIN_SITE} - VIRTUAL_HOST=${PROC_SITE} volumes: - 'sirm_proc:/app' diff --git a/volumes/proc/acq.py b/volumes/proc/acq.py new file mode 100644 index 0000000..915e218 --- /dev/null +++ b/volumes/proc/acq.py @@ -0,0 +1,77 @@ +#!/usr/bin/env python + +import os, sys +import signal +import time +import json +import paho.mqtt.client as paho +from watchdog.events import FileSystemEventHandler +from watchdog.observers.polling import PollingObserver +import platform + +MQTTHOST = os.getenv('BROKER_URL', '192.168.1.130') +PROCSITE = os.getenv('PROC_SITE', 'sophy-proc') +MQTTPORT = int(os.getenv('MQTTPORT', 1883)) +MQTTUSERNAME = os.getenv('MQTTUSERNAME', None) +MQTTPASSWORD = os.getenv('MQTTPASSWORD', None) +MQTTWATCHDIR = '/data' +MQTTQOS = int(os.getenv('MQTTQOS', 0)) +MQTTRETAIN = int(os.getenv('MQTTRETAIN', 0)) + +MQTTFIXEDTOPIC = os.getenv('MQTTFIXEDTOPIC', 'sophy/acq') + +WATCHDEBUG = os.getenv('WATCHDEBUG', 1) + +# Publish with retain (True or False) +if MQTTRETAIN == 1: + MQTTRETAIN=True +else: + MQTTRETAIN=False + +OS = platform.system() + +clientid = 'sophy-acq-%s' % os.getpid() +mqtt = paho.Client(clientid, clean_session=True) + +if MQTTUSERNAME is not None or MQTTPASSWORD is not None: + mqtt.username_pw_set(MQTTUSERNAME, MQTTPASSWORD) + +def on_publish(mosq, userdata, mid): + pass + +def on_disconnect(mosq, userdata, rc): + print ("disconnected") + time.sleep(1) + +def on_message(client, userdata, msg): + payload = msg.payload.decode() + print(f"Received `{payload}` from `{msg.topic}` topic", flush=True) + +def signal_handler(signal, frame): + """ Bail out at the top level """ + + mqtt.loop_stop() + mqtt.disconnect() + + sys.exit(0) + +def main(): + print('Sophy acquisition monitor will publish messages to {}'.format(MQTTFIXEDTOPIC), flush=True) + mqtt.on_disconnect = on_disconnect + mqtt.on_publish = on_publish + mqtt.connect(MQTTHOST, MQTTPORT) + mqtt.subscribe('sophy/control') + mqtt.on_message = on_message + + mqtt.loop_start() + + signal.signal(signal.SIGINT, signal_handler) + + test = json.dumps({'file': '', 'size': ''}) + + while 1: + mqtt.publish(MQTTFIXEDTOPIC, test, qos=MQTTQOS, retain=MQTTRETAIN) + time.sleep(1) + +if __name__ == '__main__': + main() \ No newline at end of file diff --git a/volumes/proc/app.py b/volumes/proc/app.py index 4e9c6b7..da5653f 100644 --- a/volumes/proc/app.py +++ b/volumes/proc/app.py @@ -106,9 +106,24 @@ class HDF5File(): if self.first: self.pos_time = int(data['timestamp']) + self.timestamp = int(data['timestamp']) self.first = False self.raw = data + if True: + date_folder = datetime.fromtimestamp(self.timestamp).strftime('%Y-%m-%dT%H-00-00') + filelog = os.path.join(DATA_PATH, EXPERIMENT['name'], 'position', date_folder, "pos@%10.3f.txt" % (self.timestamp)) + if not os.path.exists(os.path.dirname(filelog)): + path = os.path.dirname(filelog) + os.makedirs(path) + f = open(filelog, 'w') + f.write(json.dumps(self.raw, cls=NumpyArrayEncoder)) + f.close() + + if int(data['timestamp'])<= self.timestamp: + print('Bad time') + return + self.update(data) if self.pos_ready: @@ -137,12 +152,7 @@ class HDF5File(): self.data_pos['timestamp'] = [] self.pos_ready = True - if DEBUG: - date_folder = datetime.fromtimestamp(self.timestamp).strftime('%Y-%m-%dT%H-00-00') - filelog = os.path.join(DATA_PATH, EXPERIMENT['name'], 'position', date_folder, "pos@%10.3f.txt" % (self.timestamp)) - f = open(filelog, 'w') - f.write(json.dumps(self.raw, cls=NumpyArrayEncoder)) - f.close() + HDF = HDF5File() @@ -272,6 +282,8 @@ def start_proc(): mqtt.publish('sophy/control', json.dumps(EXPERIMENT)) socketio.emit('mqtt_message', data={'topic':'monitor', 'status': 'Running', 'name': EXPERIMENT['name']}) + r = requests.post('http://sirm-schain/start', data=EXPERIMENT) + print('Starting schain: {}'.format(r)) return jsonify({'start': 'ok'}) @@ -285,6 +297,8 @@ def stop_proc(): HDF.reset() socketio.emit('mqtt_message', data={'topic':'monitor', 'status': 'Not Running'}) mqtt.publish('sophy/control', json.dumps({'stop': 'ok'})) + r = requests.get('http://sirm-schain/stop') + print('Stopping schain: {}'.format(r)) return jsonify({'stop': 'ok'}) @@ -315,12 +329,10 @@ def run_proc(): @app.route('/mqtt') def mqtt_log(): - return render_template('mqtt.html') @app.route('/acq') def acq_log(): - return render_template('acq.html') @socketio.on('publish') @@ -374,5 +386,4 @@ def handle_logging(client, userdata, level, buf): pass if __name__ == '__main__': - socketio.run(app, host='0.0.0.0', port=5000, use_reloader=False, debug=True) - + socketio.run(app, host='0.0.0.0', port=5000, use_reloader=False, debug=True) \ No newline at end of file diff --git a/volumes/proc/templates/acq.html b/volumes/proc/templates/acq.html new file mode 100644 index 0000000..786ea36 --- /dev/null +++ b/volumes/proc/templates/acq.html @@ -0,0 +1,63 @@ +{% extends "bootstrap/base.html" %} +{% block title %}SOPHY monitor{% endblock %} + +{% block styles %} +{{ super() }} +{% endblock %} + +{% block scripts %} +{{ super() }} + + +{% endblock %} + +{% block content %} +
+
+
+

SOPHy monitor

+
+
+
+ +
+
+
+

MQTT

+
+
+
+
+
+
+
+ + +
+
+
+
` +
+
+
+
+
+
+{{debug}} +{% endblock %} \ No newline at end of file diff --git a/volumes/proc/templates/index.html b/volumes/proc/templates/index.html index 299d4ed..f68800d 100644 --- a/volumes/proc/templates/index.html +++ b/volumes/proc/templates/index.html @@ -80,7 +80,7 @@ for (let i = 0; i < n; i++) { traces.push({x: [], y: [], name: names[i]}); } - var yrange = [0, 40]; + var yrange = [0, 50]; if (div == "plot-pos"){yrange = [0, 360];} if (div == "plot-speed"){yrange = [-15, 15];} var layout = { diff --git a/volumes/schain/realtime.py b/volumes/schain/realtime.py index 5502ec9..316da7d 100644 --- a/volumes/schain/realtime.py +++ b/volumes/schain/realtime.py @@ -13,11 +13,14 @@ from watchdog.events import FileSystemEventHandler EXP = sys.argv[1] main_path = '/DATA_RM/DATA/{}/plots'.format(EXP) -print(main_path) +if not os.path.exists(main_path): + os.makedirs(main_path) CODES = { 'V': 'Velocity', 'P': 'Power', + 'Z': 'Reflectivity', + 'W': 'Spectral Width' } @@ -27,7 +30,7 @@ DATA = { 'localtime': True, 'type': 'image', 'interval': 150, - 'tag' : 'Jicamarca' + 'tag' : 'Huancayo' }, 'data': '', 'plot': '', @@ -39,7 +42,8 @@ class FileHandler(FileSystemEventHandler): last = { 'V': 0, 'P': 0, - + 'Z': 0, + 'W': 0, } def on_modified(self, event): @@ -91,7 +95,7 @@ if __name__ == "__main__": print ("Connecting to server...") event.socket = event.context.socket(zmq.REQ) #event.socket.connect ("tcp://10.10.20.128:4444") - event.socket.connect ("tcp://10.10.110.243:4444") + event.socket.connect ("tcp://190.187.237.239:4444") observer = Observer() observer.schedule(event, main_path, recursive=True) diff --git a/volumes/schain/sophy_proc.py b/volumes/schain/sophy_proc.py index c35afd1..5731b43 100644 --- a/volumes/schain/sophy_proc.py +++ b/volumes/schain/sophy_proc.py @@ -1,96 +1,116 @@ -#!/opt/conda/bin/python +# SOPHY PROC script import os, sys, json, argparse import datetime import time - -PATH = '/data' +PATH = '/DATA_RM/DATA' +#PATH = '/data' +# PATH = '/Users/jespinoza/workspace/data/' PARAM = { - 'P': {'name': 'dataPP_POWER', 'zmin': 35, 'zmax': 60, 'colormap': 'viridis', 'label': 'Power', 'cb_label': 'dB'}, - 'V': {'name': 'dataPP_DOP', 'zmin': -20, 'zmax': 20, 'colormap': 'seismic', 'label': 'Velocity', 'cb_label': 'm/s'} -} + 'P': {'name': 'dataPP_POWER', 'zmin': 30, 'zmax': 60, 'colormap': 'jet', 'label': 'Power', 'wrname': 'Pow','cb_label': 'dB', 'ch':0}, + 'V': {'name': 'dataPP_DOP', 'zmin': -20, 'zmax': 20, 'colormap': 'seismic', 'label': 'Velocity', 'wrname': 'Vel', 'cb_label': 'm/s', 'ch':0}, + 'RH': {'name': 'RhoHV_R', 'zmin': 0, 'zmax': 1, 'colormap': 'jet', 'label': 'Coef.Correlacion', 'wrname':'R', 'cb_label': '*', 'ch':0}, + 'FD': {'name': 'PhiD_P', 'zmin': -180,'zmax': 180,'colormap': 'RdBu_r', 'label': 'Fase Diferencial', 'wrname':'P' , 'cb_label': 'ยบ', 'ch':0}, + 'ZD': {'name': 'Zdb_D', 'zmin': -20, 'zmax': 80, 'colormap': 'viridis','label': 'Reflect.Diferencial','wrname':'D' , 'cb_label': 'dBz','ch':0}, + 'Z': {'name': 'Zdb', 'zmin': -40, 'zmax': 80, 'colormap': 'viridis','label': 'Reflectividad', 'wrname':'Z', 'cb_label': 'dBz','ch':1}, + 'W': {'name': 'Sigmav_W', 'zmin': -20, 'zmax': 60, 'colormap': 'viridis','label': 'Spectral Width', 'wrname':'S', 'cb_label': 'hz', 'ch':1} + } + +def max_index(r, sample_rate, ipp): + + return int(sample_rate*ipp*1e6 * r / 60) + int(sample_rate*ipp*1e6 * 1.2 / 60) def main(args): experiment = args.experiment - fp = open(os.path.join(PATH, experiment, 'experiment.conf')) + fp = open(os.path.join(PATH, experiment, 'experiment.conf')) conf = json.loads(fp.read()) ipp_km = conf['usrp_tx']['ipp'] ipp = ipp_km * 2 /300000 - samp_rate = conf['usrp_rx']['sample_rate'] + sample_rate = conf['usrp_rx']['sample_rate'] axis = ['0' if x=='elevation' else '1' for x in conf['pedestal']['axis']] # AZIMUTH 1 ELEVACION 0 speed_axis = conf['pedestal']['speed'] - steeps = conf['pedestal']['table'] + steps = conf['pedestal']['table'] time_offset = args.time_offset parameters = args.parameters start_date = experiment.split('@')[1].split('T')[0].replace('-', '/') end_date = start_date - start_time = experiment.split('@')[1].split('T')[1].replace('-', ':') + if args.start_time: + start_time = args.start_time + else: + start_time = experiment.split('@')[1].split('T')[1].replace('-', ':') + #start_time = '13:00:00' end_time = '23:59:59' - max_index = int(samp_rate*ipp*1e6 * args.range / 60) + int(samp_rate*ipp*1e6 * 1.2 / 60) N = int(1/(speed_axis[0]*ipp)) # 1 GRADO DE RESOLUCION path = os.path.join(PATH, experiment, 'rawdata') path_ped = os.path.join(PATH, experiment, 'position') path_plots = os.path.join(PATH, experiment, 'plots') path_save = os.path.join(PATH, experiment, 'param') + RMIX = 5 - dBmin = 35 - dBmax = 60 - Vmin = -20 - Vmax = 20 - from schainpy.controller import Project - + project = Project() project.setup(id='1', name='Sophy', description='sophy proc') - + print(start_time) reader = project.addReadUnit(datatype='DigitalRFReader', path=path, startDate=start_date, endDate=end_date, - startTime=start_time, + start_time=start_time, endTime=end_time, - delay=0, - online=0, + delay=30, + online=args.online, walk=1, ippKm = ipp_km, getByBlock = 1, nProfileBlocks = N, ) - voltage = project.addProcUnit(datatype='VoltageProc', inputId=reader.getId()) - op = voltage.addOperation(name='setH0') - op.addParameter(name='h0', value='-1.2') + if not conf['usrp_tx']['enable_2']: # One Pulse + voltage = project.addProcUnit(datatype='VoltageProc', inputId=reader.getId()) - if args.range > 0: - op = voltage.addOperation(name='selectHeights') - op.addParameter(name='minIndex', value='0', format='int') - op.addParameter(name='maxIndex', value=max_index, format='int') + if conf['usrp_tx']['code_type_1']: + code = [c.split() for c in conf['usrp']['code_1']] + op = voltage.addOperation(name='Decoder', optype='other') + op.addParameter(name='code', value=code) + op.addParameter(name='nCode', value=len(code), format='int') + op.addParameter(name='nBaud', value=len(code[0]), format='int') - op = voltage.addOperation(name='PulsePair_vRF', optype='other') - op.addParameter(name='n', value=int(N), format='int') + op = voltage.addOperation(name='setH0') + op.addParameter(name='h0', value='-1.2') - proc = project.addProcUnit(datatype='ParametersProc', inputId=voltage.getId()) - - op = proc.addOperation(name='PedestalInformation') - op.addParameter(name='path', value=path_ped, format='str') - op.addParameter(name='interval', value='0.04', format='float') - op.addParameter(name='time_offset', value=time_offset) - op.addParameter(name='az_offset', value=0, format='int') - - for param in parameters: - - op = proc.addOperation(name='Block360_vRF4') - op.addParameter(name='axis', value=','.join(axis)) - op.addParameter(name='attr_data', value=PARAM[param]['name']) - op.addParameter(name='runNextOp', value=True) - - if axis[0] == '1': - path_fig = '/PPI-{}km'.format(args.range) - op= proc.addOperation(name='Weather_vRF_Plot') - if args.save: op.addParameter(name='save', value=path_plots+path_fig, format='str') + if args.range > 0: + op = voltage.addOperation(name='selectHeights') + op.addParameter(name='minIndex', value='0', format='int') + op.addParameter(name='maxIndex', value=max_index(RMIX, sample_rate, ipp), format='int') + + op = voltage.addOperation(name='PulsePair_vRF', optype='other') + op.addParameter(name='n', value=int(N), format='int') + + proc = project.addProcUnit(datatype='ParametersProc', inputId=voltage.getId()) + + opObj10 = proc.addOperation(name="WeatherRadar") + opObj10.addParameter(name='variableList',value='Reflectividad,VelocidadRadial,AnchoEspectral') + + # {"latitude": -12.0404828587, "longitude": -75.2147483647, "altitude": 3379.2147483647} + + op = proc.addOperation(name='PedestalInformation') + op.addParameter(name='path', value=path_ped, format='str') + op.addParameter(name='interval', value='0.04') + op.addParameter(name='time_offset', value=time_offset) + op.addParameter(name='az_offset', value=-26.2) + + for param in parameters: + op = proc.addOperation(name='Block360_vRF4') + #op.addParameter(name='axis', value=','.join(axis)) + op.addParameter(name='attr_data', value=PARAM[param]['name']) + op.addParameter(name='runNextOp', value=True) + + op= proc.addOperation(name='WeatherParamsPlot') + if args.save: op.addParameter(name='save', value=path_plots, format='str') op.addParameter(name='save_period', value=-1) op.addParameter(name='show', value=args.show) op.addParameter(name='channels', value='1,') @@ -101,13 +121,134 @@ def main(args): op.addParameter(name='save_code', value=param) op.addParameter(name='cb_label', value=PARAM[param]['cb_label']) op.addParameter(name='colormap', value=PARAM[param]['colormap']) - if axis[0] == '0': - path_fig = '/RHI{}km'.format(args.range) - op= proc.addOperation(name='WeatherRHI_vRF4_Plot') - if args.save: op.addParameter(name='save', value=path_plots+path_fig, format='str') + + desc = { + 'Data': { + PARAM[param]['name']: PARAM[param]['label'], + 'utctime': 'time' + }, + 'Metadata': { + 'heightList': 'range', + 'data_azi': 'azimuth', + 'data_ele': 'elevation', + } + } + + if args.save: + opObj10 = proc.addOperation(name='HDFWriter') + opObj10.addParameter(name='path',value=path_save+'-{}'.format(param), format='str') + opObj10.addParameter(name='Reset',value=True) + opObj10.addParameter(name='setType',value='weather') + opObj10.addParameter(name='description',value='desc') + opObj10.addParameter(name='blocksPerFile',value='1',format='int') + opObj10.addParameter(name='metadataList',value='heightList,data_azi,data_ele') + opObj10.addParameter(name='dataList',value='{},utctime'.format(PARAM[param]['name'])) + + else: #Two pulses + + voltage1 = project.addProcUnit(datatype='VoltageProc', inputId=reader.getId()) + + op = voltage1.addOperation(name='ProfileSelector') + op.addParameter(name='profileRangeList', value='0,{}'.format(conf['usrp_tx']['repetitions_1']-1)) + + if conf['usrp_tx']['code_type_1'] != 'None': + code = [c.split() for c in conf['usrp_tx']['code_1']] + op = voltage1.addOperation(name='Decoder', optype='other') + op.addParameter(name='code', value=code) + op.addParameter(name='nCode', value=len(code), format='int') + op.addParameter(name='nBaud', value=len(code[0]), format='int') + + op = voltage1.addOperation(name='setH0') + op.addParameter(name='h0', value='-1.2') + + if args.range > 0: + op = voltage1.addOperation(name='selectHeights') + op.addParameter(name='minIndex', value='0', format='int') + op.addParameter(name='maxIndex', value=max_index(RMIX, sample_rate, ipp), format='int') + + op = voltage1.addOperation(name='PulsePair_vRF', optype='other') + op.addParameter(name='n', value=int(N), format='int') + + proc1 = project.addProcUnit(datatype='ParametersProc', inputId=voltage1.getId()) + proc1.addParameter(name='runNextUnit', value=True) + + opObj10 = proc1.addOperation(name="WeatherRadar") + opObj10.addParameter(name='variableList',value='Reflectividad,VelocidadRadial,AnchoEspectral') + + # {"latitude": -12.0404828587, "longitude": -75.2147483647, "altitude": 3379.2147483647} + + op = proc1.addOperation(name='PedestalInformation') + op.addParameter(name='path', value=path_ped, format='str') + op.addParameter(name='interval', value='0.04') + op.addParameter(name='time_offset', value=time_offset) + op.addParameter(name='az_offset', value=-26.2) + + for param in parameters: + op = proc1.addOperation(name='Block360_vRF4') + op.addParameter(name='attr_data', value=PARAM[param]['name']) + op.addParameter(name='runNextOp', value=True) + + voltage2 = project.addProcUnit(datatype='VoltageProc', inputId=reader.getId()) + + op = voltage2.addOperation(name='ProfileSelector') + op.addParameter(name='profileRangeList', value='{},{}'.format(conf['usrp_tx']['repetitions_1'], conf['usrp_tx']['repetitions_1']+conf['usrp_tx']['repetitions_2']-1)) + + + if conf['usrp_tx']['code_type_2']: + codes = [ c.strip() for c in conf['usrp_tx']['code_2'].split(',')] + code = [] + for c in codes: + code.append([int(x) for x in c]) + op = voltage2.addOperation(name='Decoder', optype='other') + op.addParameter(name='code', value=code) + op.addParameter(name='nCode', value=len(code), format='int') + op.addParameter(name='nBaud', value=len(code[0]), format='int') + + op = voltage2.addOperation(name='CohInt', optype='other') #Minimo integrar 2 perfiles por ser codigo complementario + op.addParameter(name='n', value=len(code), format='int') + ncode = len(code) + else: + ncode = 1 + + op = voltage2.addOperation(name='setH0') + op.addParameter(name='h0', value='-1.2') + + if args.range > 0: + op = voltage2.addOperation(name='selectHeights') + op.addParameter(name='minIndex', value=max_index(RMIX, sample_rate, ipp), format='int') + op.addParameter(name='maxIndex', value=max_index(args.range, sample_rate, ipp), format='int') + + op = voltage2.addOperation(name='PulsePair_vRF', optype='other') + op.addParameter(name='n', value=int(N)/ncode, format='int') + + proc2 = project.addProcUnit(datatype='ParametersProc', inputId=voltage2.getId()) + + opObj10 = proc2.addOperation(name="WeatherRadar") + opObj10.addParameter(name='variableList',value='Reflectividad,AnchoEspectral') + + # {"latitude": -12.0404828587, "longitude": -75.2147483647, "altitude": 3379.2147483647} + + op = proc2.addOperation(name='PedestalInformation') + op.addParameter(name='path', value=path_ped, format='str') + op.addParameter(name='interval', value='0.04') + op.addParameter(name='time_offset', value=time_offset) + op.addParameter(name='az_offset', value=-26.2) + + for param in parameters: + op = proc2.addOperation(name='Block360_vRF4') + #op.addParameter(name='axis', value=','.join(axis)) + op.addParameter(name='attr_data', value=PARAM[param]['name']) + op.addParameter(name='runNextOp', value=True) + + merge = project.addProcUnit(datatype='MergeProc', inputId=[proc1.getId(), proc2.getId()]) + merge.addParameter(name='attr_data', value=PARAM[param]['name']) + merge.addParameter(name='mode', value='7') #RM + + op= merge.addOperation(name='WeatherParamsPlot') + if args.save: op.addParameter(name='save', value=path_plots, format='str') op.addParameter(name='save_period', value=-1) op.addParameter(name='show', value=args.show) - op.addParameter(name='channels', value='(1,)') + op.addParameter(name='channels', value='1,') op.addParameter(name='zmin', value=PARAM[param]['zmin']) op.addParameter(name='zmax', value=PARAM[param]['zmax']) op.addParameter(name='attr_data', value=PARAM[param]['name'], format='str') @@ -115,14 +256,28 @@ def main(args): op.addParameter(name='save_code', value=param) op.addParameter(name='cb_label', value=PARAM[param]['cb_label']) op.addParameter(name='colormap', value=PARAM[param]['colormap']) - - if args.save: - opObj10 = proc.addOperation(name='HDFWriter') - opObj10.addParameter(name='path',value=path_save, format='str') - opObj10.addParameter(name='Reset',value=True) - opObj10.addParameter(name='blocksPerFile',value='1',format='int') - opObj10.addParameter(name='metadataList',value='heightList,data_azi,data_ele') - opObj10.addParameter(name='dataList',value='dataPP_POWER,utctime') + + desc = { + 'Data': { + PARAM[param]['name']: PARAM[param]['label'], + 'utctime': 'time' + }, + 'Metadata': { + 'heightList': 'range', + 'data_azi': 'azimuth', + 'data_ele': 'elevation', + } + } + + if args.save: + opObj10 = merge.addOperation(name='HDFWriter') + opObj10.addParameter(name='path',value=path_save, format='str') + opObj10.addParameter(name='Reset',value=True) + opObj10.addParameter(name='setType',value='weather') + opObj10.addParameter(name='description',value='desc') + opObj10.addParameter(name='blocksPerFile',value='1',format='int') + opObj10.addParameter(name='metadataList',value='heightList,data_azi,data_ele') + opObj10.addParameter(name='dataList',value='{},utctime'.format(PARAM[param]['name'])) project.start() @@ -143,9 +298,10 @@ if __name__ == '__main__': help='Show matplotlib plot.') parser.add_argument('--online', action='store_true', help='Set online mode.') - parser.add_argument('--rti', action='store_true', - help='Set RTI plot.') + parser.add_argument('--start_time', default='', + help='Set start time.') - args = parser.parse_args() - main(args) + args = parser.parse_args() + print(args) + main(args) \ No newline at end of file diff --git a/volumes/sirm/apps/main/management/commands/reset_exp.py b/volumes/sirm/apps/main/management/commands/reset_exp.py new file mode 100644 index 0000000..cc151ac --- /dev/null +++ b/volumes/sirm/apps/main/management/commands/reset_exp.py @@ -0,0 +1,40 @@ +from django.core.management.base import BaseCommand +from apps.main.models import Experiment +from django.shortcuts import get_object_or_404 +import os +import time +import requests + +class Command(BaseCommand): + """ + Create a superuser if none exist + Example: + manage.py reset_exp --pk=1 + """ + + def handle(self, *args, **options): + if check_experiment(): + #value = 36 + #experiment = get_object_or_404(Experiment, pk=value) + ##time.sleep(15) + #experiment.stop() + #self.stdout.write(f'Experiment "{value}" was stoped') + #time.sleep(15) + #experiment.start() + #self.stdout.write(f'Experiment "{value}" is running') + value = 36 + self.stdout.write(f'Experiment "{value}" is running') + else: + pass + +def check_experiment(): + try: + url = 'http://{}/status'.format(os.environ.get('PROC_SITE', 'sophy-proc')) + response = requests.get(url, timeout=0.4) + if response.status_code == 200: + data = response.json() + return data['status'] + else: + return False + except: + return False \ No newline at end of file diff --git a/volumes/sirm/apps/pedestal/models.py b/volumes/sirm/apps/pedestal/models.py index ef4e741..7a2c733 100644 --- a/volumes/sirm/apps/pedestal/models.py +++ b/volumes/sirm/apps/pedestal/models.py @@ -1,4 +1,4 @@ -import ast +import os from datetime import datetime import json import requests @@ -127,7 +127,10 @@ class PedestalConfiguration(Configuration): payload_az = {'axis': 'azimuth'} if axi == 'elevation': - payload_az['position'] = angle + # CORRECT AZ OFFSET + azi = angle - float(os.environ.get('AZ_OFFSET', 26.27)) + if azi<0: azi += 360 + payload_az['position'] = round(azi, 2) payload_el['position'] = 0 elif axi == 'azimuth': payload_el['position'] = angle @@ -222,6 +225,14 @@ class PedestalConfiguration(Configuration): elif self.mode == 'table': url = self.device.url() + "combinedtable?params=" list_of_floats = [float(x.strip()) for x in self.angle.split(",")] + + # CORRECT AZ OFFSET + for i, ax in enumerate(axis): + if ax == 'elevation': + azi = list_of_floats[i] - float(os.environ.get('AZ_OFFSET', 26.27)) + if azi<0: azi += 360 + list_of_floats[i] = round(azi, 2) + byte_table = [] for x in list_of_floats: temp = bytearray(struct.pack("f", x)) @@ -282,4 +293,4 @@ class PedestalConfiguration(Configuration): return payload def get_absolute_url_import(self): - return reverse('url_import_pedestal_conf', args=[str(self.id)]) + return reverse('url_import_pedestal_conf', args=[str(self.id)]) \ No newline at end of file diff --git a/volumes/sirm/scripts/scheduler.py b/volumes/sirm/scripts/scheduler.py new file mode 100644 index 0000000..246ad42 --- /dev/null +++ b/volumes/sirm/scripts/scheduler.py @@ -0,0 +1,41 @@ +#!/usr/local/bin/python + +import os +import sys +from datetime import datetime, timedelta +from time import sleep +import django + +sys.path.append('/workspace/sirm') +os.environ.setdefault("DJANGO_SETTINGS_MODULE", "radarsys.settings") +django.setup() + +from apps.main.models import Experiment + +exp = Experiment.objects.get(pk=36) + +N = 0 +ok = True + +while True: + if N >=3: + ok = False + print('Stopping Experiment {}'.format(exp.name)) + exp.stop() + sleep(30) + print('Starting Experiment {}'.format(exp.name)) + exp.start() + dt = datetime.utcnow() + sleep(30) + path = os.path.join(exp.reception_rx.datadir, 'ch0', dt.strftime('%Y-%m-%dT%H-00-00')) + path = path.replace('DATA_RM/DATA', 'data') + if not os.path.exists(path): + N += 1 + continue + else: + break + +if ok: + print('Experiment started ok in {} try at {}!!!'.format(N+1, dt-timedelta(hours=5))) +else: + print('Error starting Experiment') \ No newline at end of file