improve set_instrument
- this still needs some checks
This commit is contained in:
34
secop.py
34
secop.py
@ -3,6 +3,7 @@ import os
|
||||
import json
|
||||
import time
|
||||
import socket
|
||||
from collections import namedtuple
|
||||
from select import select
|
||||
from streams import Stream, Base, StreamDead
|
||||
|
||||
@ -24,6 +25,9 @@ class TagsDict(dict):
|
||||
return self.default_value
|
||||
|
||||
|
||||
ParamInfo = namedtuple('ParamInfo', ['cvt', 'key', 'tags'])
|
||||
|
||||
|
||||
class SecopStream(Stream):
|
||||
ping_time = 0
|
||||
|
||||
@ -57,17 +61,23 @@ class SecopStream(Stream):
|
||||
self.param_info = {}
|
||||
self.tags_dict = TagsDict(self.tags)
|
||||
for mod, moddesc in self.modules.items():
|
||||
mod_tags = None
|
||||
for key in ('_original_id', 'original_id'):
|
||||
value = moddesc.get(key)
|
||||
if value:
|
||||
self.tags_dict[mod] = dict(self.tags, device=value)
|
||||
mod_tags = dict(self.tags, device=value)
|
||||
break
|
||||
parameters = moddesc['accessibles']
|
||||
for param, desc in parameters.items():
|
||||
dt = desc['datainfo']
|
||||
if dt['type'] in ('double', 'int', 'enum'):
|
||||
stripped = param[1:] if param.startswith('_') else param
|
||||
self.param_info[mod, param] = float, (mod, param if stripped in parameters else stripped)
|
||||
unit = dt.get('unit')
|
||||
tags = self.tags or mod_tags
|
||||
if unit:
|
||||
tags = dict(tags, unit=unit)
|
||||
key = mod, (param if stripped in parameters else stripped)
|
||||
self.param_info[mod, param] = ParamInfo(float, key, tags)
|
||||
self.send('activate')
|
||||
|
||||
def ping(self):
|
||||
@ -83,27 +93,26 @@ class SecopStream(Stream):
|
||||
if match:
|
||||
cmd, ident, data = match.groups()
|
||||
mod, _, param = ident.partition(':')
|
||||
cvt_key = self.param_info.get((mod, param or 'value'))
|
||||
if cvt_key:
|
||||
cvt, key = cvt_key
|
||||
pinfo = self.param_info.get((mod, param or 'value'))
|
||||
if pinfo:
|
||||
data = json.loads(data)
|
||||
tags = self.tags_dict[key[0]]
|
||||
tags = self.tags_dict[pinfo.key[0]]
|
||||
if cmd == 'error_update':
|
||||
error = ': '.join(data[0:2])
|
||||
print(msg, repr(error))
|
||||
# print(msg, repr(error))
|
||||
timestamp = data[2].get('t', time.time())
|
||||
yield 'error', error, key, tags, timestamp
|
||||
yield 'error', error, pinfo.key, pinfo.tags, timestamp
|
||||
else:
|
||||
value = cvt(data[0])
|
||||
value = pinfo.cvt(data[0])
|
||||
timestamp = data[1].get('t', time.time())
|
||||
yield 'value', value, key, tags, timestamp
|
||||
yield 'value', value, pinfo.key, pinfo.tags, timestamp
|
||||
elif msg == 'active':
|
||||
# from now on, no more waiting
|
||||
self.notimeout()
|
||||
|
||||
except Exception as e:
|
||||
# probably other end closed
|
||||
print(self.uri, repr(e))
|
||||
raise
|
||||
|
||||
|
||||
SECOP_UDP_PORT = 10767
|
||||
@ -118,6 +127,7 @@ class UdpStream(Base):
|
||||
msg, addr = self.socket.recvfrom(1024)
|
||||
except socket.error: # pragma: no cover
|
||||
return None
|
||||
addr = socket.getnameinfo(addr, socket.NI_NOFQDN)[0]
|
||||
msg = json.loads(msg.decode('utf-8'))
|
||||
kind = msg.pop('SECoP', None)
|
||||
if not kind:
|
||||
@ -128,7 +138,7 @@ class UdpStream(Base):
|
||||
# msg['device'] = uri.split('://', 1)[-1].split(':')[0]
|
||||
kwargs = msg
|
||||
elif kind == 'node':
|
||||
uri = f"{addr[0]}:{msg['port']}"
|
||||
uri = f"{addr}:{msg['port']}"
|
||||
kwargs = {'name': msg['equipment_id']}
|
||||
else:
|
||||
continue
|
||||
|
Reference in New Issue
Block a user