python-bsblan 6.1.11__py3-none-any.whl → 6.2.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- bsblan/bsblan.py +15 -22
- bsblan/constants.py +1 -0
- bsblan/utility.py +0 -60
- {python_bsblan-6.1.11.dist-info → python_bsblan-6.2.0.dist-info}/METADATA +1 -1
- {python_bsblan-6.1.11.dist-info → python_bsblan-6.2.0.dist-info}/RECORD +7 -7
- {python_bsblan-6.1.11.dist-info → python_bsblan-6.2.0.dist-info}/WHEEL +0 -0
- {python_bsblan-6.1.11.dist-info → python_bsblan-6.2.0.dist-info}/licenses/LICENSE.md +0 -0
bsblan/bsblan.py
CHANGED
|
@@ -51,9 +51,10 @@ from .models import (
|
|
|
51
51
|
State,
|
|
52
52
|
StaticState,
|
|
53
53
|
)
|
|
54
|
-
from .utility import is_param_value_active
|
|
54
|
+
from .utility import is_param_value_active
|
|
55
55
|
|
|
56
56
|
if TYPE_CHECKING:
|
|
57
|
+
from datetime import datetime
|
|
57
58
|
from typing import Self
|
|
58
59
|
|
|
59
60
|
from aiohttp.client import ClientSession
|
|
@@ -862,24 +863,31 @@ class BSBLAN:
|
|
|
862
863
|
time_data = {"time": data["0"]}
|
|
863
864
|
return DeviceTime.model_validate(time_data)
|
|
864
865
|
|
|
865
|
-
async def set_time(self,
|
|
866
|
+
async def set_time(self, value: datetime) -> None:
|
|
866
867
|
"""Set the time on the BSB-LAN device.
|
|
867
868
|
|
|
868
869
|
Args:
|
|
869
|
-
|
|
870
|
-
|
|
870
|
+
value (datetime): The local time of the heating system. Its date and
|
|
871
|
+
time are written as they are, without timezone conversion.
|
|
871
872
|
|
|
872
873
|
Raises:
|
|
873
|
-
BSBLANInvalidParameterError: If the
|
|
874
|
+
BSBLANInvalidParameterError: If the year is out of range.
|
|
875
|
+
BSBLANError: If the device does not accept the new time.
|
|
874
876
|
|
|
875
877
|
"""
|
|
876
878
|
await self._ensure_device_metadata()
|
|
877
879
|
self._validate_time_sync_supported()
|
|
878
|
-
|
|
880
|
+
if not Validation.MIN_YEAR <= value.year <= Validation.MAX_YEAR:
|
|
881
|
+
msg = f"Invalid year: {value.year}"
|
|
882
|
+
raise BSBLANInvalidParameterError(msg)
|
|
883
|
+
# BSB-LAN 4.1 rejects a space between the date and the time
|
|
879
884
|
response = await self._request(
|
|
880
|
-
base_path="/JS",
|
|
885
|
+
base_path="/JS",
|
|
886
|
+
data=self._set_payload("0", value.strftime("%d.%m.%Y_%H:%M:%S")),
|
|
881
887
|
)
|
|
882
888
|
logger.debug("Response for setting time: %s", response)
|
|
889
|
+
if response.get("0", {}).get("status") != 1:
|
|
890
|
+
raise BSBLANError(ErrorMsg.TIME_SYNC_FAILED)
|
|
883
891
|
|
|
884
892
|
async def thermostat( # noqa: PLR0913 # pylint: disable=too-many-arguments
|
|
885
893
|
self,
|
|
@@ -992,21 +1000,6 @@ class BSBLAN:
|
|
|
992
1000
|
circuit,
|
|
993
1001
|
)
|
|
994
1002
|
|
|
995
|
-
def _validate_time_format(self, time_value: str) -> None:
|
|
996
|
-
"""Validate the time format.
|
|
997
|
-
|
|
998
|
-
Args:
|
|
999
|
-
time_value (str): The time value to validate.
|
|
1000
|
-
|
|
1001
|
-
Raises:
|
|
1002
|
-
BSBLANInvalidParameterError: If the time format is invalid.
|
|
1003
|
-
|
|
1004
|
-
"""
|
|
1005
|
-
try:
|
|
1006
|
-
validate_time_format(time_value, Validation.MIN_YEAR, Validation.MAX_YEAR)
|
|
1007
|
-
except ValueError as err:
|
|
1008
|
-
raise BSBLANInvalidParameterError(str(err)) from err
|
|
1009
|
-
|
|
1010
1003
|
def _set_payload(
|
|
1011
1004
|
self, parameter: str, value: str, type_: str = "1"
|
|
1012
1005
|
) -> dict[str, Any]:
|
bsblan/constants.py
CHANGED
|
@@ -561,6 +561,7 @@ class ErrorMsg:
|
|
|
561
561
|
)
|
|
562
562
|
NO_HEATING_SCHEDULE_PARAMS = "No heating schedule parameters available"
|
|
563
563
|
TIME_SYNC_NOT_SUPPORTED = "Time synchronization is not supported by this device"
|
|
564
|
+
TIME_SYNC_FAILED = "The device did not accept the new time"
|
|
564
565
|
BUS_WRITE_NOT_SUPPORTED = "Writing parameters is not supported by this device"
|
|
565
566
|
|
|
566
567
|
|
bsblan/utility.py
CHANGED
|
@@ -3,7 +3,6 @@
|
|
|
3
3
|
from __future__ import annotations
|
|
4
4
|
|
|
5
5
|
import logging
|
|
6
|
-
import re
|
|
7
6
|
from dataclasses import dataclass, field
|
|
8
7
|
from typing import Any
|
|
9
8
|
|
|
@@ -12,65 +11,6 @@ from .constants import CircuitConfig
|
|
|
12
11
|
logger = logging.getLogger(__name__)
|
|
13
12
|
|
|
14
13
|
|
|
15
|
-
def validate_time_format(
|
|
16
|
-
time_value: str,
|
|
17
|
-
min_year: int,
|
|
18
|
-
max_year: int,
|
|
19
|
-
) -> None:
|
|
20
|
-
"""Validate the BSB-LAN time format.
|
|
21
|
-
|
|
22
|
-
Args:
|
|
23
|
-
time_value: The time value to validate in format DD.MM.YYYY HH:MM:SS.
|
|
24
|
-
min_year: Minimum valid year.
|
|
25
|
-
max_year: Maximum valid year.
|
|
26
|
-
|
|
27
|
-
Raises:
|
|
28
|
-
ValueError: If the time format is invalid.
|
|
29
|
-
|
|
30
|
-
"""
|
|
31
|
-
# BSB-LAN supports format: DD.MM.YYYY HH:MM:SS (e.g., "13.08.2025 10:25:55")
|
|
32
|
-
pattern = r"^(\d{2})\.(\d{2})\.(\d{4}) (\d{2}):(\d{2}):(\d{2})$"
|
|
33
|
-
|
|
34
|
-
match = re.match(pattern, time_value)
|
|
35
|
-
if not match:
|
|
36
|
-
msg = f"Invalid time format: {time_value}. Expected DD.MM.YYYY HH:MM:SS"
|
|
37
|
-
raise ValueError(msg)
|
|
38
|
-
|
|
39
|
-
day, month, year, hour, minute, second = map(int, match.groups())
|
|
40
|
-
|
|
41
|
-
# Validate ranges
|
|
42
|
-
if not (1 <= day <= 31):
|
|
43
|
-
msg = f"Invalid day: {day}"
|
|
44
|
-
raise ValueError(msg)
|
|
45
|
-
if not (1 <= month <= 12):
|
|
46
|
-
msg = f"Invalid month: {month}"
|
|
47
|
-
raise ValueError(msg)
|
|
48
|
-
if not (min_year <= year <= max_year):
|
|
49
|
-
msg = f"Invalid year: {year}"
|
|
50
|
-
raise ValueError(msg)
|
|
51
|
-
if not (0 <= hour <= 23):
|
|
52
|
-
msg = f"Invalid hour: {hour}"
|
|
53
|
-
raise ValueError(msg)
|
|
54
|
-
if not (0 <= minute <= 59):
|
|
55
|
-
msg = f"Invalid minute: {minute}"
|
|
56
|
-
raise ValueError(msg)
|
|
57
|
-
if not (0 <= second <= 59):
|
|
58
|
-
msg = f"Invalid second: {second}"
|
|
59
|
-
raise ValueError(msg)
|
|
60
|
-
|
|
61
|
-
# Additional validation for days per month
|
|
62
|
-
if month in (4, 6, 9, 11) and day > 30:
|
|
63
|
-
msg = f"Invalid day {day} for month {month}"
|
|
64
|
-
raise ValueError(msg)
|
|
65
|
-
if month == 2:
|
|
66
|
-
# Leap year check
|
|
67
|
-
is_leap = (year % 4 == 0 and year % 100 != 0) or (year % 400 == 0)
|
|
68
|
-
max_day = 29 if is_leap else 28
|
|
69
|
-
if day > max_day:
|
|
70
|
-
msg = f"Invalid day {day} for February in year {year}"
|
|
71
|
-
raise ValueError(msg)
|
|
72
|
-
|
|
73
|
-
|
|
74
14
|
def is_param_value_active(param: dict[str, Any] | None) -> bool:
|
|
75
15
|
"""Check whether a parameter payload carries an active value.
|
|
76
16
|
|
|
@@ -7,13 +7,13 @@ bsblan/_thermostat.py,sha256=Yl-AM4gJikwSQwcpYH7fHH6I1lEVggnendf28-d0IAE,6520
|
|
|
7
7
|
bsblan/_transport.py,sha256=qNtV_8uJrfYfHlbaExPln4jCaJxqE5sypq5OHyxG8KE,8266
|
|
8
8
|
bsblan/_validation.py,sha256=w93Hg5sqeJKXOozwWV4Hjh7_aR197tOpHn6LgxL1Pek,17836
|
|
9
9
|
bsblan/_version.py,sha256=hpeIg9JUswHSorY3iSUERcMC1MzwM9Rpdo1wqeh5rc8,2799
|
|
10
|
-
bsblan/bsblan.py,sha256=
|
|
11
|
-
bsblan/constants.py,sha256=
|
|
10
|
+
bsblan/bsblan.py,sha256=XOzwrThvxT6NQcaKz7BKdpeZPkZRBbgnXd8plcrU-X4,48987
|
|
11
|
+
bsblan/constants.py,sha256=xcL43NpsyrJ6NRJHO2x2iH9J97Dq6DsVsFn-CzpBxoo,26373
|
|
12
12
|
bsblan/exceptions.py,sha256=Z9pXtVc8zhy9FTBkT8leJ1UE9zdOdLHF7pE7C4GjBmg,2795
|
|
13
13
|
bsblan/models.py,sha256=UJbCoVr7_ohtKG5n_jSzoYDzBpl9y4OWj3bqGYRvf_0,23111
|
|
14
14
|
bsblan/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
15
|
-
bsblan/utility.py,sha256=
|
|
16
|
-
python_bsblan-6.
|
|
17
|
-
python_bsblan-6.
|
|
18
|
-
python_bsblan-6.
|
|
19
|
-
python_bsblan-6.
|
|
15
|
+
bsblan/utility.py,sha256=V5OjZieC6NpQHMKdfrUMJkjSrbrMvpnT7A5k5bQnmgM,5543
|
|
16
|
+
python_bsblan-6.2.0.dist-info/METADATA,sha256=DyrUwQh3bu9ueQKDpOkBipZzpIIAPo1OG-q0bn2ZFt8,9585
|
|
17
|
+
python_bsblan-6.2.0.dist-info/WHEEL,sha256=W3fkpkm7-wf9vBI5Z-7s0eWkeM-spu78I8Neb98DeEg,87
|
|
18
|
+
python_bsblan-6.2.0.dist-info/licenses/LICENSE.md,sha256=Shv8HPcD1WbZjBPvfb5r3h_cwaPeVaUZMUqU_XQGwGw,1092
|
|
19
|
+
python_bsblan-6.2.0.dist-info/RECORD,,
|
|
File without changes
|
|
File without changes
|