Files
ha-nvidia-shield/tests
James Mackay 3175582419 fix(config): degrade an unreachable Shield to the pairing form (t44 F1)
`_start_protocol_pairing` called androidtvremote2's cert generation and
`async_start_pairing` with no try/except, so `CannotConnect` propagated straight
out of `async_step_protocol_pair`. The caller already had the shape for a soft
failure — `_async_begin_protocol_pairing()` returns `(client, None) | (None,
error)` and `_async_restart_protocol_pairing` renders `errors["base"]` — the
exception simply bypassed it, and the protocol_pair form never appeared: not the
address field, not the "continue without pairing" escape.

That made it a default-path crash rather than an edge case: t41 turned the
protocol transport ON by default, so an asleep, rebooting or mis-addressed Shield
(whenever someone adds the integration, or skips ADB pairing into this step)
raised out of the flow instead of showing the form. The reviewer reproduced both
under real HA.

Now the step returns `(None, "protocol_unreachable")`, logs the address and the
library error, discards the half-built client so a retry starts clean, and renders
the same form the other failures render — with the address editable and the skip
option intact. `protocol_unreachable` is documented in strings.json AND
translations/en.json (a form error without copy shows a bare key in the UI).

Tests (tests/test_config_flow_ux.py::TestUnreachableShieldDuringPairing): the fake
client can now fail to start pairing, and five cases cover fresh setup, the
ADB-skip route into the protocol step, reconfigure, reauth and the skip path that
still finishes the entry — all as FORMS, never exceptions. Red proof on HEAD:
the same drive raises CannotConnectStubError out of async_step_user.

Verified: 361 passed / 2 skipped, 362 / 1 with androidtvremote2, ruff clean.
2026-10-11 06:37:18 +01:00
..