Repository: home-assistant-libs/zwave-js-server-python (language: python)

Issue:
TODO: Remove redundant validation
`Z-Wave JS` does a lot of internal validation that we have attempted to replicate within the library, and in some cases we may have been overly strict. Where it makes sense, we should fallback to the driver validation. To accomplish this we will need to make sure that whatever cases that lead to an exception and would also return an error from zwave-js are removed from the library.

CC @MartinHjelmare as this is something we have tackled here or there, but I think this is an overall design decision we should align on


Discussion / hints:

Fix patch:
diff --git a/zwave_js_server/util/lock.py b/zwave_js_server/util/lock.py
index faa4121de..1b9b00793 100644
--- a/zwave_js_server/util/lock.py
+++ b/zwave_js_server/util/lock.py
@@ -143,11 +143,6 @@ async def set_usercode(
 ) -> SetValueResult | None:
     """Set the usercode to index X on the lock."""
     value = get_code_slot_value(node, code_slot, LOCK_USERCODE_PROPERTY)
-    usercode = str(usercode)
-
-    if len(usercode) < 4:
-        raise ValueError("User code must be at least 4 digits")
-
     return await node.async_set_value(value, usercode)
 
 
@@ -155,17 +150,12 @@ async def set_usercodes(node: Node, codes: dict[int, str]) -> SupervisionResult
     """Set the usercode to index X on the lock."""
     cc_api_codes = [
         {
-            LOCK_USERCODE_ID_PROPERTY: int(code_slot),
+            LOCK_USERCODE_ID_PROPERTY: code_slot,
             LOCK_USERCODE_STATUS_PROPERTY: CodeSlotStatus.ENABLED,
-            LOCK_USERCODE_PROPERTY: str(usercode),
+            LOCK_USERCODE_PROPERTY: usercode,
         }
         for code_slot, usercode in codes.items()
-        if len(str(usercode)) >= 4
     ]
-
-    if len(cc_api_codes) < len(codes):
-        raise ValueError("User codes must be at least 4 digits")
-
     # https://zwave-js.github.io/node-zwave-js/#/api/CCs/UserCode?id=setmany
     data = await node.async_invoke_cc_api(
         CommandClass.USER_CODE, "setMany", cc_api_codes, wait_for_result=True
@@ -180,7 +170,7 @@ async def set_usercodes(node: Node, codes: dict[int, str]) -> SupervisionResult
 async def clear_usercode(node: Node, code_slot: int) -> SetValueResult | None:
     """Clear a code slot on the lock."""
     value = get_code_slot_value(node, code_slot, LOCK_USERCODE_STATUS_PROPERTY)
-    return await node.async_set_value(value, CodeSlotStatus.AVAILABLE.value)
+    return await node.async_set_value(value, CodeSlotStatus.AVAILABLE)
 
 
 async def set_configuration(


Test patch:
diff --git a/test/util/test_lock.py b/test/util/test_lock.py
index 8bfef5d4b..142376cb1 100644
--- a/test/util/test_lock.py
+++ b/test/util/test_lock.py
@@ -100,13 +100,6 @@ async def test_set_usercode(lock_schlage_be469, mock_command, uuid4):
     # assert no new command calls
     assert len(ack_commands) == 1
 
-    # Test invalid code length
-    with pytest.raises(ValueError):
-        await set_usercode(node, 1, "123")
-
-    # assert no new command calls
-    assert len(ack_commands) == 1
-
 
 async def test_set_usercodes(
     lock_schlage_be469: Node, mock_command: MockCommandProtocol, uuid4: str
@@ -118,8 +111,7 @@ async def test_set_usercodes(
         {"response": {"status": 255}},
     )
 
-    # Test wrong types to ensure values get converted
-    assert await set_usercodes(node, {"1": 1234}) == SupervisionResult(
+    assert await set_usercodes(node, {1: "1234"}) == SupervisionResult(
         {"status": SupervisionStatus.SUCCESS}
     )
     assert len(ack_commands) == 1
@@ -141,13 +133,6 @@ async def test_set_usercodes(
         ],
     }
 
-    # Test invalid code length
-    with pytest.raises(ValueError):
-        await set_usercodes(node, {1: "123"})
-
-    # assert no new command calls
-    assert len(ack_commands) == 1
-
 
 async def test_set_usercodes_invalid(
     lock_schlage_be469: Node, mock_command: MockCommandProtocol