Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
# Changelog

## v0.47.4 - 2026-03-08

PR [422](https://github.com/plugwise/python-plugwise-usb/pull/422): Add missing response-types

## v0.47.3 - 2026-03-04

- PR [418](https://github.com/plugwise/python-plugwise-usb/pull/418): Improve raise-message for better debugging
Expand Down
50 changes: 28 additions & 22 deletions plugwise_usb/messages/responses.py
Original file line number Diff line number Diff line change
Expand Up @@ -50,39 +50,45 @@ class StickResponseType(bytes, Enum):

ACCEPT = b"00C1"
FAILED = b"00C2"
TIMEOUT = b"00E1"
COMMAND_NOT_ALLOWED = b"00C3"
CANNOT_JOIN_NETWORK = b"00C4"
NODE_CHANGE_ACCEPTED = b"00C7"
PING_TIMEOUT_1SEC = b"00CD"
PUBLIC_NETWORK_INFO_COMPLETE = b"00CE"
TIMEOUT = b"00E1" # HN_STATUS_102


class NodeResponseType(bytes, Enum):
"""Response types of a 'NodeResponse' reply message."""

CIRCLE_PLUS = b"00DD" # ack for CirclePlusAllowJoiningRequest with state false
CLOCK_ACCEPTED = b"00D7"
JOIN_ACCEPTED = b"00D9" # ack for CirclePlusAllowJoiningRequest with state true
NODE_RESET_ACK = b"00F2"
POWER_LOG_INTERVAL_ACCEPTED = b"00F8" # ack for CircleMeasureIntervalRequest
REAL_TIME_CLOCK_ACCEPTED = b"00DF"
REAL_TIME_CLOCK_FAILED = b"00E7"
RELAY_SWITCHED_OFF = b"00DE"
RELAY_SWITCHED_ON = b"00D8"
RELAY_SWITCH_FAILED = b"00E2"
SED_CONFIG_ACCEPTED = b"00F6"

# TODO: Validate these response types
SED_CONFIG_FAILED = b"00F7"
POWER_CALIBRATION_ACCEPTED = b"00DA"
CLOCK_ACCEPTED = b"00D7" # HN_SETYEARMONTHANDFLASHADDRESS_DONE
RELAY_SWITCHED_ON = b"00D8" # HN_SETRELAISPOSITION_ON
JOIN_ACCEPTED = b"00D9" # ack for CirclePlusAllowJoiningRequest with state true - HN_ALLOWNEWNODESTOJOIN_ACK_1
POWER_CALIBRATION_ACCEPTED = b"00DA" # HN_SETCALIBPARAMETERS_ACK
CIRCLE_PLUS = b"00DD" # ack for CirclePlusAllowJoiningRequest with state false - HN_ALLOWNEWNODESTOJOIN_ACK_0
RELAY_SWITCHED_OFF = b"00DE" # HN_SETRELAISPOSITION_OFF
REAL_TIME_CLOCK_ACCEPTED = b"00DF" # HN_SETRTCDATA_ACK
RELAY_SWITCH_FAILED = b"00E2" # HN_SETRELAISPOSITION_DENIED
REAL_TIME_CLOCK_FAILED = b"00E7" # HN_SETRTCDATA_NACK
NODE_RESET_ACK = b"00F2" # HN_REPLYROLECHANGED_OK
NODE_RESET_FAIL = b"00F3" # HN_REPLYROLECHANGED_NOT_OK
SED_CONFIG_ACCEPTED = b"00F6" # HN_ACKSETSLEEPBEHAVIOR
SED_CONFIG_FAILED = b"00F7" # HN_ACKREQUESTSELFREMOVALFROMNETWORK
POWER_LOG_INTERVAL_ACCEPTED = b"00F8" # ack for CircleMeasureIntervalRequest - HN_ACKSETPOWERRECORDING


class NodeAckResponseType(bytes, Enum):
"""Response types of a 'NodeAckResponse' reply message."""

SCAN_CONFIG_ACCEPTED = b"00BE"
SCAN_CONFIG_FAILED = b"00BF"
DEFAULT_ACK= b"00A0"
DEFAULT_FAIL = b"00A1"
SENSE_INTERVAL_ACCEPTED = b"00B3" # HN_ACKSETSENSEINTERVAL_ACK
SENSE_INTERVAL_FAILED = b"00B4" # HN_ACKSETSENSEINTERVAL_NACK
SENSE_BOUNDARIES_ACCEPTED = b"00B5" # HN_ACKSETSENSEBOUNDARIES_ACK
SENSE_BOUNDARIES_FAILED = b"00B6" # HN_ACKSETSENSEBOUNDARIES_NACK
Comment on lines +83 to +88
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

Update the NodeAckResponseType consumers with these new default codes.

DEFAULT_ACK / DEFAULT_FAIL only fix enum parsing here. At minimum, plugwise_usb/nodes/scan.py Lines 452-465 still treats any NodeAckResponseType outside SCAN_CONFIG_* as unexpected and returns False, so a successful DEFAULT_ACK would still be surfaced as a failed scan configuration.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@plugwise_usb/messages/responses.py` around lines 83 - 91, NodeAckResponseType
introduced DEFAULT_ACK and DEFAULT_FAIL but consumers still treat
non-SCAN_CONFIG_* values as unexpected; update the code that interprets ack
results (e.g., the handler in plugwise_usb/nodes/scan.py that checks
NodeAckResponseType around the scan config ack logic) to treat DEFAULT_ACK as
equivalent to SCAN_CONFIG_ACCEPTED and DEFAULT_FAIL as equivalent to
SCAN_CONFIG_FAILED (or otherwise branch validly for DEFAULT_*), and audit other
uses of NodeAckResponseType to ensure DEFAULT_ACK/DEFAULT_FAIL are handled
consistently instead of being treated as failures/unexpected.

SCAN_LIGHT_CALIBRATION_ACCEPTED = b"00BD"
SENSE_INTERVAL_ACCEPTED = b"00B3"
SENSE_INTERVAL_FAILED = b"00B4"
SENSE_BOUNDARIES_ACCEPTED = b"00B5"
SENSE_BOUNDARIES_FAILED = b"00B6"
SCAN_CONFIG_ACCEPTED = b"00BE" # HN_ACKSETSCANPARAMS_ACK
SCAN_CONFIG_FAILED = b"00BF" # HN_ACKSETSCANPARAMS_NACK


class NodeAwakeResponseType(int, Enum):
Expand Down
Loading