conson-xp 1.1.0__py3-none-any.whl → 1.3.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.
- {conson_xp-1.1.0.dist-info → conson_xp-1.3.0.dist-info}/METADATA +1 -5
- conson_xp-1.3.0.dist-info/RECORD +164 -0
- xp/__init__.py +4 -3
- xp/cli/__init__.py +1 -1
- xp/cli/commands/__init__.py +1 -2
- xp/cli/commands/conbus/conbus.py +9 -37
- xp/cli/commands/conbus/conbus_actiontable_commands.py +26 -4
- xp/cli/commands/conbus/conbus_autoreport_commands.py +58 -30
- xp/cli/commands/conbus/conbus_blink_commands.py +61 -29
- xp/cli/commands/conbus/conbus_config_commands.py +10 -5
- xp/cli/commands/conbus/conbus_custom_commands.py +16 -5
- xp/cli/commands/conbus/conbus_datapoint_commands.py +32 -10
- xp/cli/commands/conbus/conbus_discover_commands.py +20 -7
- xp/cli/commands/conbus/conbus_lightlevel_commands.py +114 -39
- xp/cli/commands/conbus/conbus_linknumber_commands.py +50 -25
- xp/cli/commands/conbus/conbus_msactiontable_commands.py +36 -5
- xp/cli/commands/conbus/conbus_output_commands.py +52 -14
- xp/cli/commands/conbus/conbus_raw_commands.py +17 -6
- xp/cli/commands/conbus/conbus_receive_commands.py +20 -10
- xp/cli/commands/conbus/conbus_scan_commands.py +17 -4
- xp/cli/commands/file_commands.py +35 -18
- xp/cli/commands/homekit/homekit.py +14 -8
- xp/cli/commands/homekit/homekit_start_commands.py +8 -6
- xp/cli/commands/module_commands.py +38 -23
- xp/cli/commands/reverse_proxy_commands.py +27 -19
- xp/cli/commands/server/server_commands.py +18 -18
- xp/cli/commands/telegram/telegram.py +4 -12
- xp/cli/commands/telegram/telegram_blink_commands.py +10 -8
- xp/cli/commands/telegram/telegram_checksum_commands.py +19 -8
- xp/cli/commands/telegram/telegram_discover_commands.py +2 -4
- xp/cli/commands/telegram/telegram_linknumber_commands.py +11 -8
- xp/cli/commands/telegram/telegram_parse_commands.py +10 -9
- xp/cli/commands/telegram/telegram_version_commands.py +8 -4
- xp/cli/main.py +5 -3
- xp/cli/utils/click_tree.py +23 -3
- xp/cli/utils/datapoint_type_choice.py +20 -0
- xp/cli/utils/decorators.py +165 -14
- xp/cli/utils/error_handlers.py +49 -18
- xp/cli/utils/formatters.py +95 -10
- xp/cli/utils/serial_number_type.py +18 -0
- xp/cli/utils/system_function_choice.py +20 -0
- xp/cli/utils/xp_module_type.py +20 -0
- xp/connection/__init__.py +1 -1
- xp/connection/exceptions.py +5 -5
- xp/models/__init__.py +1 -1
- xp/models/actiontable/__init__.py +1 -0
- xp/models/actiontable/actiontable.py +17 -1
- xp/models/actiontable/msactiontable_xp20.py +10 -0
- xp/models/actiontable/msactiontable_xp24.py +20 -3
- xp/models/actiontable/msactiontable_xp33.py +27 -4
- xp/models/conbus/__init__.py +1 -0
- xp/models/conbus/conbus.py +34 -4
- xp/models/conbus/conbus_autoreport.py +20 -2
- xp/models/conbus/conbus_blink.py +22 -2
- xp/models/conbus/conbus_client_config.py +22 -1
- xp/models/conbus/conbus_connection_status.py +16 -2
- xp/models/conbus/conbus_custom.py +21 -2
- xp/models/conbus/conbus_datapoint.py +25 -2
- xp/models/conbus/conbus_discover.py +18 -2
- xp/models/conbus/conbus_lightlevel.py +20 -2
- xp/models/conbus/conbus_linknumber.py +20 -2
- xp/models/conbus/conbus_output.py +22 -2
- xp/models/conbus/conbus_raw.py +17 -2
- xp/models/conbus/conbus_receive.py +16 -2
- xp/models/conbus/conbus_writeconfig.py +60 -0
- xp/models/homekit/__init__.py +1 -0
- xp/models/homekit/homekit_accessory.py +15 -1
- xp/models/homekit/homekit_config.py +52 -0
- xp/models/homekit/homekit_conson_config.py +32 -0
- xp/models/log_entry.py +49 -9
- xp/models/protocol/__init__.py +1 -0
- xp/models/protocol/conbus_protocol.py +130 -21
- xp/models/telegram/__init__.py +1 -0
- xp/models/telegram/action_type.py +16 -2
- xp/models/telegram/datapoint_type.py +36 -2
- xp/models/telegram/event_telegram.py +46 -10
- xp/models/telegram/event_type.py +8 -1
- xp/models/telegram/input_action_type.py +34 -2
- xp/models/telegram/input_type.py +9 -1
- xp/models/telegram/module_type.py +69 -19
- xp/models/telegram/module_type_code.py +43 -1
- xp/models/telegram/output_telegram.py +30 -6
- xp/models/telegram/reply_telegram.py +56 -11
- xp/models/telegram/system_function.py +35 -3
- xp/models/telegram/system_telegram.py +18 -4
- xp/models/telegram/telegram.py +12 -3
- xp/models/telegram/telegram_type.py +8 -1
- xp/models/telegram/timeparam_type.py +27 -0
- xp/models/write_config_type.py +17 -2
- xp/services/__init__.py +1 -1
- xp/services/conbus/__init__.py +1 -0
- xp/services/conbus/actiontable/__init__.py +1 -0
- xp/services/conbus/actiontable/actiontable_service.py +33 -2
- xp/services/conbus/actiontable/msactiontable_service.py +40 -3
- xp/services/conbus/actiontable/msactiontable_xp24_serializer.py +36 -4
- xp/services/conbus/actiontable/msactiontable_xp33_serializer.py +45 -5
- xp/services/conbus/conbus_blink_all_service.py +40 -21
- xp/services/conbus/conbus_blink_service.py +37 -13
- xp/services/conbus/conbus_custom_service.py +29 -13
- xp/services/conbus/conbus_datapoint_queryall_service.py +40 -16
- xp/services/conbus/conbus_datapoint_service.py +42 -18
- xp/services/conbus/conbus_discover_service.py +43 -7
- xp/services/conbus/conbus_output_service.py +33 -13
- xp/services/conbus/conbus_raw_service.py +36 -16
- xp/services/conbus/conbus_receive_service.py +38 -6
- xp/services/conbus/conbus_scan_service.py +44 -18
- xp/services/conbus/write_config_service.py +193 -0
- xp/services/homekit/__init__.py +1 -0
- xp/services/homekit/homekit_cache_service.py +31 -6
- xp/services/homekit/homekit_conbus_service.py +33 -2
- xp/services/homekit/homekit_config_validator.py +97 -15
- xp/services/homekit/homekit_conson_validator.py +51 -7
- xp/services/homekit/homekit_dimminglight.py +47 -1
- xp/services/homekit/homekit_dimminglight_service.py +35 -1
- xp/services/homekit/homekit_hap_service.py +71 -18
- xp/services/homekit/homekit_lightbulb.py +35 -1
- xp/services/homekit/homekit_lightbulb_service.py +30 -2
- xp/services/homekit/homekit_module_service.py +23 -1
- xp/services/homekit/homekit_outlet.py +47 -1
- xp/services/homekit/homekit_outlet_service.py +44 -2
- xp/services/homekit/homekit_service.py +113 -19
- xp/services/log_file_service.py +37 -41
- xp/services/module_type_service.py +26 -5
- xp/services/protocol/__init__.py +1 -1
- xp/services/protocol/conbus_protocol.py +110 -16
- xp/services/protocol/protocol_factory.py +40 -0
- xp/services/protocol/telegram_protocol.py +38 -7
- xp/services/reverse_proxy_service.py +79 -14
- xp/services/server/__init__.py +1 -0
- xp/services/server/base_server_service.py +102 -14
- xp/services/server/cp20_server_service.py +12 -4
- xp/services/server/server_service.py +26 -11
- xp/services/server/xp130_server_service.py +11 -3
- xp/services/server/xp20_server_service.py +11 -3
- xp/services/server/xp230_server_service.py +11 -3
- xp/services/server/xp24_server_service.py +33 -6
- xp/services/server/xp33_server_service.py +41 -8
- xp/services/telegram/__init__.py +1 -0
- xp/services/telegram/telegram_blink_service.py +19 -31
- xp/services/telegram/telegram_checksum_service.py +10 -10
- xp/services/telegram/telegram_datapoint_service.py +70 -0
- xp/services/telegram/telegram_discover_service.py +58 -29
- xp/services/telegram/telegram_link_number_service.py +27 -40
- xp/services/telegram/telegram_output_service.py +46 -49
- xp/services/telegram/telegram_service.py +41 -41
- xp/services/telegram/telegram_version_service.py +4 -2
- xp/utils/__init__.py +1 -1
- xp/utils/dependencies.py +4 -47
- xp/utils/serialization.py +6 -0
- xp/utils/time_utils.py +6 -11
- conson_xp-1.1.0.dist-info/RECORD +0 -181
- xp/api/__init__.py +0 -1
- xp/api/main.py +0 -110
- xp/api/models/__init__.py +0 -1
- xp/api/models/api.py +0 -20
- xp/api/models/discover.py +0 -21
- xp/api/routers/__init__.py +0 -17
- xp/api/routers/conbus.py +0 -5
- xp/api/routers/conbus_blink.py +0 -105
- xp/api/routers/conbus_custom.py +0 -63
- xp/api/routers/conbus_datapoint.py +0 -67
- xp/api/routers/conbus_output.py +0 -147
- xp/api/routers/errors.py +0 -37
- xp/cli/commands/api.py +0 -16
- xp/cli/commands/api_start_commands.py +0 -126
- xp/services/conbus/conbus_autoreport_get_service.py +0 -85
- xp/services/conbus/conbus_autoreport_set_service.py +0 -128
- xp/services/conbus/conbus_lightlevel_get_service.py +0 -101
- xp/services/conbus/conbus_lightlevel_set_service.py +0 -205
- xp/services/conbus/conbus_linknumber_get_service.py +0 -86
- xp/services/conbus/conbus_linknumber_set_service.py +0 -155
- {conson_xp-1.1.0.dist-info → conson_xp-1.3.0.dist-info}/WHEEL +0 -0
- {conson_xp-1.1.0.dist-info → conson_xp-1.3.0.dist-info}/entry_points.txt +0 -0
- {conson_xp-1.1.0.dist-info → conson_xp-1.3.0.dist-info}/licenses/LICENSE +0 -0
|
@@ -1,3 +1,8 @@
|
|
|
1
|
+
"""Conbus DataPoint Query All Service.
|
|
2
|
+
|
|
3
|
+
This module provides service for querying all datapoint types from a module.
|
|
4
|
+
"""
|
|
5
|
+
|
|
1
6
|
import logging
|
|
2
7
|
from datetime import datetime
|
|
3
8
|
from typing import Callable, Optional
|
|
@@ -28,12 +33,12 @@ class ConbusDatapointQueryAllService(ConbusProtocol):
|
|
|
28
33
|
cli_config: ConbusClientConfig,
|
|
29
34
|
reactor: PosixReactorBase,
|
|
30
35
|
) -> None:
|
|
31
|
-
"""Initialize the query all service
|
|
36
|
+
"""Initialize the query all service.
|
|
32
37
|
|
|
33
38
|
Args:
|
|
34
|
-
telegram_service: TelegramService for dependency injection
|
|
35
|
-
cli_config: ConbusClientConfig for connection settings
|
|
36
|
-
reactor: PosixReactorBase for async operations
|
|
39
|
+
telegram_service: TelegramService for dependency injection.
|
|
40
|
+
cli_config: ConbusClientConfig for connection settings.
|
|
41
|
+
reactor: PosixReactorBase for async operations.
|
|
37
42
|
"""
|
|
38
43
|
super().__init__(cli_config, reactor)
|
|
39
44
|
self.telegram_service = telegram_service
|
|
@@ -51,11 +56,16 @@ class ConbusDatapointQueryAllService(ConbusProtocol):
|
|
|
51
56
|
self.logger = logging.getLogger(__name__)
|
|
52
57
|
|
|
53
58
|
def connection_established(self) -> None:
|
|
54
|
-
|
|
59
|
+
"""Handle connection established event."""
|
|
60
|
+
self.logger.debug("Connection established, querying datapoints.")
|
|
55
61
|
self.next_datapoint()
|
|
56
62
|
|
|
57
63
|
def next_datapoint(self) -> bool:
|
|
64
|
+
"""Query the next datapoint type.
|
|
58
65
|
|
|
66
|
+
Returns:
|
|
67
|
+
True if there are more datapoints to query, False otherwise.
|
|
68
|
+
"""
|
|
59
69
|
self.logger.debug("Querying next datapoint")
|
|
60
70
|
|
|
61
71
|
if self.current_index >= len(self.datapoint_types):
|
|
@@ -75,6 +85,11 @@ class ConbusDatapointQueryAllService(ConbusProtocol):
|
|
|
75
85
|
return True
|
|
76
86
|
|
|
77
87
|
def timeout(self) -> bool:
|
|
88
|
+
"""Handle timeout event by querying next datapoint.
|
|
89
|
+
|
|
90
|
+
Returns:
|
|
91
|
+
True to continue, False to stop the reactor.
|
|
92
|
+
"""
|
|
78
93
|
self.logger.debug("Timeout, querying next datapoint")
|
|
79
94
|
query_next_datapoint = self.next_datapoint()
|
|
80
95
|
if not query_next_datapoint:
|
|
@@ -89,10 +104,19 @@ class ConbusDatapointQueryAllService(ConbusProtocol):
|
|
|
89
104
|
return True
|
|
90
105
|
|
|
91
106
|
def telegram_sent(self, telegram_sent: str) -> None:
|
|
107
|
+
"""Handle telegram sent event.
|
|
108
|
+
|
|
109
|
+
Args:
|
|
110
|
+
telegram_sent: The telegram that was sent.
|
|
111
|
+
"""
|
|
92
112
|
self.service_response.sent_telegram = telegram_sent
|
|
93
113
|
|
|
94
114
|
def telegram_received(self, telegram_received: TelegramReceivedEvent) -> None:
|
|
115
|
+
"""Handle telegram received event.
|
|
95
116
|
|
|
117
|
+
Args:
|
|
118
|
+
telegram_received: The telegram received event.
|
|
119
|
+
"""
|
|
96
120
|
self.logger.debug(f"Telegram received: {telegram_received}")
|
|
97
121
|
if not self.service_response.received_telegrams:
|
|
98
122
|
self.service_response.received_telegrams = []
|
|
@@ -122,6 +146,11 @@ class ConbusDatapointQueryAllService(ConbusProtocol):
|
|
|
122
146
|
self.progress_callback(datapoint_telegram)
|
|
123
147
|
|
|
124
148
|
def failed(self, message: str) -> None:
|
|
149
|
+
"""Handle failed connection event.
|
|
150
|
+
|
|
151
|
+
Args:
|
|
152
|
+
message: Failure message.
|
|
153
|
+
"""
|
|
125
154
|
self.logger.debug(f"Failed with message: {message}")
|
|
126
155
|
self.service_response.success = False
|
|
127
156
|
self.service_response.timestamp = datetime.now()
|
|
@@ -136,20 +165,15 @@ class ConbusDatapointQueryAllService(ConbusProtocol):
|
|
|
136
165
|
progress_callback: Callable[[ReplyTelegram], None],
|
|
137
166
|
timeout_seconds: Optional[float] = None,
|
|
138
167
|
) -> None:
|
|
139
|
-
"""
|
|
140
|
-
Query a specific datapoint from a module.
|
|
168
|
+
"""Query all datapoints from a module.
|
|
141
169
|
|
|
142
170
|
Args:
|
|
143
|
-
serial_number: 10-digit module serial number
|
|
144
|
-
finish_callback:
|
|
145
|
-
progress_callback:
|
|
146
|
-
timeout_seconds:
|
|
147
|
-
|
|
148
|
-
Returns:
|
|
149
|
-
ConbusDatapointResponse with operation result and datapoint value
|
|
171
|
+
serial_number: 10-digit module serial number.
|
|
172
|
+
finish_callback: Callback function to call when all datapoints are received.
|
|
173
|
+
progress_callback: Callback function to call when each datapoint is received.
|
|
174
|
+
timeout_seconds: Timeout in seconds.
|
|
150
175
|
"""
|
|
151
|
-
|
|
152
|
-
self.logger.info("Starting query_datapoint")
|
|
176
|
+
self.logger.info("Starting query_all_datapoints")
|
|
153
177
|
if timeout_seconds:
|
|
154
178
|
self.timeout_seconds = timeout_seconds
|
|
155
179
|
self.finish_callback = finish_callback
|
|
@@ -33,12 +33,20 @@ class ConbusDatapointService(ConbusProtocol):
|
|
|
33
33
|
cli_config: ConbusClientConfig,
|
|
34
34
|
reactor: PosixReactorBase,
|
|
35
35
|
) -> None:
|
|
36
|
-
"""Initialize the Conbus datapoint service
|
|
36
|
+
"""Initialize the Conbus datapoint service.
|
|
37
|
+
|
|
38
|
+
Args:
|
|
39
|
+
telegram_service: Service for parsing telegrams.
|
|
40
|
+
cli_config: Configuration for Conbus client connection.
|
|
41
|
+
reactor: Twisted reactor for event loop.
|
|
42
|
+
"""
|
|
37
43
|
super().__init__(cli_config, reactor)
|
|
38
44
|
self.telegram_service = telegram_service
|
|
39
45
|
self.serial_number: str = ""
|
|
40
46
|
self.datapoint_type: Optional[DataPointType] = None
|
|
41
|
-
self.
|
|
47
|
+
self.datapoint_finished_callback: Optional[
|
|
48
|
+
Callable[[ConbusDatapointResponse], None]
|
|
49
|
+
] = None
|
|
42
50
|
self.service_response: ConbusDatapointResponse = ConbusDatapointResponse(
|
|
43
51
|
success=False,
|
|
44
52
|
serial_number=self.serial_number,
|
|
@@ -48,8 +56,9 @@ class ConbusDatapointService(ConbusProtocol):
|
|
|
48
56
|
self.logger = logging.getLogger(__name__)
|
|
49
57
|
|
|
50
58
|
def connection_established(self) -> None:
|
|
59
|
+
"""Handle connection established event."""
|
|
51
60
|
self.logger.debug(
|
|
52
|
-
f"Connection established, querying datapoint {self.datapoint_type}
|
|
61
|
+
f"Connection established, querying datapoint {self.datapoint_type}."
|
|
53
62
|
)
|
|
54
63
|
if self.datapoint_type is None:
|
|
55
64
|
self.failed("Datapoint type not set")
|
|
@@ -63,10 +72,19 @@ class ConbusDatapointService(ConbusProtocol):
|
|
|
63
72
|
)
|
|
64
73
|
|
|
65
74
|
def telegram_sent(self, telegram_sent: str) -> None:
|
|
75
|
+
"""Handle telegram sent event.
|
|
76
|
+
|
|
77
|
+
Args:
|
|
78
|
+
telegram_sent: The telegram that was sent.
|
|
79
|
+
"""
|
|
66
80
|
self.service_response.sent_telegram = telegram_sent
|
|
67
81
|
|
|
68
82
|
def telegram_received(self, telegram_received: TelegramReceivedEvent) -> None:
|
|
83
|
+
"""Handle telegram received event.
|
|
69
84
|
|
|
85
|
+
Args:
|
|
86
|
+
telegram_received: The telegram received event.
|
|
87
|
+
"""
|
|
70
88
|
self.logger.debug(f"Telegram received: {telegram_received}")
|
|
71
89
|
if not self.service_response.received_telegrams:
|
|
72
90
|
self.service_response.received_telegrams = []
|
|
@@ -97,6 +115,11 @@ class ConbusDatapointService(ConbusProtocol):
|
|
|
97
115
|
self.succeed(datapoint_telegram)
|
|
98
116
|
|
|
99
117
|
def succeed(self, datapoint_telegram: ReplyTelegram) -> None:
|
|
118
|
+
"""Handle successful datapoint query.
|
|
119
|
+
|
|
120
|
+
Args:
|
|
121
|
+
datapoint_telegram: The parsed datapoint telegram.
|
|
122
|
+
"""
|
|
100
123
|
self.logger.debug("Succeed querying datapoint")
|
|
101
124
|
self.service_response.success = True
|
|
102
125
|
self.service_response.timestamp = datetime.now()
|
|
@@ -104,17 +127,23 @@ class ConbusDatapointService(ConbusProtocol):
|
|
|
104
127
|
self.service_response.system_function = SystemFunction.READ_DATAPOINT
|
|
105
128
|
self.service_response.datapoint_type = self.datapoint_type
|
|
106
129
|
self.service_response.datapoint_telegram = datapoint_telegram
|
|
107
|
-
|
|
108
|
-
|
|
130
|
+
self.service_response.data_value = datapoint_telegram.data_value
|
|
131
|
+
if self.datapoint_finished_callback:
|
|
132
|
+
self.datapoint_finished_callback(self.service_response)
|
|
109
133
|
|
|
110
134
|
def failed(self, message: str) -> None:
|
|
135
|
+
"""Handle failed connection event.
|
|
136
|
+
|
|
137
|
+
Args:
|
|
138
|
+
message: Failure message.
|
|
139
|
+
"""
|
|
111
140
|
self.logger.debug(f"Failed with message: {message}")
|
|
112
141
|
self.service_response.success = False
|
|
113
142
|
self.service_response.timestamp = datetime.now()
|
|
114
143
|
self.service_response.serial_number = self.serial_number
|
|
115
144
|
self.service_response.error = message
|
|
116
|
-
if self.
|
|
117
|
-
self.
|
|
145
|
+
if self.datapoint_finished_callback:
|
|
146
|
+
self.datapoint_finished_callback(self.service_response)
|
|
118
147
|
|
|
119
148
|
def query_datapoint(
|
|
120
149
|
self,
|
|
@@ -123,23 +152,18 @@ class ConbusDatapointService(ConbusProtocol):
|
|
|
123
152
|
finish_callback: Callable[[ConbusDatapointResponse], None],
|
|
124
153
|
timeout_seconds: Optional[float] = None,
|
|
125
154
|
) -> None:
|
|
126
|
-
"""
|
|
127
|
-
Query a specific datapoint from a module.
|
|
155
|
+
"""Query a specific datapoint from a module.
|
|
128
156
|
|
|
129
157
|
Args:
|
|
130
|
-
serial_number: 10-digit module serial number
|
|
131
|
-
datapoint_type: Type of datapoint to query
|
|
132
|
-
finish_callback:
|
|
133
|
-
timeout_seconds:
|
|
134
|
-
|
|
135
|
-
Returns:
|
|
136
|
-
ConbusDatapointResponse with operation result and datapoint value
|
|
158
|
+
serial_number: 10-digit module serial number.
|
|
159
|
+
datapoint_type: Type of datapoint to query.
|
|
160
|
+
finish_callback: Callback function to call when the datapoint is received.
|
|
161
|
+
timeout_seconds: Timeout in seconds.
|
|
137
162
|
"""
|
|
138
|
-
|
|
139
163
|
self.logger.info("Starting query_datapoint")
|
|
140
164
|
if timeout_seconds:
|
|
141
165
|
self.timeout_seconds = timeout_seconds
|
|
142
|
-
self.
|
|
166
|
+
self.datapoint_finished_callback = finish_callback
|
|
143
167
|
self.serial_number = serial_number
|
|
144
168
|
self.datapoint_type = datapoint_type
|
|
145
169
|
self.start_reactor()
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
"""Conbus
|
|
1
|
+
"""Conbus Discover Service for TCP communication with Conbus servers.
|
|
2
2
|
|
|
3
3
|
This service implements a TCP client that connects to Conbus servers and sends
|
|
4
|
-
|
|
4
|
+
discover telegrams to find modules on the network.
|
|
5
5
|
"""
|
|
6
6
|
|
|
7
7
|
import logging
|
|
@@ -18,10 +18,10 @@ from xp.services.protocol.conbus_protocol import ConbusProtocol
|
|
|
18
18
|
|
|
19
19
|
class ConbusDiscoverService(ConbusProtocol):
|
|
20
20
|
"""
|
|
21
|
-
|
|
21
|
+
Service for discovering modules on Conbus servers.
|
|
22
22
|
|
|
23
|
-
|
|
24
|
-
|
|
23
|
+
Uses ConbusProtocol to provide discovery functionality for finding
|
|
24
|
+
modules connected to the Conbus network.
|
|
25
25
|
"""
|
|
26
26
|
|
|
27
27
|
def __init__(
|
|
@@ -29,7 +29,12 @@ class ConbusDiscoverService(ConbusProtocol):
|
|
|
29
29
|
cli_config: ConbusClientConfig,
|
|
30
30
|
reactor: PosixReactorBase,
|
|
31
31
|
) -> None:
|
|
32
|
-
"""Initialize the Conbus
|
|
32
|
+
"""Initialize the Conbus discover service.
|
|
33
|
+
|
|
34
|
+
Args:
|
|
35
|
+
cli_config: Conbus client configuration.
|
|
36
|
+
reactor: Twisted reactor instance.
|
|
37
|
+
"""
|
|
33
38
|
super().__init__(cli_config, reactor)
|
|
34
39
|
self.progress_callback: Optional[Callable[[str], None]] = None
|
|
35
40
|
self.finish_callback: Optional[Callable[[ConbusDiscoverResponse], None]] = None
|
|
@@ -39,6 +44,7 @@ class ConbusDiscoverService(ConbusProtocol):
|
|
|
39
44
|
self.logger = logging.getLogger(__name__)
|
|
40
45
|
|
|
41
46
|
def connection_established(self) -> None:
|
|
47
|
+
"""Handle connection established event."""
|
|
42
48
|
self.logger.debug("Connection established, sending discover telegram")
|
|
43
49
|
self.send_telegram(
|
|
44
50
|
telegram_type=TelegramType.SYSTEM,
|
|
@@ -48,11 +54,20 @@ class ConbusDiscoverService(ConbusProtocol):
|
|
|
48
54
|
)
|
|
49
55
|
|
|
50
56
|
def telegram_sent(self, telegram_sent: str) -> None:
|
|
57
|
+
"""Handle telegram sent event.
|
|
58
|
+
|
|
59
|
+
Args:
|
|
60
|
+
telegram_sent: The telegram that was sent.
|
|
61
|
+
"""
|
|
51
62
|
self.logger.debug(f"Telegram sent: {telegram_sent}")
|
|
52
63
|
self.discovered_device_result.sent_telegram = telegram_sent
|
|
53
64
|
|
|
54
65
|
def telegram_received(self, telegram_received: TelegramReceivedEvent) -> None:
|
|
66
|
+
"""Handle telegram received event.
|
|
55
67
|
|
|
68
|
+
Args:
|
|
69
|
+
telegram_received: The telegram received event.
|
|
70
|
+
"""
|
|
56
71
|
self.logger.debug(f"Telegram received: {telegram_received}")
|
|
57
72
|
if not self.discovered_device_result.received_telegrams:
|
|
58
73
|
self.discovered_device_result.received_telegrams = []
|
|
@@ -69,6 +84,11 @@ class ConbusDiscoverService(ConbusProtocol):
|
|
|
69
84
|
self.logger.debug("Not a discover response")
|
|
70
85
|
|
|
71
86
|
def discovered_device(self, serial_number: str) -> None:
|
|
87
|
+
"""Handle discovered device event.
|
|
88
|
+
|
|
89
|
+
Args:
|
|
90
|
+
serial_number: Serial number of the discovered device.
|
|
91
|
+
"""
|
|
72
92
|
self.logger.info("discovered_device: %s", serial_number)
|
|
73
93
|
if not self.discovered_device_result.discovered_devices:
|
|
74
94
|
self.discovered_device_result.discovered_devices = []
|
|
@@ -77,6 +97,11 @@ class ConbusDiscoverService(ConbusProtocol):
|
|
|
77
97
|
self.progress_callback(serial_number)
|
|
78
98
|
|
|
79
99
|
def timeout(self) -> bool:
|
|
100
|
+
"""Handle timeout event to stop discovery.
|
|
101
|
+
|
|
102
|
+
Returns:
|
|
103
|
+
False to stop the reactor.
|
|
104
|
+
"""
|
|
80
105
|
self.logger.info("Discovery stopped after: %ss", self.timeout_seconds)
|
|
81
106
|
self.discovered_device_result.success = True
|
|
82
107
|
if self.finish_callback:
|
|
@@ -84,6 +109,11 @@ class ConbusDiscoverService(ConbusProtocol):
|
|
|
84
109
|
return False
|
|
85
110
|
|
|
86
111
|
def failed(self, message: str) -> None:
|
|
112
|
+
"""Handle failed connection event.
|
|
113
|
+
|
|
114
|
+
Args:
|
|
115
|
+
message: Failure message.
|
|
116
|
+
"""
|
|
87
117
|
self.logger.debug(f"Failed: {message}")
|
|
88
118
|
self.discovered_device_result.success = False
|
|
89
119
|
self.discovered_device_result.error = message
|
|
@@ -96,7 +126,13 @@ class ConbusDiscoverService(ConbusProtocol):
|
|
|
96
126
|
finish_callback: Callable[[ConbusDiscoverResponse], None],
|
|
97
127
|
timeout_seconds: Optional[float] = None,
|
|
98
128
|
) -> None:
|
|
99
|
-
"""Run reactor in dedicated thread with its own event loop
|
|
129
|
+
"""Run reactor in dedicated thread with its own event loop.
|
|
130
|
+
|
|
131
|
+
Args:
|
|
132
|
+
progress_callback: Callback for each discovered device.
|
|
133
|
+
finish_callback: Callback when discovery completes.
|
|
134
|
+
timeout_seconds: Optional timeout in seconds.
|
|
135
|
+
"""
|
|
100
136
|
self.logger.info("Starting discovery")
|
|
101
137
|
if timeout_seconds:
|
|
102
138
|
self.timeout_seconds = timeout_seconds
|
|
@@ -25,7 +25,7 @@ from xp.services.telegram.telegram_output_service import (
|
|
|
25
25
|
|
|
26
26
|
|
|
27
27
|
class ConbusOutputError(Exception):
|
|
28
|
-
"""Raised when Conbus output operations fail"""
|
|
28
|
+
"""Raised when Conbus output operations fail."""
|
|
29
29
|
|
|
30
30
|
pass
|
|
31
31
|
|
|
@@ -44,12 +44,12 @@ class ConbusOutputService(ConbusProtocol):
|
|
|
44
44
|
cli_config: ConbusClientConfig,
|
|
45
45
|
reactor: PosixReactorBase,
|
|
46
46
|
):
|
|
47
|
-
"""Initialize the Conbus output service
|
|
47
|
+
"""Initialize the Conbus output service.
|
|
48
48
|
|
|
49
49
|
Args:
|
|
50
|
-
telegram_output_service: TelegramOutputService for telegram generation/parsing
|
|
51
|
-
cli_config: Conbus client configuration
|
|
52
|
-
reactor: Twisted reactor for async operations
|
|
50
|
+
telegram_output_service: TelegramOutputService for telegram generation/parsing.
|
|
51
|
+
cli_config: Conbus client configuration.
|
|
52
|
+
reactor: Twisted reactor for async operations.
|
|
53
53
|
"""
|
|
54
54
|
super().__init__(cli_config, reactor)
|
|
55
55
|
self.telegram_output_service = telegram_output_service
|
|
@@ -69,8 +69,9 @@ class ConbusOutputService(ConbusProtocol):
|
|
|
69
69
|
self.logger = logging.getLogger(__name__)
|
|
70
70
|
|
|
71
71
|
def connection_established(self) -> None:
|
|
72
|
+
"""Handle connection established event."""
|
|
72
73
|
self.logger.debug(
|
|
73
|
-
f"Connection established, sending action {self.action_type} to output {self.output_number}
|
|
74
|
+
f"Connection established, sending action {self.action_type} to output {self.output_number}."
|
|
74
75
|
)
|
|
75
76
|
|
|
76
77
|
# Validate parameters before sending
|
|
@@ -91,9 +92,19 @@ class ConbusOutputService(ConbusProtocol):
|
|
|
91
92
|
)
|
|
92
93
|
|
|
93
94
|
def telegram_sent(self, telegram_sent: str) -> None:
|
|
95
|
+
"""Handle telegram sent event.
|
|
96
|
+
|
|
97
|
+
Args:
|
|
98
|
+
telegram_sent: The telegram that was sent.
|
|
99
|
+
"""
|
|
94
100
|
self.service_response.sent_telegram = telegram_sent
|
|
95
101
|
|
|
96
102
|
def telegram_received(self, telegram_received: TelegramReceivedEvent) -> None:
|
|
103
|
+
"""Handle telegram received event.
|
|
104
|
+
|
|
105
|
+
Args:
|
|
106
|
+
telegram_received: The telegram received event.
|
|
107
|
+
"""
|
|
97
108
|
self.logger.debug(f"Telegram received: {telegram_received}")
|
|
98
109
|
|
|
99
110
|
if not self.service_response.received_telegrams:
|
|
@@ -125,6 +136,11 @@ class ConbusOutputService(ConbusProtocol):
|
|
|
125
136
|
)
|
|
126
137
|
|
|
127
138
|
def succeed(self, output_telegram: OutputTelegram) -> None:
|
|
139
|
+
"""Handle successful output action.
|
|
140
|
+
|
|
141
|
+
Args:
|
|
142
|
+
output_telegram: The output telegram received as response.
|
|
143
|
+
"""
|
|
128
144
|
self.logger.debug("Successfully sent action to output")
|
|
129
145
|
self.service_response.success = True
|
|
130
146
|
self.service_response.timestamp = datetime.now()
|
|
@@ -136,6 +152,11 @@ class ConbusOutputService(ConbusProtocol):
|
|
|
136
152
|
self.finish_callback(self.service_response)
|
|
137
153
|
|
|
138
154
|
def failed(self, message: str) -> None:
|
|
155
|
+
"""Handle failed connection event.
|
|
156
|
+
|
|
157
|
+
Args:
|
|
158
|
+
message: Failure message.
|
|
159
|
+
"""
|
|
139
160
|
self.logger.debug(f"Failed with message: {message}")
|
|
140
161
|
self.service_response.success = False
|
|
141
162
|
self.service_response.timestamp = datetime.now()
|
|
@@ -154,15 +175,14 @@ class ConbusOutputService(ConbusProtocol):
|
|
|
154
175
|
finish_callback: Callable[[ConbusOutputResponse], None],
|
|
155
176
|
timeout_seconds: Optional[float] = None,
|
|
156
177
|
) -> None:
|
|
157
|
-
"""
|
|
158
|
-
Send an action telegram to a module output.
|
|
178
|
+
"""Send an action telegram to a module output.
|
|
159
179
|
|
|
160
180
|
Args:
|
|
161
|
-
serial_number: 10-digit module serial number
|
|
162
|
-
output_number: Output number (0-99)
|
|
163
|
-
action_type: Action to perform (ON_RELEASE, OFF_PRESS, etc.)
|
|
164
|
-
finish_callback: Callback function to call when operation completes
|
|
165
|
-
timeout_seconds: Optional timeout in seconds
|
|
181
|
+
serial_number: 10-digit module serial number.
|
|
182
|
+
output_number: Output number (0-99).
|
|
183
|
+
action_type: Action to perform (ON_RELEASE, OFF_PRESS, etc.).
|
|
184
|
+
finish_callback: Callback function to call when operation completes.
|
|
185
|
+
timeout_seconds: Optional timeout in seconds.
|
|
166
186
|
"""
|
|
167
187
|
self.logger.info("Starting send_action")
|
|
168
188
|
if timeout_seconds:
|
|
@@ -17,10 +17,10 @@ from xp.services.protocol import ConbusProtocol
|
|
|
17
17
|
|
|
18
18
|
class ConbusRawService(ConbusProtocol):
|
|
19
19
|
"""
|
|
20
|
-
Service for
|
|
20
|
+
Service for sending raw telegram sequences to Conbus modules.
|
|
21
21
|
|
|
22
|
-
Uses ConbusProtocol to provide
|
|
23
|
-
for
|
|
22
|
+
Uses ConbusProtocol to provide raw telegram functionality
|
|
23
|
+
for sending arbitrary telegram strings without validation.
|
|
24
24
|
"""
|
|
25
25
|
|
|
26
26
|
def __init__(
|
|
@@ -28,7 +28,12 @@ class ConbusRawService(ConbusProtocol):
|
|
|
28
28
|
cli_config: ConbusClientConfig,
|
|
29
29
|
reactor: PosixReactorBase,
|
|
30
30
|
) -> None:
|
|
31
|
-
"""Initialize the Conbus
|
|
31
|
+
"""Initialize the Conbus raw service.
|
|
32
|
+
|
|
33
|
+
Args:
|
|
34
|
+
cli_config: Configuration for Conbus client connection.
|
|
35
|
+
reactor: Twisted reactor for event loop.
|
|
36
|
+
"""
|
|
32
37
|
super().__init__(cli_config, reactor)
|
|
33
38
|
self.raw_input: str = ""
|
|
34
39
|
self.progress_callback: Optional[Callable[[str], None]] = None
|
|
@@ -40,17 +45,27 @@ class ConbusRawService(ConbusProtocol):
|
|
|
40
45
|
self.logger = logging.getLogger(__name__)
|
|
41
46
|
|
|
42
47
|
def connection_established(self) -> None:
|
|
48
|
+
"""Handle connection established event."""
|
|
43
49
|
self.logger.debug(f"Connection established, sending {self.raw_input}")
|
|
44
50
|
self.sendFrame(self.raw_input.encode())
|
|
45
51
|
|
|
46
52
|
def telegram_sent(self, telegram_sent: str) -> None:
|
|
53
|
+
"""Handle telegram sent event.
|
|
54
|
+
|
|
55
|
+
Args:
|
|
56
|
+
telegram_sent: The telegram that was sent.
|
|
57
|
+
"""
|
|
47
58
|
self.service_response.success = True
|
|
48
59
|
self.service_response.sent_telegrams = telegram_sent
|
|
49
60
|
self.service_response.timestamp = datetime.now()
|
|
50
61
|
self.service_response.received_telegrams = []
|
|
51
|
-
pass
|
|
52
62
|
|
|
53
63
|
def telegram_received(self, telegram_received: TelegramReceivedEvent) -> None:
|
|
64
|
+
"""Handle telegram received event.
|
|
65
|
+
|
|
66
|
+
Args:
|
|
67
|
+
telegram_received: The telegram received event.
|
|
68
|
+
"""
|
|
54
69
|
self.logger.debug(f"Telegram received: {telegram_received}")
|
|
55
70
|
if not self.service_response.received_telegrams:
|
|
56
71
|
self.service_response.received_telegrams = []
|
|
@@ -60,12 +75,22 @@ class ConbusRawService(ConbusProtocol):
|
|
|
60
75
|
self.progress_callback(telegram_received.frame)
|
|
61
76
|
|
|
62
77
|
def timeout(self) -> bool:
|
|
78
|
+
"""Handle timeout event.
|
|
79
|
+
|
|
80
|
+
Returns:
|
|
81
|
+
False to indicate connection should be closed.
|
|
82
|
+
"""
|
|
63
83
|
self.logger.debug(f"Timeout: {self.timeout_seconds}s")
|
|
64
84
|
if self.finish_callback:
|
|
65
85
|
self.finish_callback(self.service_response)
|
|
66
86
|
return False
|
|
67
87
|
|
|
68
88
|
def failed(self, message: str) -> None:
|
|
89
|
+
"""Handle failed connection event.
|
|
90
|
+
|
|
91
|
+
Args:
|
|
92
|
+
message: Failure message.
|
|
93
|
+
"""
|
|
69
94
|
self.logger.debug(f"Failed with message: {message}")
|
|
70
95
|
self.service_response.success = False
|
|
71
96
|
self.service_response.timestamp = datetime.now()
|
|
@@ -80,20 +105,15 @@ class ConbusRawService(ConbusProtocol):
|
|
|
80
105
|
finish_callback: Callable[[ConbusRawResponse], None],
|
|
81
106
|
timeout_seconds: Optional[float] = None,
|
|
82
107
|
) -> None:
|
|
83
|
-
"""
|
|
84
|
-
Query a specific datapoint from a module.
|
|
108
|
+
"""Send a raw telegram string to the Conbus server.
|
|
85
109
|
|
|
86
110
|
Args:
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
finish_callback:
|
|
90
|
-
timeout_seconds:
|
|
91
|
-
|
|
92
|
-
Returns:
|
|
93
|
-
ConbusDatapointResponse with operation result and datapoint value
|
|
111
|
+
raw_input: Raw telegram string to send.
|
|
112
|
+
progress_callback: Callback to handle progress updates.
|
|
113
|
+
finish_callback: Callback function to call when the operation is complete.
|
|
114
|
+
timeout_seconds: Timeout in seconds.
|
|
94
115
|
"""
|
|
95
|
-
|
|
96
|
-
self.logger.info("Starting query_datapoint")
|
|
116
|
+
self.logger.info("Starting send_raw_telegram")
|
|
97
117
|
if timeout_seconds:
|
|
98
118
|
self.timeout_seconds = timeout_seconds
|
|
99
119
|
self.progress_callback = progress_callback
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"""Conbus Receive Service for receiving telegrams from Conbus servers.
|
|
2
2
|
|
|
3
|
-
This service uses
|
|
3
|
+
This service uses ConbusProtocol to provide receive-only functionality,
|
|
4
4
|
allowing clients to receive waiting event telegrams using empty telegram sends.
|
|
5
5
|
"""
|
|
6
6
|
|
|
@@ -19,7 +19,7 @@ class ConbusReceiveService(ConbusProtocol):
|
|
|
19
19
|
"""
|
|
20
20
|
Service for receiving telegrams from Conbus servers.
|
|
21
21
|
|
|
22
|
-
Uses
|
|
22
|
+
Uses ConbusProtocol to provide receive-only functionality
|
|
23
23
|
for collecting waiting event telegrams from the server.
|
|
24
24
|
"""
|
|
25
25
|
|
|
@@ -28,7 +28,12 @@ class ConbusReceiveService(ConbusProtocol):
|
|
|
28
28
|
cli_config: ConbusClientConfig,
|
|
29
29
|
reactor: PosixReactorBase,
|
|
30
30
|
) -> None:
|
|
31
|
-
"""Initialize the Conbus
|
|
31
|
+
"""Initialize the Conbus receive service.
|
|
32
|
+
|
|
33
|
+
Args:
|
|
34
|
+
cli_config: Conbus client configuration.
|
|
35
|
+
reactor: Twisted reactor instance.
|
|
36
|
+
"""
|
|
32
37
|
super().__init__(cli_config, reactor)
|
|
33
38
|
self.progress_callback: Optional[Callable[[str], None]] = None
|
|
34
39
|
self.finish_callback: Optional[Callable[[ConbusReceiveResponse], None]] = None
|
|
@@ -40,12 +45,23 @@ class ConbusReceiveService(ConbusProtocol):
|
|
|
40
45
|
self.logger = logging.getLogger(__name__)
|
|
41
46
|
|
|
42
47
|
def connection_established(self) -> None:
|
|
43
|
-
|
|
48
|
+
"""Handle connection established event."""
|
|
49
|
+
self.logger.debug("Connection established, waiting for telegrams.")
|
|
44
50
|
|
|
45
51
|
def telegram_sent(self, telegram_sent: str) -> None:
|
|
52
|
+
"""Handle telegram sent event.
|
|
53
|
+
|
|
54
|
+
Args:
|
|
55
|
+
telegram_sent: The telegram that was sent.
|
|
56
|
+
"""
|
|
46
57
|
pass
|
|
47
58
|
|
|
48
59
|
def telegram_received(self, telegram_received: TelegramReceivedEvent) -> None:
|
|
60
|
+
"""Handle telegram received event.
|
|
61
|
+
|
|
62
|
+
Args:
|
|
63
|
+
telegram_received: The telegram received event.
|
|
64
|
+
"""
|
|
49
65
|
self.logger.debug(f"Telegram received: {telegram_received}")
|
|
50
66
|
if self.progress_callback:
|
|
51
67
|
self.progress_callback(telegram_received.frame)
|
|
@@ -55,6 +71,11 @@ class ConbusReceiveService(ConbusProtocol):
|
|
|
55
71
|
self.receive_response.received_telegrams.append(telegram_received.frame)
|
|
56
72
|
|
|
57
73
|
def timeout(self) -> bool:
|
|
74
|
+
"""Handle timeout event to stop receiving.
|
|
75
|
+
|
|
76
|
+
Returns:
|
|
77
|
+
False to stop the reactor.
|
|
78
|
+
"""
|
|
58
79
|
self.logger.info("Receive stopped after: %ss", self.timeout_seconds)
|
|
59
80
|
self.receive_response.success = True
|
|
60
81
|
if self.finish_callback:
|
|
@@ -62,6 +83,11 @@ class ConbusReceiveService(ConbusProtocol):
|
|
|
62
83
|
return False
|
|
63
84
|
|
|
64
85
|
def failed(self, message: str) -> None:
|
|
86
|
+
"""Handle failed connection event.
|
|
87
|
+
|
|
88
|
+
Args:
|
|
89
|
+
message: Failure message.
|
|
90
|
+
"""
|
|
65
91
|
self.logger.debug("Failed %s:", message)
|
|
66
92
|
self.receive_response.success = False
|
|
67
93
|
self.receive_response.error = message
|
|
@@ -74,8 +100,14 @@ class ConbusReceiveService(ConbusProtocol):
|
|
|
74
100
|
finish_callback: Callable[[ConbusReceiveResponse], None],
|
|
75
101
|
timeout_seconds: Optional[float] = None,
|
|
76
102
|
) -> None:
|
|
77
|
-
"""Run reactor in dedicated thread with its own event loop
|
|
78
|
-
|
|
103
|
+
"""Run reactor in dedicated thread with its own event loop.
|
|
104
|
+
|
|
105
|
+
Args:
|
|
106
|
+
progress_callback: Callback for each received telegram.
|
|
107
|
+
finish_callback: Callback when receiving completes.
|
|
108
|
+
timeout_seconds: Optional timeout in seconds.
|
|
109
|
+
"""
|
|
110
|
+
self.logger.info("Starting receive")
|
|
79
111
|
if timeout_seconds:
|
|
80
112
|
self.timeout_seconds = timeout_seconds
|
|
81
113
|
self.progress_callback = progress_callback
|