Fix Z-Wave JS sync loop from stale AVAILABLE events#863
Conversation
Some locks send stale userIdStatus=AVAILABLE events after a code was successfully set, which was clearing coordinator data and triggering infinite sync loops. Add _slot_expects_pin() check to ignore these events when LCM expects a PIN on the slot (active=ON with PIN set). Also: - Extract _get_slot_entity_states() helper to reduce duplication - Skip redundant push_update() calls when data hasn't changed Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Codecov Report❌ Patch coverage is
Additional details and impacted files@@ Coverage Diff @@
## main #863 +/- ##
==========================================
- Coverage 96.00% 95.99% -0.02%
==========================================
Files 29 29
Lines 2581 2599 +18
Branches 83 83
==========================================
+ Hits 2478 2495 +17
- Misses 103 104 +1
Flags with carried forward coverage won't be shown. Click here to find out more.
🚀 New features to boost your workflow:
|
There was a problem hiding this comment.
Pull request overview
This PR fixes an infinite sync loop issue in Z-Wave JS lock integration caused by some locks sending stale userIdStatus=AVAILABLE events shortly after a code is successfully set. The fix adds logic to ignore these stale AVAILABLE events when Lock Code Manager (LCM) expects a PIN on the slot.
Changes:
- Added
_get_slot_entity_states()helper method to reduce code duplication between_slot_expects_pin()and_resolve_pin_if_masked() - Added
_slot_expects_pin()method to check if LCM expects a PIN on a slot (active=ON with PIN set) - Modified AVAILABLE event handling to skip clearing slots when LCM expects a PIN on them
- Optimized coordinator's
push_update()to skip redundant updates when data hasn't changed - Added comprehensive tests for the new functionality
Reviewed changes
Copilot reviewed 3 out of 3 changed files in this pull request and generated no comments.
| File | Description |
|---|---|
| custom_components/lock_code_manager/providers/zwave_js.py | Added helper methods to check slot expectations and refactored PIN resolution logic; added check to ignore stale AVAILABLE events |
| custom_components/lock_code_manager/coordinator.py | Added optimization to skip redundant push_update calls when data unchanged |
| tests/providers/test_zwave_js.py | Added comprehensive tests for new _slot_expects_pin() method and AVAILABLE event handling |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Proposed change
Some Z-Wave locks send stale
userIdStatus=AVAILABLEevents after a code was successfully set, which was causing Lock Code Manager to clear coordinator data and trigger infinite sync loops.This PR adds a
_slot_expects_pin()check to ignore these stale AVAILABLE events when LCM expects a PIN on the slot (active=ON with PIN set).Changes:
_slot_expects_pin()method to check if LCM expects a PIN on a slot_get_slot_entity_states()helper to reduce code duplication between_slot_expects_pin()and_resolve_pin_if_masked()push_update()calls in coordinator when data hasn't actually changed (reduces log noise)Type of change
Additional information
userIdStatus=AVAILABLE~3 seconds after code set, clearing coordinator data