mirror of
https://github.com/python-kasa/python-kasa.git
synced 2026-07-08 14:52:03 +00:00
tests: add type annotations to CLI, protocol, and smartcam tests (#1687)
Add type annotations (`-> None` return types and parameter types) to test files in the `tests/cli/`, `tests/protocols/`, and `tests/smartcam/` directories. This enables mypy to check test function bodies, catching type errors that were previously hidden.
This commit is contained in:
@@ -16,7 +16,7 @@ from ...conftest import hub_smartcam
|
||||
|
||||
|
||||
@hub_smartcam
|
||||
async def test_alarm(dev: Device):
|
||||
async def test_alarm(dev: Device) -> None:
|
||||
"""Test device alarm."""
|
||||
alarm = dev.modules.get(Module.Alarm)
|
||||
assert alarm
|
||||
@@ -83,7 +83,7 @@ async def test_alarm(dev: Device):
|
||||
|
||||
|
||||
@hub_smartcam
|
||||
async def test_alarm_invalid_setters(dev: Device):
|
||||
async def test_alarm_invalid_setters(dev: Device) -> None:
|
||||
"""Test device alarm invalid setter values."""
|
||||
alarm = dev.modules.get(Module.Alarm)
|
||||
assert alarm
|
||||
@@ -105,7 +105,7 @@ async def test_alarm_invalid_setters(dev: Device):
|
||||
|
||||
|
||||
@hub_smartcam
|
||||
async def test_alarm_features(dev: Device):
|
||||
async def test_alarm_features(dev: Device) -> None:
|
||||
"""Test device alarm features."""
|
||||
alarm = dev.modules.get(Module.Alarm)
|
||||
assert alarm
|
||||
|
||||
@@ -17,7 +17,7 @@ battery_smartcam = parametrize(
|
||||
|
||||
|
||||
@battery_smartcam
|
||||
async def test_battery(dev: Device):
|
||||
async def test_battery(dev: Device) -> None:
|
||||
"""Test device battery."""
|
||||
battery = dev.modules.get(SmartCamModule.SmartCamBattery)
|
||||
assert battery
|
||||
@@ -46,7 +46,9 @@ async def test_battery(dev: Device):
|
||||
("12.3", 12.3), # sanity: happy path
|
||||
],
|
||||
)
|
||||
async def test_battery_temperature_edge_cases(dev: Device, raw, expected):
|
||||
async def test_battery_temperature_edge_cases(
|
||||
dev: Device, raw: str | None, expected: float | None
|
||||
) -> None:
|
||||
battery = dev.modules.get(SmartCamModule.SmartCamBattery)
|
||||
assert battery
|
||||
|
||||
@@ -63,7 +65,9 @@ async def test_battery_temperature_edge_cases(dev: Device, raw, expected):
|
||||
("12000", 12.0), # sanity: parses string -> float(...) / 1000
|
||||
],
|
||||
)
|
||||
async def test_battery_voltage_edge_cases(dev: Device, voltage_raw, expected_v):
|
||||
async def test_battery_voltage_edge_cases(
|
||||
dev: Device, voltage_raw: str | None, expected_v: float | None
|
||||
) -> None:
|
||||
battery = dev.modules.get(SmartCamModule.SmartCamBattery)
|
||||
assert battery
|
||||
|
||||
@@ -82,7 +86,9 @@ async def test_battery_voltage_edge_cases(dev: Device, voltage_raw, expected_v):
|
||||
("NO", False), # sanity: string normalization path
|
||||
],
|
||||
)
|
||||
async def test_battery_charging_edge_cases(dev: Device, charging_raw, expected):
|
||||
async def test_battery_charging_edge_cases(
|
||||
dev: Device, charging_raw: bool | str | None, expected: bool
|
||||
) -> None:
|
||||
battery = dev.modules.get(SmartCamModule.SmartCamBattery)
|
||||
assert battery
|
||||
|
||||
|
||||
@@ -20,7 +20,7 @@ not_child_camera_smartcam = parametrize(
|
||||
|
||||
|
||||
@device_smartcam
|
||||
async def test_state(dev: Device):
|
||||
async def test_state(dev: Device) -> None:
|
||||
if dev.device_type is DeviceType.Hub:
|
||||
pytest.skip("Hubs cannot be switched on and off")
|
||||
|
||||
@@ -31,7 +31,7 @@ async def test_state(dev: Device):
|
||||
|
||||
|
||||
@not_child_camera_smartcam
|
||||
async def test_stream_rtsp_url(dev: Device):
|
||||
async def test_stream_rtsp_url(dev: Device) -> None:
|
||||
camera_module = dev.modules.get(Module.Camera)
|
||||
assert camera_module
|
||||
|
||||
@@ -91,7 +91,7 @@ async def test_stream_rtsp_url(dev: Device):
|
||||
|
||||
|
||||
@not_child_camera_smartcam
|
||||
async def test_onvif_url(dev: Device):
|
||||
async def test_onvif_url(dev: Device) -> None:
|
||||
"""Test the onvif url."""
|
||||
camera_module = dev.modules.get(Module.Camera)
|
||||
assert camera_module
|
||||
|
||||
@@ -15,7 +15,7 @@ childsetup = parametrize(
|
||||
|
||||
|
||||
@childsetup
|
||||
async def test_childsetup_features(dev: Device):
|
||||
async def test_childsetup_features(dev: Device) -> None:
|
||||
"""Test the exposed features."""
|
||||
cs = dev.modules[Module.ChildSetup]
|
||||
|
||||
@@ -27,7 +27,7 @@ async def test_childsetup_features(dev: Device):
|
||||
@childsetup
|
||||
async def test_childsetup_pair(
|
||||
dev: Device, mocker: MockerFixture, caplog: pytest.LogCaptureFixture
|
||||
):
|
||||
) -> None:
|
||||
"""Test device pairing."""
|
||||
caplog.set_level(logging.INFO)
|
||||
mock_query_helper = mocker.spy(dev, "_query_helper")
|
||||
@@ -70,7 +70,7 @@ async def test_childsetup_pair(
|
||||
@childsetup
|
||||
async def test_childsetup_unpair(
|
||||
dev: Device, mocker: MockerFixture, caplog: pytest.LogCaptureFixture
|
||||
):
|
||||
) -> None:
|
||||
"""Test unpair."""
|
||||
mock_query_helper = mocker.spy(dev, "_query_helper")
|
||||
DUMMY_ID = "dummy_id"
|
||||
|
||||
@@ -25,8 +25,8 @@ class Detection(NamedTuple):
|
||||
def parametrize_detection(
|
||||
*,
|
||||
model_filter=None,
|
||||
protocol_filter=None,
|
||||
fixture_name="dev",
|
||||
protocol_filter: set[str] | None = None,
|
||||
fixture_name: str = "dev",
|
||||
extra_params_names: list[str],
|
||||
extra_params_values: list[Detection],
|
||||
):
|
||||
@@ -139,7 +139,7 @@ params_detections = parametrize_detection(
|
||||
@params_detections
|
||||
async def test_detections(
|
||||
dev: Device, module: ModuleName[DetectionModule], feature_name: str
|
||||
):
|
||||
) -> None:
|
||||
detection = dev.modules.get(module)
|
||||
assert detection
|
||||
|
||||
|
||||
@@ -15,7 +15,7 @@ pantilt = parametrize(
|
||||
|
||||
|
||||
@pantilt
|
||||
async def test_pantilt_presets(dev: Device, mocker: MockerFixture):
|
||||
async def test_pantilt_presets(dev: Device, mocker: MockerFixture) -> None:
|
||||
"""Test PanTilt module preset functionality."""
|
||||
pantilt_mod = dev.modules.get(Module.PanTilt)
|
||||
assert pantilt_mod is not None
|
||||
@@ -42,7 +42,7 @@ async def test_pantilt_presets(dev: Device, mocker: MockerFixture):
|
||||
|
||||
|
||||
@pantilt
|
||||
async def test_pantilt_save_preset(dev: Device, mocker: MockerFixture):
|
||||
async def test_pantilt_save_preset(dev: Device, mocker: MockerFixture) -> None:
|
||||
"""Test PanTilt save_preset functionality."""
|
||||
pantilt_mod = dev.modules.get(Module.PanTilt)
|
||||
assert pantilt_mod is not None
|
||||
@@ -62,7 +62,7 @@ async def test_pantilt_save_preset(dev: Device, mocker: MockerFixture):
|
||||
|
||||
|
||||
@pantilt
|
||||
async def test_pantilt_invalid_preset(dev: Device, mocker: MockerFixture):
|
||||
async def test_pantilt_invalid_preset(dev: Device, mocker: MockerFixture) -> None:
|
||||
"""Test set_preset with invalid preset name raises ValueError."""
|
||||
pantilt_mod = dev.modules.get(Module.PanTilt)
|
||||
assert pantilt_mod is not None
|
||||
@@ -81,7 +81,7 @@ async def test_pantilt_invalid_preset(dev: Device, mocker: MockerFixture):
|
||||
|
||||
|
||||
@pantilt
|
||||
async def test_pantilt_move(dev: Device, mocker: MockerFixture):
|
||||
async def test_pantilt_move(dev: Device, mocker: MockerFixture) -> None:
|
||||
"""Test PanTilt move commands."""
|
||||
pantilt_mod = dev.modules.get(Module.PanTilt)
|
||||
assert pantilt_mod is not None
|
||||
@@ -103,7 +103,7 @@ async def test_pantilt_move(dev: Device, mocker: MockerFixture):
|
||||
|
||||
|
||||
@pantilt
|
||||
async def test_pantilt_goto_preset(dev: Device, mocker: MockerFixture):
|
||||
async def test_pantilt_goto_preset(dev: Device, mocker: MockerFixture) -> None:
|
||||
"""Test PanTilt goto_preset command."""
|
||||
pantilt_mod = dev.modules.get(Module.PanTilt)
|
||||
assert pantilt_mod is not None
|
||||
@@ -119,7 +119,7 @@ async def test_pantilt_goto_preset(dev: Device, mocker: MockerFixture):
|
||||
|
||||
|
||||
@pantilt
|
||||
async def test_pantilt_get_presets(dev: Device, mocker: MockerFixture):
|
||||
async def test_pantilt_get_presets(dev: Device, mocker: MockerFixture) -> None:
|
||||
"""Test PanTilt get_presets command."""
|
||||
pantilt_mod = dev.modules.get(Module.PanTilt)
|
||||
assert pantilt_mod is not None
|
||||
@@ -135,7 +135,7 @@ async def test_pantilt_get_presets(dev: Device, mocker: MockerFixture):
|
||||
|
||||
|
||||
@pantilt
|
||||
async def test_pantilt_set_preset_by_id(dev: Device, mocker: MockerFixture):
|
||||
async def test_pantilt_set_preset_by_id(dev: Device, mocker: MockerFixture) -> None:
|
||||
"""Test set_preset with preset ID instead of name."""
|
||||
pantilt_mod = dev.modules.get(Module.PanTilt)
|
||||
assert pantilt_mod is not None
|
||||
@@ -160,7 +160,7 @@ async def test_pantilt_set_preset_by_id(dev: Device, mocker: MockerFixture):
|
||||
|
||||
|
||||
@pantilt
|
||||
async def test_pantilt_set_preset_not_found(dev: Device, mocker: MockerFixture):
|
||||
async def test_pantilt_set_preset_not_found(dev: Device, mocker: MockerFixture) -> None:
|
||||
"""Test set_preset with non-existent preset returns empty dict."""
|
||||
pantilt_mod = dev.modules.get(Module.PanTilt)
|
||||
assert pantilt_mod is not None
|
||||
@@ -177,7 +177,7 @@ async def test_pantilt_set_preset_not_found(dev: Device, mocker: MockerFixture):
|
||||
|
||||
|
||||
@pantilt
|
||||
async def test_pantilt_step_features(dev: Device, mocker: MockerFixture):
|
||||
async def test_pantilt_step_features(dev: Device, mocker: MockerFixture) -> None:
|
||||
"""Test pan/tilt step features."""
|
||||
pantilt_mod = dev.modules.get(Module.PanTilt)
|
||||
assert pantilt_mod is not None
|
||||
@@ -200,7 +200,7 @@ async def test_pantilt_step_features(dev: Device, mocker: MockerFixture):
|
||||
|
||||
|
||||
@pantilt
|
||||
async def test_pantilt_no_presets_in_data(dev: Device, mocker: MockerFixture):
|
||||
async def test_pantilt_no_presets_in_data(dev: Device, mocker: MockerFixture) -> None:
|
||||
"""Test _presets returns empty dict when no preset data."""
|
||||
pantilt_mod = dev.modules.get(Module.PanTilt)
|
||||
assert pantilt_mod is not None
|
||||
|
||||
@@ -17,7 +17,7 @@ from ..conftest import device_smartcam, hub_smartcam
|
||||
|
||||
|
||||
@device_smartcam
|
||||
async def test_state(dev: Device):
|
||||
async def test_state(dev: Device) -> None:
|
||||
if dev.device_type is DeviceType.Hub:
|
||||
pytest.skip("Hubs cannot be switched on and off")
|
||||
|
||||
@@ -38,7 +38,7 @@ async def test_state(dev: Device):
|
||||
|
||||
|
||||
@device_smartcam
|
||||
async def test_alias(dev: Device):
|
||||
async def test_alias(dev: Device) -> None:
|
||||
test_alias = "TEST1234"
|
||||
original = dev.alias
|
||||
|
||||
@@ -53,7 +53,7 @@ async def test_alias(dev: Device):
|
||||
|
||||
|
||||
@hub_smartcam
|
||||
async def test_hub(dev: Device):
|
||||
async def test_hub(dev: Device) -> None:
|
||||
assert dev.children
|
||||
for child in dev.children:
|
||||
assert child.modules
|
||||
@@ -65,7 +65,7 @@ async def test_hub(dev: Device):
|
||||
|
||||
|
||||
@device_smartcam
|
||||
async def test_wifi_scan(dev: SmartCamDevice):
|
||||
async def test_wifi_scan(dev: SmartCamDevice) -> None:
|
||||
fake_scan_data = {
|
||||
"scanApList": {
|
||||
"onboarding": {
|
||||
@@ -97,7 +97,7 @@ async def test_wifi_scan(dev: SmartCamDevice):
|
||||
|
||||
|
||||
@device_smartcam
|
||||
async def test_wifi_join_success_and_errors(dev: SmartCamDevice):
|
||||
async def test_wifi_join_success_and_errors(dev: SmartCamDevice) -> None:
|
||||
dev._networks = [
|
||||
type(
|
||||
"WifiNetwork",
|
||||
@@ -154,7 +154,7 @@ async def test_wifi_join_success_and_errors(dev: SmartCamDevice):
|
||||
|
||||
|
||||
@device_smartcam
|
||||
async def test_device_time(dev: Device, freezer: FrozenDateTimeFactory):
|
||||
async def test_device_time(dev: Device, freezer: FrozenDateTimeFactory) -> None:
|
||||
"""Test a child device gets the time from it's parent module."""
|
||||
fallback_time = datetime.now(UTC).astimezone().replace(microsecond=0)
|
||||
assert dev.time != fallback_time
|
||||
@@ -165,7 +165,7 @@ async def test_device_time(dev: Device, freezer: FrozenDateTimeFactory):
|
||||
|
||||
|
||||
@device_smartcam
|
||||
async def test_wifi_join_typeerror_on_non_rsa_key(dev: SmartCamDevice):
|
||||
async def test_wifi_join_typeerror_on_non_rsa_key(dev: SmartCamDevice) -> None:
|
||||
dev._networks = [
|
||||
type(
|
||||
"WifiNetwork",
|
||||
|
||||
Reference in New Issue
Block a user