From 68f73b5aa162d2cec8c1c6f4802d4aa59035974a Mon Sep 17 00:00:00 2001 From: Enrico Faulhaber Date: Wed, 21 Dec 2016 16:59:32 +0100 Subject: [PATCH] Fix some bugs. - Commandreplies format their timestamp like events Change-Id: I388b9f26bb8b0234d9209b05732e98f9ce1d01c7 --- secop/client/baseclient.py | 42 +++++++++++++++++++++--------- secop/protocol/dispatcher.py | 9 ++----- secop/protocol/encoding/demo_v4.py | 8 +++++- secop/protocol/messages.py | 1 + 4 files changed, 39 insertions(+), 21 deletions(-) diff --git a/secop/client/baseclient.py b/secop/client/baseclient.py index 62c6a65..412ac59 100644 --- a/secop/client/baseclient.py +++ b/secop/client/baseclient.py @@ -132,7 +132,7 @@ class Value(object): class Client(object): - equipmentId = 'unknown' + equipment_id = 'unknown' secop_id = 'unknown' describing_data = {} stopflag = False @@ -182,12 +182,12 @@ class Client(object): def _inner_run(self): data = '' self.connection.writeline('*IDN?') - idstring = self.connection.readline() - self.log.info('connected to: ' + idstring.strip()) while not self.stopflag: line = self.connection.readline() + self.log.debug('got answer %r' % line) if line.startswith(('SECoP', 'Sine2020WP7')): + self.log.info('connected to: ' + line.strip()) self.secop_id = line continue msgtype, spec, data = self._decode_message(line) @@ -196,12 +196,20 @@ class Client(object): self._handle_event(spec, data) if msgtype != 'event': # handle sync stuff - if msgtype == "ERROR" or msgtype in self.expected_replies: - # XXX: make an assignment of ERROR to an expected reply. + if msgtype in self.expected_replies: entry = self.expected_replies[msgtype] - entry.extend([spec, data]) + entry.extend([msgtype, spec, data]) # wake up calling process entry[0].set() + elif msgtype == "ERROR": + # XXX: hack! + if len(self.expected_replies) == 1: + entry = self.expected_replies.values()[0] + entry.extend([msgtype, spec, data]) + # wake up calling process + entry[0].set() + # XXX: make an assignment of ERROR to an expected reply. + self.log.error('TODO: handle ERROR replies!') else: self.log.error('ignoring unexpected reply %r' % line) @@ -234,7 +242,7 @@ class Client(object): def _handle_event(self, spec, data): """handles event""" - self.log.info('handle_event %r %r' % (spec, data)) + self.log.debug('handle_event %r %r' % (spec, data)) if ':' not in spec: self.log.warning("deprecated specifier %r" % spec) spec = '%s:value' % spec @@ -281,7 +289,7 @@ class Client(object): "activate": "active", "deactivate": "inactive", "*IDN?": "SECoP,", - "ping": "ping", + "ping": "pong", } if self.stopflag: raise RuntimeError('alreading stopping!') @@ -306,14 +314,18 @@ class Client(object): "can not have more than one requests of the same type at the same time!") event = threading.Event() self.expected_replies[rply] = [event] + self.log.debug('prepared reception of %r msg' % rply) self.connection.writeline(self._encode_message(msgtype, spec, data)) + self.log.debug('sent %r msg' % msgtype) if event.wait(10): # wait 10s for reply - result = rply, self.expected_replies[rply][ - 1], self.expected_replies[rply][2] + self.log.debug('checking reply') + result = self.expected_replies[rply][1:4] del self.expected_replies[rply] +# if result[0] == "ERROR": +# raise RuntimeError('Got %s! %r' % (str(result[1]), repr(result[2]))) return result del self.expected_replies[rply] - raise RuntimeError("timeout upon waiting for reply!") + raise RuntimeError("timeout upon waiting for reply to %r!" % msgtype) def quit(self): # after calling this the client is dysfunctional! @@ -339,6 +351,10 @@ class Client(object): if not async: self.communicate('deactivate') + @property + def equipmentId(self): + return self.equipment_id + @property def protocolVersion(self): return self.secop_id @@ -360,5 +376,5 @@ class Client(object): return self.describing_data['modules'][ module]['parameters'][parameter].items() - def syncCommunicate(self, msg): - return self.communicate(msg) + def syncCommunicate(self, *msg): + return self.communicate(*msg) diff --git a/secop/protocol/dispatcher.py b/secop/protocol/dispatcher.py index cc63836..2cc8238 100644 --- a/secop/protocol/dispatcher.py +++ b/secop/protocol/dispatcher.py @@ -241,13 +241,8 @@ class Dispatcher(object): # note: exceptions are handled in handle_request, not here! func = getattr(moduleobj, 'do' + command) res = func(*arguments) - res = CommandReply( - module=modulename, - command=command, - result=[ - res, - dict( - t=time.time())]) + res = CommandReply(module=modulename, command=command, + result=res, qualifiers=dict(t=time.time())) # res = Value(modulename, command=command, value=func(*arguments), t=time.time()) return res diff --git a/secop/protocol/encoding/demo_v4.py b/secop/protocol/encoding/demo_v4.py index 54f6c13..49a80d7 100644 --- a/secop/protocol/encoding/demo_v4.py +++ b/secop/protocol/encoding/demo_v4.py @@ -76,6 +76,12 @@ ERRORCLASSES = ['NoSuchDevice', 'NoSuchParameter', 'NoSuchCommand', # starts with another +def encode_cmd_result(msgobj): + q = msgobj.qualifiers.copy() + if 't' in q: + q['t'] = format_time(q['t']) + return msgobj.result, q + def encode_value_data(vobj): q = vobj.qualifiers.copy() if 't' in q: @@ -95,7 +101,7 @@ class DemoEncoder(MessageEncoder): DeactivateRequest: (DISABLEEVENTSREQUEST,), DeactivateReply: (DISABLEEVENTSREPLY,), CommandRequest: (COMMANDREQUEST, lambda msg: "%s:%s" % (msg.module, msg.command), 'arguments',), - CommandReply: (COMMANDREPLY, lambda msg: "%s:%s" % (msg.module, msg.command), 'result',), + CommandReply: (COMMANDREPLY, lambda msg: "%s:%s" % (msg.module, msg.command), encode_cmd_result,), WriteRequest: (WRITEREQUEST, lambda msg: "%s:%s" % (msg.module, msg.parameter) if msg.parameter else msg.module, 'value',), WriteReply: (WRITEREPLY, lambda msg: "%s:%s" % (msg.module, msg.parameter) if msg.parameter else msg.module, 'value',), PollRequest: (TRIGGERREQUEST, lambda msg: "%s:%s" % (msg.module, msg.parameter) if msg.parameter else msg.module, ), diff --git a/secop/protocol/messages.py b/secop/protocol/messages.py index ede948a..668e005 100644 --- a/secop/protocol/messages.py +++ b/secop/protocol/messages.py @@ -28,6 +28,7 @@ class Message(object): is_request = False is_reply = False is_error = False + qualifiers = {} def __init__(self, **kwds): self.ARGS = set()