Compare commits
18
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
6c4f058cf6 | ||
|
|
34f419d10f | ||
|
|
a73585c862 | ||
|
|
9a3d7e2a85 | ||
|
|
04c4f68242 | ||
|
|
26563c8e7e | ||
|
|
0270b61d15 | ||
|
|
94189b6b63 | ||
|
|
8829260b15 | ||
|
|
55ac551a2a | ||
|
|
fc65326370 | ||
|
|
059c0802ad | ||
|
|
d7f30b5069 | ||
|
|
b42ceb6555 | ||
|
|
3cf627eedc | ||
|
|
d680d44683 | ||
|
|
6387cc4440 | ||
|
|
61985c5c89 |
@@ -21,15 +21,15 @@ jobs:
|
|||||||
|
|
||||||
name: Python ${{ matrix.python-version }}
|
name: Python ${{ matrix.python-version }}
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@v3
|
- uses: actions/checkout@v4
|
||||||
|
|
||||||
- name: Setup Python ${{ matrix.python-version }}
|
- name: Setup Python ${{ matrix.python-version }}
|
||||||
uses: actions/setup-python@v2
|
uses: actions/setup-python@v5
|
||||||
with:
|
with:
|
||||||
python-version: ${{ matrix.python-version }}
|
python-version: ${{ matrix.python-version }}
|
||||||
|
|
||||||
- name: Cached PIP dependencies
|
- name: Cached PIP dependencies
|
||||||
uses: actions/cache@v3
|
uses: actions/cache@v4
|
||||||
with:
|
with:
|
||||||
path: |
|
path: |
|
||||||
~/.cache/pip
|
~/.cache/pip
|
||||||
@@ -44,4 +44,4 @@ jobs:
|
|||||||
run: tox
|
run: tox
|
||||||
|
|
||||||
- name: Code coverage upload
|
- name: Code coverage upload
|
||||||
uses: codecov/codecov-action@v3
|
uses: codecov/codecov-action@v4
|
||||||
|
|||||||
+19
-13
@@ -1,30 +1,36 @@
|
|||||||
Change Log
|
Change Log
|
||||||
----------
|
----------
|
||||||
|
|
||||||
**1.4.0** (2024-03-12)
|
**1.4.2** (2024-07-14)
|
||||||
- Q3D add CURRENT_ELECTRICITY_DELIVERY
|
|
||||||
(`PR #149 <https://github.com/ndokter/dsmr_parser/pull/149>`_ by `Aeroid <https://github.com/Aeroid>`_)
|
|
||||||
- Copy head_parsers list on construct.
|
|
||||||
(`PR #150 <https://github.com/ndokter/dsmr_parser/pull/150>`_ by `dupondje <https://github.com/dupondje>`_)
|
|
||||||
|
|
||||||
|
- Bump Github Actions to latest versions in favor of Node deprecations (`PR #159 <https://github.com/ndokter/dsmr_parser/pull/159>`_ by `dennissiemensma <https://github.com/dennissiemensma>`_)
|
||||||
|
- Swap pyserial-asyncio for pyserial-asyncio-fast (`PR #158 <https://github.com/ndokter/dsmr_parser/pull/158>`_ by `bdraco <https://github.com/bdraco>`_)
|
||||||
|
|
||||||
|
**1.4.1** (2024-06-04)
|
||||||
|
|
||||||
|
- Avoid loading timezone at runtime (`PR #157 <https://github.com/ndokter/dsmr_parser/pull/157>`_ by `elupus <https://github.com/elupus>`_)
|
||||||
|
|
||||||
|
**1.4.0** (2024-03-12)
|
||||||
|
|
||||||
|
- Mbus alt (`PR #142 <https://github.com/ndokter/dsmr_parser/pull/142>`_ by `dupondje <https://github.com/dupondje>`_)
|
||||||
|
- Q3D add CURRENT_ELECTRICITY_DELIVERY (`PR #149 <https://github.com/ndokter/dsmr_parser/pull/149>`_ by `Aeroid <https://github.com/Aeroid>`_)
|
||||||
|
- Copy head_parsers list on construct. (`PR #150 <https://github.com/ndokter/dsmr_parser/pull/150>`_ by `dupondje <https://github.com/dupondje>`_)
|
||||||
|
|
||||||
**1.3.2** (2024-01-29)
|
**1.3.2** (2024-01-29)
|
||||||
- Fix unit test for pyton 3.12
|
|
||||||
(`PR #148 <https://github.com/ndokter/dsmr_parser/pull/148>`_ by `ndokter <https://github.com/ndokter>`_)
|
- Fix unit test for pyton 3.12 (`PR #148 <https://github.com/ndokter/dsmr_parser/pull/148>`_ by `ndokter <https://github.com/ndokter>`_)
|
||||||
|
|
||||||
**1.3.1** (2023-11-06)
|
**1.3.1** (2023-11-06)
|
||||||
- Fix parsing peak usage with invalid timestamps
|
|
||||||
(`PR #143 <https://github.com/ndokter/dsmr_parser/pull/143>`_ by `dupondje <https://github.com/dupondje>`_)
|
- Fix parsing peak usage with invalid timestamps (`PR #143 <https://github.com/ndokter/dsmr_parser/pull/143>`_ by `dupondje <https://github.com/dupondje>`_)
|
||||||
|
|
||||||
**1.3.0** (2023-08-01)
|
**1.3.0** (2023-08-01)
|
||||||
|
|
||||||
- added E.ON Hungary; refactored DSMR specifications to fix obis reference conflicts
|
- added E.ON Hungary; refactored DSMR specifications to fix obis reference conflicts (`PR #137 <https://github.com/ndokter/dsmr_parser/pull/137>`_ by `balazs92117 <https://github.com/balazs92117>`_)
|
||||||
(`PR #137 <https://github.com/ndokter/dsmr_parser/pull/137>`_ by `balazs92117 <https://github.com/balazs92117>`_)
|
|
||||||
|
|
||||||
**1.2.4** (2023-07-11)
|
**1.2.4** (2023-07-11)
|
||||||
|
|
||||||
- EQUIPMENT IDENTIFIER is wrong for Fluvius meters when other mbus devices are present
|
- EQUIPMENT IDENTIFIER is wrong for Fluvius meters when other mbus devices are present (`PR #133 <https://github.com/ndokter/dsmr_parser/pull/133>`_ by `ejpalacios <https://github.com/ejpalacios>`_)
|
||||||
(`PR #133 <https://github.com/ndokter/dsmr_parser/pull/133>`_ by `ejpalacios <https://github.com/ejpalacios>`_)
|
|
||||||
|
|
||||||
|
|
||||||
**1.2.3** (2023-04-18)
|
**1.2.3** (2023-04-18)
|
||||||
|
|||||||
+30
@@ -293,6 +293,36 @@ To install DSMR Parser:
|
|||||||
|
|
||||||
$ pip install dsmr-parser
|
$ pip install dsmr-parser
|
||||||
|
|
||||||
|
Development
|
||||||
|
-----------
|
||||||
|
|
||||||
|
Create a virtualenv and activate it followed by the installation of the dsmr-parser:
|
||||||
|
|
||||||
|
.. code-block:: bash
|
||||||
|
|
||||||
|
python3 -m venv venv
|
||||||
|
source venv/bin/activate
|
||||||
|
pip install -e .
|
||||||
|
|
||||||
|
Install tox and run it:
|
||||||
|
|
||||||
|
.. code-block:: bash
|
||||||
|
|
||||||
|
pip install tox
|
||||||
|
tox
|
||||||
|
|
||||||
|
You should see that the tests have succeeded:
|
||||||
|
|
||||||
|
.. code-block:: text
|
||||||
|
|
||||||
|
======================================================================================================== 59 passed in 0.91s ========================================================================================================
|
||||||
|
py: commands[1]> pylama dsmr_parser test
|
||||||
|
py: OK (11.55=setup[9.73]+cmd[1.29,0.53] seconds)
|
||||||
|
congratulations :) (11.69 seconds)
|
||||||
|
|
||||||
|
|
||||||
|
Now you can make changes by editing the code and rerunning tox to verify your changes.
|
||||||
|
|
||||||
Known issues
|
Known issues
|
||||||
------------
|
------------
|
||||||
|
|
||||||
|
|||||||
@@ -73,7 +73,7 @@ class FileReader(object):
|
|||||||
try:
|
try:
|
||||||
yield self.telegram_parser.parse(telegram)
|
yield self.telegram_parser.parse(telegram)
|
||||||
except InvalidChecksumError as e:
|
except InvalidChecksumError as e:
|
||||||
logger.warning(str(e))
|
logger.info(str(e))
|
||||||
except ParseError as e:
|
except ParseError as e:
|
||||||
logger.error('Failed to parse telegram: %s', e)
|
logger.error('Failed to parse telegram: %s', e)
|
||||||
|
|
||||||
|
|||||||
@@ -4,7 +4,7 @@ from functools import partial
|
|||||||
import asyncio
|
import asyncio
|
||||||
import logging
|
import logging
|
||||||
|
|
||||||
from serial_asyncio import create_serial_connection
|
from serial_asyncio_fast import create_serial_connection
|
||||||
|
|
||||||
from dsmr_parser import telegram_specifications
|
from dsmr_parser import telegram_specifications
|
||||||
from dsmr_parser.clients.telegram_buffer import TelegramBuffer
|
from dsmr_parser.clients.telegram_buffer import TelegramBuffer
|
||||||
@@ -158,7 +158,7 @@ class DSMRProtocol(asyncio.Protocol):
|
|||||||
try:
|
try:
|
||||||
parsed_telegram = self.telegram_parser.parse(telegram)
|
parsed_telegram = self.telegram_parser.parse(telegram)
|
||||||
except InvalidChecksumError as e:
|
except InvalidChecksumError as e:
|
||||||
self.log.warning(str(e))
|
self.log.info(str(e))
|
||||||
except ParseError:
|
except ParseError:
|
||||||
self.log.exception("failed to parse telegram")
|
self.log.exception("failed to parse telegram")
|
||||||
else:
|
else:
|
||||||
|
|||||||
@@ -2,7 +2,7 @@
|
|||||||
|
|
||||||
import asyncio
|
import asyncio
|
||||||
|
|
||||||
from serial_asyncio import create_serial_connection
|
from serial_asyncio_fast import create_serial_connection
|
||||||
from .protocol import DSMRProtocol, _create_dsmr_protocol
|
from .protocol import DSMRProtocol, _create_dsmr_protocol
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
import logging
|
import logging
|
||||||
import serial
|
import serial
|
||||||
import serial_asyncio
|
import serial_asyncio_fast
|
||||||
|
|
||||||
from dsmr_parser.clients.telegram_buffer import TelegramBuffer
|
from dsmr_parser.clients.telegram_buffer import TelegramBuffer
|
||||||
from dsmr_parser.exceptions import ParseError, InvalidChecksumError
|
from dsmr_parser.exceptions import ParseError, InvalidChecksumError
|
||||||
@@ -37,7 +37,7 @@ class SerialReader(object):
|
|||||||
try:
|
try:
|
||||||
yield self.telegram_parser.parse(telegram)
|
yield self.telegram_parser.parse(telegram)
|
||||||
except InvalidChecksumError as e:
|
except InvalidChecksumError as e:
|
||||||
logger.warning(str(e))
|
logger.info(str(e))
|
||||||
except ParseError as e:
|
except ParseError as e:
|
||||||
logger.error('Failed to parse telegram: %s', e)
|
logger.error('Failed to parse telegram: %s', e)
|
||||||
|
|
||||||
@@ -77,7 +77,7 @@ class AsyncSerialReader(SerialReader):
|
|||||||
:rtype: None
|
:rtype: None
|
||||||
"""
|
"""
|
||||||
# create Serial StreamReader
|
# create Serial StreamReader
|
||||||
conn = serial_asyncio.open_serial_connection(**self.serial_settings)
|
conn = serial_asyncio_fast.open_serial_connection(**self.serial_settings)
|
||||||
reader, _ = await conn
|
reader, _ = await conn
|
||||||
|
|
||||||
while True:
|
while True:
|
||||||
@@ -107,7 +107,7 @@ class AsyncSerialReader(SerialReader):
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
# create Serial StreamReader
|
# create Serial StreamReader
|
||||||
conn = serial_asyncio.open_serial_connection(**self.serial_settings)
|
conn = serial_asyncio_fast.open_serial_connection(**self.serial_settings)
|
||||||
reader, _ = await conn
|
reader, _ = await conn
|
||||||
|
|
||||||
while True:
|
while True:
|
||||||
|
|||||||
@@ -31,11 +31,15 @@ class SocketReader(object):
|
|||||||
buffer = b""
|
buffer = b""
|
||||||
|
|
||||||
with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as socket_handle:
|
with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as socket_handle:
|
||||||
|
socket_handle.settimeout(60)
|
||||||
socket_handle.connect((self.host, self.port))
|
socket_handle.connect((self.host, self.port))
|
||||||
|
|
||||||
while True:
|
while True:
|
||||||
buffer += socket_handle.recv(self.BUFFER_SIZE)
|
try:
|
||||||
|
buffer += socket_handle.recv(self.BUFFER_SIZE)
|
||||||
|
except socket.timeout:
|
||||||
|
logger.error("Socket timeout occurred, exiting")
|
||||||
|
break
|
||||||
|
|
||||||
lines = buffer.splitlines(keepends=True)
|
lines = buffer.splitlines(keepends=True)
|
||||||
|
|
||||||
@@ -54,7 +58,7 @@ class SocketReader(object):
|
|||||||
try:
|
try:
|
||||||
yield self.telegram_parser.parse(telegram)
|
yield self.telegram_parser.parse(telegram)
|
||||||
except InvalidChecksumError as e:
|
except InvalidChecksumError as e:
|
||||||
logger.warning(str(e))
|
logger.info(str(e))
|
||||||
except ParseError as e:
|
except ParseError as e:
|
||||||
logger.error('Failed to parse telegram: %s', e)
|
logger.error('Failed to parse telegram: %s', e)
|
||||||
|
|
||||||
|
|||||||
@@ -2,6 +2,10 @@ import datetime
|
|||||||
|
|
||||||
import pytz
|
import pytz
|
||||||
|
|
||||||
|
# TODO : Use system timezone
|
||||||
|
# Preload timezone to avoid loading in event loop later
|
||||||
|
local_tz = pytz.timezone('Europe/Amsterdam')
|
||||||
|
|
||||||
|
|
||||||
def timestamp(value):
|
def timestamp(value):
|
||||||
try:
|
try:
|
||||||
@@ -20,8 +24,6 @@ def timestamp(value):
|
|||||||
else:
|
else:
|
||||||
is_dst = False
|
is_dst = False
|
||||||
|
|
||||||
# TODO : Use system timezone
|
|
||||||
local_tz = pytz.timezone('Europe/Amsterdam')
|
|
||||||
localized_datetime = local_tz.localize(naive_datetime, is_dst=is_dst)
|
localized_datetime = local_tz.localize(naive_datetime, is_dst=is_dst)
|
||||||
|
|
||||||
return localized_datetime.astimezone(pytz.utc)
|
return localized_datetime.astimezone(pytz.utc)
|
||||||
|
|||||||
@@ -7,11 +7,11 @@ setup(
|
|||||||
author_email='mail@nldr.net',
|
author_email='mail@nldr.net',
|
||||||
license='MIT',
|
license='MIT',
|
||||||
url='https://github.com/ndokter/dsmr_parser',
|
url='https://github.com/ndokter/dsmr_parser',
|
||||||
version='1.4.0',
|
version='1.4.2',
|
||||||
packages=find_packages(exclude=('test', 'test.*')),
|
packages=find_packages(exclude=('test', 'test.*')),
|
||||||
install_requires=[
|
install_requires=[
|
||||||
'pyserial>=3,<4',
|
'pyserial>=3,<4',
|
||||||
'pyserial-asyncio<1',
|
'pyserial-asyncio-fast>=0.11',
|
||||||
'pytz',
|
'pytz',
|
||||||
'Tailer==0.4.1',
|
'Tailer==0.4.1',
|
||||||
'dlms_cosem==21.3.2'
|
'dlms_cosem==21.3.2'
|
||||||
|
|||||||
@@ -14,6 +14,9 @@ commands=
|
|||||||
[pylama:dsmr_parser/clients/__init__.py]
|
[pylama:dsmr_parser/clients/__init__.py]
|
||||||
ignore = W0611
|
ignore = W0611
|
||||||
|
|
||||||
|
[pylama:dsmr_parser/clients/socket_.py]
|
||||||
|
ignore = C901
|
||||||
|
|
||||||
[pylama:dsmr_parser/parsers.py]
|
[pylama:dsmr_parser/parsers.py]
|
||||||
ignore = W605
|
ignore = W605
|
||||||
|
|
||||||
@@ -24,4 +27,4 @@ ignore = E501
|
|||||||
max_line_length = 120
|
max_line_length = 120
|
||||||
|
|
||||||
[pylama:pycodestyle]
|
[pylama:pycodestyle]
|
||||||
max_line_length = 120
|
max_line_length = 120
|
||||||
|
|||||||
Reference in New Issue
Block a user