Discovery: accept cameras that only send the encrypt_type list (#1770)
Some checks failed
CI / Perform Lint Checks (3.14) (push) Has been cancelled
CI / Python 3.11 on macos-latest (push) Has been cancelled
CI / Python 3.12 on macos-latest (push) Has been cancelled
CI / Python 3.13 on macos-latest (push) Has been cancelled
CI / Python 3.14 on macos-latest (push) Has been cancelled
CI / Python 3.11 on ubuntu-latest (push) Has been cancelled
CI / Python 3.12 on ubuntu-latest (push) Has been cancelled
CI / Python 3.13 on ubuntu-latest (push) Has been cancelled
CI / Python 3.14 on ubuntu-latest (push) Has been cancelled
CI / Python 3.11 on windows-latest (push) Has been cancelled
CI / Python 3.12 on windows-latest (push) Has been cancelled
CI / Python 3.13 on windows-latest (push) Has been cancelled
CI / Python 3.14 on windows-latest (push) Has been cancelled
CodeQL Checks / Analyze (python) (push) Has been cancelled

The C460 on firmware 1.2.2 answers the UDP discovery with
`mgt_encrypt_schm: {"is_support_https": true}` and `encrypt_type:
["3"]`, but no `encrypt_type` inside the scheme and no `encrypt_info`.
`_get_connection_parameters` only looks at those two places for the
encryption type, so the camera ends up as "Unsupported device ... with
no encryption type" even though it works with the same AES login as
every other camera.

This uses the top level list as a last resort: when nothing else names
the encryption type, the device supports https and the list says 3,
treat it as AES.

Co-authored-by: freeKC <7538438+freeKC@users.noreply.github.com>
This commit is contained in:
FreeKC
2026-09-30 00:40:39 +02:00
committed by GitHub
parent b7b41f2c81
commit 9d84bb74e7
2 changed files with 35 additions and 0 deletions

View File

@@ -831,6 +831,13 @@ class Discover:
# Reuse the login_version attribute to pass the max to transport
login_version = max([int(i) for i in et])
if not encrypt_type and encrypt_schm.is_support_https and login_version == 3:
# Some camera firmwares (C460 1.2.2 for one) leave encrypt_type out
# of mgt_encrypt_schm and send no encrypt_info, only the top level
# encrypt_type list. "3" is the AES login that every other camera
# reports as sym_schm AES.
encrypt_type = DeviceEncryptionType.Aes.value
if not encrypt_type:
raise UnsupportedDeviceError(
f"Unsupported device {discovery_result.ip} of type {type_} "

View File

@@ -31,6 +31,8 @@ from kasa.device_factory import (
from kasa.deviceconfig import (
DeviceConfig,
DeviceConnectionParameters,
DeviceEncryptionType,
DeviceFamily,
)
from kasa.discover import (
DiscoveryResult,
@@ -749,3 +751,29 @@ async def test_discovery_device_repr(discovery_mock, mocker):
assert "update() needed" not in repr_
else:
assert "update() needed" in repr_
async def test_connection_parameters_from_encrypt_type_list_only():
"""Cameras that send only the encrypt_type list are treated as AES login."""
result = {
"device_type": "SMART.IPCAMERA",
"device_model": "C460",
"device_id": "0000000000000000000000000000000000000000",
"ip": "127.0.0.123",
"mac": "7C-F1-7E-00-00-00",
"mgt_encrypt_schm": {"is_support_https": True},
"encrypt_type": ["3"],
"firmware_version": "1.2.2 Build 260416 Rel.13928n",
"hardware_version": "1.0",
}
params = Discover._get_connection_parameters(DiscoveryResult.from_dict(result))
assert params.device_family is DeviceFamily.SmartIpCamera
assert params.encryption_type is DeviceEncryptionType.Aes
assert params.login_version == 3
assert params.https is True
# Without the "3" hint the device is still reported as unsupported
result["encrypt_type"] = ["9"]
with pytest.raises(UnsupportedDeviceError, match="no encryption type"):
Discover._get_connection_parameters(DiscoveryResult.from_dict(result))