test(config): pin the Jellyfin name tiers and the address redaction (t41)
Two acceptance items that had no test of their own:
* the Jellyfin auto-detect tiers. t41 replaced the entity-derived search key
(the Android TV Remote entity's friendly_name) with the names setup already
knows — the name the user typed, then the discovery device name. Three tests
pin it, the third being the regression: a Jellyfin player matching the *atv*
friendly_name, with a serving state, used to be auto-detected; now only the
typed/discovered names search. Red proof on the pre-t41 tree (60d884b):
`_find_jellyfin_entity(hass, "jellyfin shield")` DID match
media_player.jellyfin_shield there.
* diagnostics redaction of the renamed address field. The G14 field list already
carried "host" (alongside the legacy spellings), but the test only exercised
the legacy keys — so a future edit could have dropped the live one unnoticed.
The fixture and assertion now cover both spellings.
Verified: 337 passed / 2 skipped, 338 / 1 with androidtvremote2, ruff clean.
This commit is contained in:
1 parent
130dee4bc6
commit
aea9f9f9d2
2 files changed
+93
-1
No files matched your search
@@ -1034,7 +1034,8 @@ class TestEntryDiagnostics:
|
||||
options={
|
||||
"adb_command_enabled": True,
|
||||
"protocol_pairing_code": "4821",
|
||||
"adb_host": "192.168.1.50",
|
||||
"host": "192.168.1.50", # t41: the one address field
|
||||
"adb_host": "192.168.1.50", # legacy spellings stay redacted too
|
||||
"protocol_host": "192.168.1.50",
|
||||
},
|
||||
title="Shield",
|
||||
@@ -1052,6 +1053,7 @@ class TestEntryDiagnostics:
|
||||
# old import pointed at homeassistant.util.diagnostic, which does not
|
||||
# exist, so this pass silently did nothing and only the marker scan
|
||||
# (pairing-/key-shaped names) masked anything.
|
||||
assert payload["entry"]["options"]["host"] == "**REDACTED**"
|
||||
assert payload["entry"]["options"]["adb_host"] == "**REDACTED**"
|
||||
assert payload["entry"]["options"]["protocol_host"] == "**REDACTED**"
|
||||
assert payload["entry"]["data"]["nested"]["adb_host"] == "**REDACTED**"
|
||||
|
||||
@@ -33,6 +33,7 @@ from nsh.const import (
|
||||
CONF_ADB_ENABLED,
|
||||
CONF_ADB_PORT,
|
||||
CONF_HOST,
|
||||
CONF_JELLYFIN_ENTITY,
|
||||
CONF_PAIRING_CODE,
|
||||
CONF_PROTOCOL_ENABLED,
|
||||
CONF_SKIP_PAIRING,
|
||||
@@ -581,6 +582,95 @@ class TestDiscoveryPrefill:
|
||||
assert defaults[CONF_HOST] == DISCOVERED_HOST
|
||||
|
||||
|
||||
class TestJellyfinAutoDetect:
|
||||
"""t41: auto-detect searches with the names setup already knows.
|
||||
|
||||
The removed tier resolved the Android TV Remote entity's ``friendly_name``
|
||||
and searched the Jellyfin registry with THAT. What remains is the name the
|
||||
user typed and the device name from discovery — and another integration's
|
||||
entity is never consulted, not even as a search term.
|
||||
"""
|
||||
|
||||
def _patch_registry(self, monkeypatch, entity_ids):
|
||||
er = sys.modules["homeassistant.helpers.entity_registry"]
|
||||
entities = {
|
||||
eid: SimpleNamespace(
|
||||
domain="media_player",
|
||||
platform="jellyfin",
|
||||
entity_id=eid,
|
||||
original_name=eid.split(".", 1)[1].replace("_", " "),
|
||||
disabled_by=None,
|
||||
)
|
||||
for eid in entity_ids
|
||||
}
|
||||
monkeypatch.setattr(
|
||||
er, "async_get", lambda hass: SimpleNamespace(entities=entities)
|
||||
)
|
||||
|
||||
async def test_the_typed_name_finds_the_jellyfin_player(self, tmp_path, monkeypatch):
|
||||
module = _form_module()
|
||||
_patch_protocol(monkeypatch, module)
|
||||
self._patch_registry(monkeypatch, ["media_player.jellyfin_living_room"])
|
||||
flow, hass = _new_flow(module, tmp_path)
|
||||
state = SimpleNamespace(state="idle")
|
||||
hass.states = SimpleNamespace(
|
||||
get=lambda eid: state if eid == "media_player.jellyfin_living_room" else None
|
||||
)
|
||||
|
||||
await flow.async_step_user(
|
||||
_user_input(**{"name": "Jellyfin Living Room", CONF_PROTOCOL_ENABLED: True})
|
||||
)
|
||||
|
||||
assert flow._user_data[CONF_JELLYFIN_ENTITY] == "media_player.jellyfin_living_room"
|
||||
|
||||
async def test_the_discovered_device_name_is_the_second_tier(
|
||||
self, tmp_path, monkeypatch
|
||||
):
|
||||
module = _form_module()
|
||||
_patch_protocol(monkeypatch, module)
|
||||
self._patch_registry(monkeypatch, ["media_player.jellyfin_living_room"])
|
||||
flow, hass = _new_flow(module, tmp_path)
|
||||
state = SimpleNamespace(state="idle")
|
||||
hass.states = SimpleNamespace(
|
||||
get=lambda eid: state if eid == "media_player.jellyfin_living_room" else None
|
||||
)
|
||||
flow._discovered_name = "jellyfin living room"
|
||||
|
||||
await flow.async_step_user(
|
||||
_user_input(**{"name": "Living Room TV", CONF_PROTOCOL_ENABLED: True})
|
||||
)
|
||||
|
||||
assert flow._user_data[CONF_JELLYFIN_ENTITY] == "media_player.jellyfin_living_room"
|
||||
|
||||
async def test_another_integrations_entity_is_not_a_search_term(
|
||||
self, tmp_path, monkeypatch
|
||||
):
|
||||
"""The regression pin: the old tier searched with the atv friendly_name.
|
||||
|
||||
A Jellyfin player matches THAT name, and the state machine serves it, so
|
||||
the pre-t41 code auto-detected it. Only the typed name may search now.
|
||||
"""
|
||||
module = _form_module()
|
||||
_patch_protocol(monkeypatch, module)
|
||||
self._patch_registry(monkeypatch, ["media_player.jellyfin_shield"])
|
||||
flow, hass = _new_flow(module, tmp_path)
|
||||
atv_state = SimpleNamespace(
|
||||
state="idle", attributes={"friendly_name": "jellyfin shield"}
|
||||
)
|
||||
state = SimpleNamespace(state="idle")
|
||||
hass.states = SimpleNamespace(
|
||||
get=lambda eid: state
|
||||
if eid == "media_player.jellyfin_shield"
|
||||
else (atv_state if eid == "media_player.shield" else None)
|
||||
)
|
||||
|
||||
await flow.async_step_user(
|
||||
_user_input(**{"name": "Living Room", CONF_PROTOCOL_ENABLED: True})
|
||||
)
|
||||
|
||||
assert flow._user_data[CONF_JELLYFIN_ENTITY] == ""
|
||||
|
||||
|
||||
class TestTransportsDefaultOn:
|
||||
"""t41: the two native transports are OURS — both start enabled.
|
||||
|
||||
|
||||
Reference in new issue
Block a user