From 45ee8dbb32b24c3b5dcddbb8e77610f7e09f66c7 Mon Sep 17 00:00:00 2001 From: Nigel Dokter Date: Sun, 22 Jan 2017 16:39:16 +0100 Subject: [PATCH] added basic config for DSMR v5 specification; added DSMR v5 example telegram for testing; --- dsmr_parser/obis_references.py | 3 +- dsmr_parser/telegram_specifications.py | 47 +++++++++++++++++++++++--- test/example_telegrams.py | 43 +++++++++++++++++++++++ test/test_parse_v5.py | 21 ++++++++++++ 4 files changed, 109 insertions(+), 5 deletions(-) create mode 100644 test/test_parse_v5.py diff --git a/dsmr_parser/obis_references.py b/dsmr_parser/obis_references.py index 392b83c..40475ec 100644 --- a/dsmr_parser/obis_references.py +++ b/dsmr_parser/obis_references.py @@ -34,8 +34,9 @@ INSTANTANEOUS_ACTIVE_POWER_L1_NEGATIVE = r'\d-\d:22\.7\.0.+?\r\n' INSTANTANEOUS_ACTIVE_POWER_L2_NEGATIVE = r'\d-\d:42\.7\.0.+?\r\n' INSTANTANEOUS_ACTIVE_POWER_L3_NEGATIVE = r'\d-\d:62\.7\.0.+?\r\n' EQUIPMENT_IDENTIFIER_GAS = r'\d-\d:96\.1\.0.+?\r\n' +# TODO HOURLY_GAS_METER_READING = r'\d-\d:24\.2\.1.+?\r\n' -GAS_METER_READING = r'\d-\d:24\.3\.0.+?\r\n.+?\r\n' +GAS_METER_READING = r'(\d-\d:24\.3\.0.+?\r\n.+?\r\n)' ACTUAL_TRESHOLD_ELECTRICITY = r'\d-\d:17\.0\.0.+?\r\n' ACTUAL_SWITCH_POSITION = r'\d-\d:96\.3\.10.+?\r\n' VALVE_POSITION_GAS = r'\d-\d:24\.4\.0.+?\r\n' diff --git a/dsmr_parser/telegram_specifications.py b/dsmr_parser/telegram_specifications.py index b4f48c2..fc6c662 100644 --- a/dsmr_parser/telegram_specifications.py +++ b/dsmr_parser/telegram_specifications.py @@ -15,7 +15,7 @@ how the telegram lines are parsed. V2_2 = { 'checksum_support': False, - 'objects': { + 'object_signatures': { obis.EQUIPMENT_IDENTIFIER: CosemParser(ValueParser(str)), obis.ELECTRICITY_USED_TARIFF_1: CosemParser(ValueParser(Decimal)), obis.ELECTRICITY_USED_TARIFF_2: CosemParser(ValueParser(Decimal)), @@ -47,12 +47,12 @@ V4 = { 'objects': { obis.P1_MESSAGE_HEADER: CosemParser(ValueParser(str)), obis.P1_MESSAGE_TIMESTAMP: CosemParser(ValueParser(timestamp)), + obis.EQUIPMENT_IDENTIFIER: CosemParser(ValueParser(str)), obis.ELECTRICITY_USED_TARIFF_1: CosemParser(ValueParser(Decimal)), obis.ELECTRICITY_USED_TARIFF_2: CosemParser(ValueParser(Decimal)), obis.ELECTRICITY_DELIVERED_TARIFF_1: CosemParser(ValueParser(Decimal)), obis.ELECTRICITY_DELIVERED_TARIFF_2: CosemParser(ValueParser(Decimal)), obis.ELECTRICITY_ACTIVE_TARIFF: CosemParser(ValueParser(str)), - obis.EQUIPMENT_IDENTIFIER: CosemParser(ValueParser(str)), obis.CURRENT_ELECTRICITY_USAGE: CosemParser(ValueParser(Decimal)), obis.CURRENT_ELECTRICITY_DELIVERY: CosemParser(ValueParser(Decimal)), obis.LONG_POWER_FAILURE_COUNT: CosemParser(ValueParser(int)), @@ -73,7 +73,46 @@ V4 = { obis.INSTANTANEOUS_ACTIVE_POWER_L2_NEGATIVE: CosemParser(ValueParser(Decimal)), obis.INSTANTANEOUS_ACTIVE_POWER_L3_NEGATIVE: CosemParser(ValueParser(Decimal)), obis.EQUIPMENT_IDENTIFIER_GAS: CosemParser(ValueParser(str)), - obis.HOURLY_GAS_METER_READING: MBusParser(ValueParser(timestamp), - ValueParser(Decimal)) + obis.HOURLY_GAS_METER_READING: MBusParser( + ValueParser(timestamp), + ValueParser(Decimal) + ) + } +} + +V5 = { + 'checksum_support': True, + 'objects': { + obis.P1_MESSAGE_HEADER: CosemParser(ValueParser(str)), + obis.P1_MESSAGE_TIMESTAMP: CosemParser(ValueParser(timestamp)), + obis.EQUIPMENT_IDENTIFIER: CosemParser(ValueParser(str)), + obis.ELECTRICITY_USED_TARIFF_1: CosemParser(ValueParser(Decimal)), + obis.ELECTRICITY_USED_TARIFF_2: CosemParser(ValueParser(Decimal)), + obis.ELECTRICITY_DELIVERED_TARIFF_1: CosemParser(ValueParser(Decimal)), + obis.ELECTRICITY_DELIVERED_TARIFF_2: CosemParser(ValueParser(Decimal)), + obis.ELECTRICITY_ACTIVE_TARIFF: CosemParser(ValueParser(str)), + obis.CURRENT_ELECTRICITY_USAGE: CosemParser(ValueParser(Decimal)), + obis.CURRENT_ELECTRICITY_DELIVERY: CosemParser(ValueParser(Decimal)), + obis.LONG_POWER_FAILURE_COUNT: CosemParser(ValueParser(int)), + # POWER_EVENT_FAILURE_LOG: ProfileGenericParser(), TODO + obis.VOLTAGE_SAG_L1_COUNT: CosemParser(ValueParser(int)), + obis.VOLTAGE_SAG_L2_COUNT: CosemParser(ValueParser(int)), + obis.VOLTAGE_SAG_L3_COUNT: CosemParser(ValueParser(int)), + obis.VOLTAGE_SWELL_L1_COUNT: CosemParser(ValueParser(int)), + obis.VOLTAGE_SWELL_L2_COUNT: CosemParser(ValueParser(int)), + obis.VOLTAGE_SWELL_L3_COUNT: CosemParser(ValueParser(int)), + obis.TEXT_MESSAGE: CosemParser(ValueParser(str)), + obis.DEVICE_TYPE: CosemParser(ValueParser(int)), + obis.INSTANTANEOUS_ACTIVE_POWER_L1_POSITIVE: CosemParser(ValueParser(Decimal)), + obis.INSTANTANEOUS_ACTIVE_POWER_L2_POSITIVE: CosemParser(ValueParser(Decimal)), + obis.INSTANTANEOUS_ACTIVE_POWER_L3_POSITIVE: CosemParser(ValueParser(Decimal)), + obis.INSTANTANEOUS_ACTIVE_POWER_L1_NEGATIVE: CosemParser(ValueParser(Decimal)), + obis.INSTANTANEOUS_ACTIVE_POWER_L2_NEGATIVE: CosemParser(ValueParser(Decimal)), + obis.INSTANTANEOUS_ACTIVE_POWER_L3_NEGATIVE: CosemParser(ValueParser(Decimal)), + obis.EQUIPMENT_IDENTIFIER_GAS: CosemParser(ValueParser(str)), + obis.HOURLY_GAS_METER_READING: MBusParser( + ValueParser(timestamp), + ValueParser(Decimal) + ) } } diff --git a/test/example_telegrams.py b/test/example_telegrams.py index eb4e8d4..55e7897 100644 --- a/test/example_telegrams.py +++ b/test/example_telegrams.py @@ -60,3 +60,46 @@ TELEGRAM_V4_2 = ( '0-1:24.2.1(161129200000W)(00981.443*m3)\r\n' '!6796\r\n' ) + +TELEGRAM_V5 = ( + '/ISk5\2MT382-1000\r\n' + '\r\n' + '1-3:0.2.8(50)\r\n' + '0-0:1.0.0(170102192002W)\r\n' + '0-0:96.1.1(4B384547303034303436333935353037)\r\n' + '1-0:1.8.1(000004.426*kWh)\r\n' + '1-0:1.8.2(000002.399*kWh)\r\n' + '1-0:2.8.1(000002.444*kWh)\r\n' + '1-0:2.8.2(000000.000*kWh)\r\n' + '0-0:96.14.0(0002)\r\n' + '1-0:1.7.0(00.244*kW)\r\n' + '1-0:2.7.0(00.000*kW)\r\n' + '0-0:96.7.21(00013)\r\n' + '0-0:96.7.9(00000)\r\n' + '1-0:99.97.0(0)(0-0:96.7.19)\r\n' + '1-0:32.32.0(00000)\r\n' + '1-0:52.32.0(00000)\r\n' + '1-0:72.32.0(00000)\r\n' + '1-0:32.36.0(00000)\r\n' + '1-0:52.36.0(00000)\r\n' + '1-0:72.36.0(00000)\r\n' + '0-0:96.13.0()\r\n' + '1-0:32.7.0(0230.0*V)\r\n' + '1-0:52.7.0(0230.0*V)\r\n' + '1-0:72.7.0(0229.0*V)\r\n' + '1-0:31.7.0(0.48*A)\r\n' + '1-0:51.7.0(0.44*A)\r\n' + '1-0:71.7.0(0.86*A)\r\n' + '1-0:21.7.0(00.070*kW)\r\n' + '1-0:41.7.0(00.032*kW)\r\n' + '1-0:61.7.0(00.142*kW)\r\n' + '1-0:22.7.0(00.000*kW)\r\n' + '1-0:42.7.0(00.000*kW)\r\n' + '1-0:62.7.0(00.000*kW)\r\n' + '0-1:24.1.0(003)\r\n' + '0-1:96.1.0(3232323241424344313233343536373839)\r\n' + '0-1:24.2.1(170102161005W)(00000.107*m3)\r\n' + '0-2:24.1.0(003)\r\n' + '0-2:96.1.0()\r\n' + '!87B3\r\n' +) diff --git a/test/test_parse_v5.py b/test/test_parse_v5.py new file mode 100644 index 0000000..b337e20 --- /dev/null +++ b/test/test_parse_v5.py @@ -0,0 +1,21 @@ +import unittest + +from dsmr_parser import obis_references as obis +from dsmr_parser import telegram_specifications +from dsmr_parser.objects import CosemObject +from dsmr_parser.parsers import TelegramParser +from test.example_telegrams import TELEGRAM_V5 + + +class TelegramParserV5Test(unittest.TestCase): + """ Test parsing of a DSMR v5.x telegram. """ + + def test_parse(self): + parser = TelegramParser(telegram_specifications.V5) + result = parser.parse(TELEGRAM_V5) + + # P1_MESSAGE_HEADER (1-3:0.2.8) + assert isinstance(result[obis.P1_MESSAGE_HEADER], CosemObject) + assert result[obis.P1_MESSAGE_HEADER].unit is None + assert isinstance(result[obis.P1_MESSAGE_HEADER].value, str) + assert result[obis.P1_MESSAGE_HEADER].value == '50'