cleanup, comments

This commit is contained in:
Georg Schlisio
2022-01-20 11:20:09 +01:00
parent 6be90ff148
commit 16912b627f
4 changed files with 4 additions and 1 deletions

View File

@@ -0,0 +1,122 @@
import time
import logging
class ParseMessage():
table_commands = ["Sensors", "EGains", "InletInfo", "DetectorInfo", "AnalogInputInfo",
"AnalogOutputInfo", "DigitalInfo", "SourceAlignmentInfo", "SourceResolutionInfo",
"DiagnosticInputInfo", "RunDiagnostics", ""]
verbose_commands = ["DiagnosticInput", "DigitalPortChange", "AnalogInput", "MassReading", "ZeroReading",
"StartingScan", "FilamentStatus", ""] # commands that feel special and don't submit to the usual pattern of command - status
def __init__(self, raw):
"""
Parse incoming binary message
:param raw: raw string
"""
self.time = time.time()
self.is_table = False
self.type = None
self.status = None
self.parms = {}
self.table_head = None
self.table_body = None
self.raw = raw
self.parse(raw)
def parse(self, raw):
"""
Parser for incoming messages.
:return:
"""
# split message at newline indicators and get rid of empty entries
linebyline = list(filter(None, raw.split("\r\n")))
# first line contains command and status or more
line1 = linebyline[0].split()
self.type = line1[0]
if self.type in self.table_commands:
self.is_table = True
if len(line1) == 1:
pass
elif len(line1) == 2:
self.type = line1[0]
self.status = line1[1]
else:
assert self.type in self.verbose_commands
self.parms[self.type] = line1[1:]
# terminate here for one-line commands
if len(linebyline) == 1:
return
# following lines
if self.is_table:
# for table commands we split table head and body
thead = linebyline[1].split()
try:
tbody = [linebyline[i].split() for i in range(len(linebyline[2:]))]
except IndexError:
logging.warning(f"Digesting message {self.type}: no table body found")
tbody = []
self.table_head = thead
self.table_body = tbody
else:
# for other commands we make a dictionary with key [values, ..]
try:
self.parms.update({line.split()[0]: line.split()[1:] for line in linebyline[1:]})
except IndexError:
raise NotImplementedError("this should not happen")
class ComposeMessage():
def __init__(self):
pass
def __call__(self, mtype, args=None):
"""
Compose raw byte string to send over ethernet
TODO: check argument type
TODO: make sure all commands fit the scheme
:param mtype: command as static string
:param args: list of argument strings (optional, default None)
:return: raw byte string
"""
assert isinstance(mtype, str)
#assert isinstance(args, list)
raw = mtype
if args is not None:
raw += " "+" ".join(args)
raw += "\r\n\r\r"
return raw.encode("ASCII")
if __name__ == "__main__":
sample_messages = {
"SensorState": 'SensorState OK\r\n State InUse\r\n UserApplication "Process Eye Professional"\r\n UserVersion V5.2\r\n UserAddress 127.0.0.1\r\n',
"Info": 'Info OK\r\n SerialNumber LM70-00197021\r\n Name "Chamber A"\r\n State Ready\r\n UserApplication N/A' +\
'\r\n UserVersion N/A\r\n UserAddress N/A\r\n ProductID 70 MicroVision+\r\n RFConfiguration 0 "Smart Head"' +\
'\r\n DetectorType 0 Faraday\r\n SEMSupply 3000 3.0kV\r\n ExternalHardware 0 None\r\n TotalPressureGauge 0 ' +\
'"Not Fitted"\r\n Page 13 of 158\r\n FilamentType 0 Tungsten\r\n ControlUnitUse 4 "Standard RGA"\r\n' +\
' SensorType 1 "Standard Open Source"\r\n InletType 1 None\r\n Version V3.70\r\n NumEGains 3\r\n' +\
' NumDigitalPorts 2\r\n NumAnalogInputs 4\r\n NumAnalogOutputs 1\r\n NumSourceSettings 6\r\n ' +\
'NumInlets 1\r\n MaxMass 200\r\n ActiveFilament 1\r\n FullScaleADCAmps 0.000002\r\n FullScaleADCCount' +\
' 8388608\r\n PeakResolution 32\r\n ConfigurableIonSource Yes\r\n RolloverCompensation No\r\n',
"EGains": 'EGains OK\r\n 1\r\n 100\r\n 20000\r\n',
"InletInfo": 'InletInfo OK\r\n Automatic Yes \r\nActiveInlet 0\r\n Factor Fixed CanCalibrate DefaultFactor TypeName\r\n 1 Yes No 1 "Process Chamber direct"\r\n',
"Release": "Release Ok\r\n",
#"AcceptProtocol":
"initiate": "MKSRGA Single\r\n Protocol_Revision 1.1\r\n Min_Compatibility 1.1\r\n\r\n",
"Error": 'command ERROR\r\n Number 200\r\n Description "err description"\r\n\r\n',
"Sensors": "Sensors OK\r\n State SerialNumber Name\r\n Ready LM70-00197021 “Chamber A”\r\n Ready LM70-00198021 “Chamber B”\r\n\r\n",
"DiagnosticInput": "DiagnosticInput 0 3.2745\r\n\r\n",
"FilamentStatus": "FilamentStatus 1 OFF\r\n Trip None\r\n Drive Off\r\n EmissionTripState OK\r\n ExternalTripState OK\r\n RVCTripState OK",
}
cm = ComposeMessage()
#bmess = cm(mtype="Select", args=["LM70-00197021"])
#smess = bmess.decode("ASCII")
for m in sample_messages:
pm = ParseMessage(sample_messages[m])
print(pm.type, pm.status, pm.is_table)
#print(pm.type, pm.parms, pm.time)