Rename "satellite enabled" to "mute" (#105619)
This commit is contained in:
parent
797af14012
commit
36c56eb32a
7 changed files with 81 additions and 83 deletions
|
@ -17,11 +17,11 @@ class SatelliteDevice:
|
||||||
satellite_id: str
|
satellite_id: str
|
||||||
device_id: str
|
device_id: str
|
||||||
is_active: bool = False
|
is_active: bool = False
|
||||||
is_enabled: bool = True
|
is_muted: bool = False
|
||||||
pipeline_name: str | None = None
|
pipeline_name: str | None = None
|
||||||
|
|
||||||
_is_active_listener: Callable[[], None] | None = None
|
_is_active_listener: Callable[[], None] | None = None
|
||||||
_is_enabled_listener: Callable[[], None] | None = None
|
_is_muted_listener: Callable[[], None] | None = None
|
||||||
_pipeline_listener: Callable[[], None] | None = None
|
_pipeline_listener: Callable[[], None] | None = None
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
|
@ -33,12 +33,12 @@ class SatelliteDevice:
|
||||||
self._is_active_listener()
|
self._is_active_listener()
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def set_is_enabled(self, enabled: bool) -> None:
|
def set_is_muted(self, muted: bool) -> None:
|
||||||
"""Set enabled state."""
|
"""Set muted state."""
|
||||||
if enabled != self.is_enabled:
|
if muted != self.is_muted:
|
||||||
self.is_enabled = enabled
|
self.is_muted = muted
|
||||||
if self._is_enabled_listener is not None:
|
if self._is_muted_listener is not None:
|
||||||
self._is_enabled_listener()
|
self._is_muted_listener()
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def set_pipeline_name(self, pipeline_name: str) -> None:
|
def set_pipeline_name(self, pipeline_name: str) -> None:
|
||||||
|
@ -54,9 +54,9 @@ class SatelliteDevice:
|
||||||
self._is_active_listener = is_active_listener
|
self._is_active_listener = is_active_listener
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def set_is_enabled_listener(self, is_enabled_listener: Callable[[], None]) -> None:
|
def set_is_muted_listener(self, is_muted_listener: Callable[[], None]) -> None:
|
||||||
"""Listen for updates to is_enabled."""
|
"""Listen for updates to muted status."""
|
||||||
self._is_enabled_listener = is_enabled_listener
|
self._is_muted_listener = is_muted_listener
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def set_pipeline_listener(self, pipeline_listener: Callable[[], None]) -> None:
|
def set_pipeline_listener(self, pipeline_listener: Callable[[], None]) -> None:
|
||||||
|
@ -70,11 +70,11 @@ class SatelliteDevice:
|
||||||
"binary_sensor", DOMAIN, f"{self.satellite_id}-assist_in_progress"
|
"binary_sensor", DOMAIN, f"{self.satellite_id}-assist_in_progress"
|
||||||
)
|
)
|
||||||
|
|
||||||
def get_satellite_enabled_entity_id(self, hass: HomeAssistant) -> str | None:
|
def get_muted_entity_id(self, hass: HomeAssistant) -> str | None:
|
||||||
"""Return entity id for satellite enabled switch."""
|
"""Return entity id for satellite muted switch."""
|
||||||
ent_reg = er.async_get(hass)
|
ent_reg = er.async_get(hass)
|
||||||
return ent_reg.async_get_entity_id(
|
return ent_reg.async_get_entity_id(
|
||||||
"switch", DOMAIN, f"{self.satellite_id}-satellite_enabled"
|
"switch", DOMAIN, f"{self.satellite_id}-mute"
|
||||||
)
|
)
|
||||||
|
|
||||||
def get_pipeline_entity_id(self, hass: HomeAssistant) -> str | None:
|
def get_pipeline_entity_id(self, hass: HomeAssistant) -> str | None:
|
||||||
|
|
|
@ -49,7 +49,6 @@ class WyomingSatellite:
|
||||||
self.hass = hass
|
self.hass = hass
|
||||||
self.service = service
|
self.service = service
|
||||||
self.device = device
|
self.device = device
|
||||||
self.is_enabled = True
|
|
||||||
self.is_running = True
|
self.is_running = True
|
||||||
|
|
||||||
self._client: AsyncTcpClient | None = None
|
self._client: AsyncTcpClient | None = None
|
||||||
|
@ -57,9 +56,9 @@ class WyomingSatellite:
|
||||||
self._is_pipeline_running = False
|
self._is_pipeline_running = False
|
||||||
self._audio_queue: asyncio.Queue[bytes | None] = asyncio.Queue()
|
self._audio_queue: asyncio.Queue[bytes | None] = asyncio.Queue()
|
||||||
self._pipeline_id: str | None = None
|
self._pipeline_id: str | None = None
|
||||||
self._enabled_changed_event = asyncio.Event()
|
self._muted_changed_event = asyncio.Event()
|
||||||
|
|
||||||
self.device.set_is_enabled_listener(self._enabled_changed)
|
self.device.set_is_muted_listener(self._muted_changed)
|
||||||
self.device.set_pipeline_listener(self._pipeline_changed)
|
self.device.set_pipeline_listener(self._pipeline_changed)
|
||||||
|
|
||||||
async def run(self) -> None:
|
async def run(self) -> None:
|
||||||
|
@ -69,11 +68,11 @@ class WyomingSatellite:
|
||||||
try:
|
try:
|
||||||
while self.is_running:
|
while self.is_running:
|
||||||
try:
|
try:
|
||||||
# Check if satellite has been disabled
|
# Check if satellite has been muted
|
||||||
while not self.device.is_enabled:
|
while self.device.is_muted:
|
||||||
await self.on_disabled()
|
await self.on_muted()
|
||||||
if not self.is_running:
|
if not self.is_running:
|
||||||
# Satellite was stopped while waiting to be enabled
|
# Satellite was stopped while waiting to be unmuted
|
||||||
return
|
return
|
||||||
|
|
||||||
# Connect and run pipeline loop
|
# Connect and run pipeline loop
|
||||||
|
@ -92,8 +91,8 @@ class WyomingSatellite:
|
||||||
"""Signal satellite task to stop running."""
|
"""Signal satellite task to stop running."""
|
||||||
self.is_running = False
|
self.is_running = False
|
||||||
|
|
||||||
# Unblock waiting for enabled
|
# Unblock waiting for unmuted
|
||||||
self._enabled_changed_event.set()
|
self._muted_changed_event.set()
|
||||||
|
|
||||||
async def on_restart(self) -> None:
|
async def on_restart(self) -> None:
|
||||||
"""Block until pipeline loop will be restarted."""
|
"""Block until pipeline loop will be restarted."""
|
||||||
|
@ -111,9 +110,9 @@ class WyomingSatellite:
|
||||||
)
|
)
|
||||||
await asyncio.sleep(_RECONNECT_SECONDS)
|
await asyncio.sleep(_RECONNECT_SECONDS)
|
||||||
|
|
||||||
async def on_disabled(self) -> None:
|
async def on_muted(self) -> None:
|
||||||
"""Block until device may be enabled again."""
|
"""Block until device may be unmated again."""
|
||||||
await self._enabled_changed_event.wait()
|
await self._muted_changed_event.wait()
|
||||||
|
|
||||||
async def on_stopped(self) -> None:
|
async def on_stopped(self) -> None:
|
||||||
"""Run when run() has fully stopped."""
|
"""Run when run() has fully stopped."""
|
||||||
|
@ -121,15 +120,14 @@ class WyomingSatellite:
|
||||||
|
|
||||||
# -------------------------------------------------------------------------
|
# -------------------------------------------------------------------------
|
||||||
|
|
||||||
def _enabled_changed(self) -> None:
|
def _muted_changed(self) -> None:
|
||||||
"""Run when device enabled status changes."""
|
"""Run when device muted status changes."""
|
||||||
|
if self.device.is_muted:
|
||||||
if not self.device.is_enabled:
|
|
||||||
# Cancel any running pipeline
|
# Cancel any running pipeline
|
||||||
self._audio_queue.put_nowait(None)
|
self._audio_queue.put_nowait(None)
|
||||||
|
|
||||||
self._enabled_changed_event.set()
|
self._muted_changed_event.set()
|
||||||
self._enabled_changed_event.clear()
|
self._muted_changed_event.clear()
|
||||||
|
|
||||||
def _pipeline_changed(self) -> None:
|
def _pipeline_changed(self) -> None:
|
||||||
"""Run when device pipeline changes."""
|
"""Run when device pipeline changes."""
|
||||||
|
@ -141,7 +139,7 @@ class WyomingSatellite:
|
||||||
"""Run pipelines until an error occurs."""
|
"""Run pipelines until an error occurs."""
|
||||||
self.device.set_is_active(False)
|
self.device.set_is_active(False)
|
||||||
|
|
||||||
while self.is_running and self.is_enabled:
|
while self.is_running and (not self.device.is_muted):
|
||||||
try:
|
try:
|
||||||
await self._connect()
|
await self._connect()
|
||||||
break
|
break
|
||||||
|
@ -151,7 +149,7 @@ class WyomingSatellite:
|
||||||
assert self._client is not None
|
assert self._client is not None
|
||||||
_LOGGER.debug("Connected to satellite")
|
_LOGGER.debug("Connected to satellite")
|
||||||
|
|
||||||
if (not self.is_running) or (not self.is_enabled):
|
if (not self.is_running) or self.device.is_muted:
|
||||||
# Run was cancelled or satellite was disabled during connection
|
# Run was cancelled or satellite was disabled during connection
|
||||||
return
|
return
|
||||||
|
|
||||||
|
@ -160,7 +158,7 @@ class WyomingSatellite:
|
||||||
|
|
||||||
# Wait until we get RunPipeline event
|
# Wait until we get RunPipeline event
|
||||||
run_pipeline: RunPipeline | None = None
|
run_pipeline: RunPipeline | None = None
|
||||||
while self.is_running and self.is_enabled:
|
while self.is_running and (not self.device.is_muted):
|
||||||
run_event = await self._client.read_event()
|
run_event = await self._client.read_event()
|
||||||
if run_event is None:
|
if run_event is None:
|
||||||
raise ConnectionResetError("Satellite disconnected")
|
raise ConnectionResetError("Satellite disconnected")
|
||||||
|
@ -174,7 +172,7 @@ class WyomingSatellite:
|
||||||
assert run_pipeline is not None
|
assert run_pipeline is not None
|
||||||
_LOGGER.debug("Received run information: %s", run_pipeline)
|
_LOGGER.debug("Received run information: %s", run_pipeline)
|
||||||
|
|
||||||
if (not self.is_running) or (not self.is_enabled):
|
if (not self.is_running) or self.device.is_muted:
|
||||||
# Run was cancelled or satellite was disabled while waiting for
|
# Run was cancelled or satellite was disabled while waiting for
|
||||||
# RunPipeline event.
|
# RunPipeline event.
|
||||||
return
|
return
|
||||||
|
@ -189,7 +187,7 @@ class WyomingSatellite:
|
||||||
raise ValueError(f"Invalid end stage: {end_stage}")
|
raise ValueError(f"Invalid end stage: {end_stage}")
|
||||||
|
|
||||||
# Each loop is a pipeline run
|
# Each loop is a pipeline run
|
||||||
while self.is_running and self.is_enabled:
|
while self.is_running and (not self.device.is_muted):
|
||||||
# Use select to get pipeline each time in case it's changed
|
# Use select to get pipeline each time in case it's changed
|
||||||
pipeline_id = pipeline_select.get_chosen_pipeline(
|
pipeline_id = pipeline_select.get_chosen_pipeline(
|
||||||
self.hass,
|
self.hass,
|
||||||
|
|
|
@ -42,8 +42,8 @@
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"switch": {
|
"switch": {
|
||||||
"satellite_enabled": {
|
"mute": {
|
||||||
"name": "Satellite enabled"
|
"name": "Mute"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -29,17 +29,17 @@ async def async_setup_entry(
|
||||||
# Setup is only forwarded for satellites
|
# Setup is only forwarded for satellites
|
||||||
assert item.satellite is not None
|
assert item.satellite is not None
|
||||||
|
|
||||||
async_add_entities([WyomingSatelliteEnabledSwitch(item.satellite.device)])
|
async_add_entities([WyomingSatelliteMuteSwitch(item.satellite.device)])
|
||||||
|
|
||||||
|
|
||||||
class WyomingSatelliteEnabledSwitch(
|
class WyomingSatelliteMuteSwitch(
|
||||||
WyomingSatelliteEntity, restore_state.RestoreEntity, SwitchEntity
|
WyomingSatelliteEntity, restore_state.RestoreEntity, SwitchEntity
|
||||||
):
|
):
|
||||||
"""Entity to represent if satellite is enabled."""
|
"""Entity to represent if satellite is muted."""
|
||||||
|
|
||||||
entity_description = SwitchEntityDescription(
|
entity_description = SwitchEntityDescription(
|
||||||
key="satellite_enabled",
|
key="mute",
|
||||||
translation_key="satellite_enabled",
|
translation_key="mute",
|
||||||
entity_category=EntityCategory.CONFIG,
|
entity_category=EntityCategory.CONFIG,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -49,17 +49,17 @@ class WyomingSatelliteEnabledSwitch(
|
||||||
|
|
||||||
state = await self.async_get_last_state()
|
state = await self.async_get_last_state()
|
||||||
|
|
||||||
# Default to on
|
# Default to off
|
||||||
self._attr_is_on = (state is None) or (state.state == STATE_ON)
|
self._attr_is_on = (state is not None) and (state.state == STATE_ON)
|
||||||
|
|
||||||
async def async_turn_on(self, **kwargs: Any) -> None:
|
async def async_turn_on(self, **kwargs: Any) -> None:
|
||||||
"""Turn on."""
|
"""Turn on."""
|
||||||
self._attr_is_on = True
|
self._attr_is_on = True
|
||||||
self.async_write_ha_state()
|
self.async_write_ha_state()
|
||||||
self._device.set_is_enabled(True)
|
self._device.set_is_muted(True)
|
||||||
|
|
||||||
async def async_turn_off(self, **kwargs: Any) -> None:
|
async def async_turn_off(self, **kwargs: Any) -> None:
|
||||||
"""Turn off."""
|
"""Turn off."""
|
||||||
self._attr_is_on = False
|
self._attr_is_on = False
|
||||||
self.async_write_ha_state()
|
self.async_write_ha_state()
|
||||||
self._device.set_is_enabled(False)
|
self._device.set_is_muted(False)
|
||||||
|
|
|
@ -5,7 +5,7 @@ from homeassistant.components.assist_pipeline.select import OPTION_PREFERRED
|
||||||
from homeassistant.components.wyoming import DOMAIN
|
from homeassistant.components.wyoming import DOMAIN
|
||||||
from homeassistant.components.wyoming.devices import SatelliteDevice
|
from homeassistant.components.wyoming.devices import SatelliteDevice
|
||||||
from homeassistant.config_entries import ConfigEntry
|
from homeassistant.config_entries import ConfigEntry
|
||||||
from homeassistant.const import STATE_OFF, STATE_ON
|
from homeassistant.const import STATE_OFF
|
||||||
from homeassistant.core import HomeAssistant
|
from homeassistant.core import HomeAssistant
|
||||||
from homeassistant.helpers import device_registry as dr
|
from homeassistant.helpers import device_registry as dr
|
||||||
|
|
||||||
|
@ -34,11 +34,11 @@ async def test_device_registry_info(
|
||||||
assert assist_in_progress_state is not None
|
assert assist_in_progress_state is not None
|
||||||
assert assist_in_progress_state.state == STATE_OFF
|
assert assist_in_progress_state.state == STATE_OFF
|
||||||
|
|
||||||
satellite_enabled_id = satellite_device.get_satellite_enabled_entity_id(hass)
|
muted_id = satellite_device.get_muted_entity_id(hass)
|
||||||
assert satellite_enabled_id
|
assert muted_id
|
||||||
satellite_enabled_state = hass.states.get(satellite_enabled_id)
|
muted_state = hass.states.get(muted_id)
|
||||||
assert satellite_enabled_state is not None
|
assert muted_state is not None
|
||||||
assert satellite_enabled_state.state == STATE_ON
|
assert muted_state.state == STATE_OFF
|
||||||
|
|
||||||
pipeline_entity_id = satellite_device.get_pipeline_entity_id(hass)
|
pipeline_entity_id = satellite_device.get_pipeline_entity_id(hass)
|
||||||
assert pipeline_entity_id
|
assert pipeline_entity_id
|
||||||
|
@ -59,9 +59,9 @@ async def test_remove_device_registry_entry(
|
||||||
assert assist_in_progress_id
|
assert assist_in_progress_id
|
||||||
assert hass.states.get(assist_in_progress_id) is not None
|
assert hass.states.get(assist_in_progress_id) is not None
|
||||||
|
|
||||||
satellite_enabled_id = satellite_device.get_satellite_enabled_entity_id(hass)
|
muted_id = satellite_device.get_muted_entity_id(hass)
|
||||||
assert satellite_enabled_id
|
assert muted_id
|
||||||
assert hass.states.get(satellite_enabled_id) is not None
|
assert hass.states.get(muted_id) is not None
|
||||||
|
|
||||||
pipeline_entity_id = satellite_device.get_pipeline_entity_id(hass)
|
pipeline_entity_id = satellite_device.get_pipeline_entity_id(hass)
|
||||||
assert pipeline_entity_id
|
assert pipeline_entity_id
|
||||||
|
@ -74,5 +74,5 @@ async def test_remove_device_registry_entry(
|
||||||
|
|
||||||
# Everything should be gone
|
# Everything should be gone
|
||||||
assert hass.states.get(assist_in_progress_id) is None
|
assert hass.states.get(assist_in_progress_id) is None
|
||||||
assert hass.states.get(satellite_enabled_id) is None
|
assert hass.states.get(muted_id) is None
|
||||||
assert hass.states.get(pipeline_entity_id) is None
|
assert hass.states.get(pipeline_entity_id) is None
|
||||||
|
|
|
@ -196,7 +196,7 @@ async def test_satellite_pipeline(hass: HomeAssistant) -> None:
|
||||||
await mock_client.detect_event.wait()
|
await mock_client.detect_event.wait()
|
||||||
|
|
||||||
assert not device.is_active
|
assert not device.is_active
|
||||||
assert device.is_enabled
|
assert not device.is_muted
|
||||||
|
|
||||||
# Wake word is detected
|
# Wake word is detected
|
||||||
event_callback(
|
event_callback(
|
||||||
|
@ -312,36 +312,36 @@ async def test_satellite_pipeline(hass: HomeAssistant) -> None:
|
||||||
await hass.async_block_till_done()
|
await hass.async_block_till_done()
|
||||||
|
|
||||||
|
|
||||||
async def test_satellite_disabled(hass: HomeAssistant) -> None:
|
async def test_satellite_muted(hass: HomeAssistant) -> None:
|
||||||
"""Test callback for a satellite that has been disabled."""
|
"""Test callback for a satellite that has been muted."""
|
||||||
on_disabled_event = asyncio.Event()
|
on_muted_event = asyncio.Event()
|
||||||
|
|
||||||
original_make_satellite = wyoming._make_satellite
|
original_make_satellite = wyoming._make_satellite
|
||||||
|
|
||||||
def make_disabled_satellite(
|
def make_muted_satellite(
|
||||||
hass: HomeAssistant, config_entry: ConfigEntry, service: WyomingService
|
hass: HomeAssistant, config_entry: ConfigEntry, service: WyomingService
|
||||||
):
|
):
|
||||||
satellite = original_make_satellite(hass, config_entry, service)
|
satellite = original_make_satellite(hass, config_entry, service)
|
||||||
satellite.device.set_is_enabled(False)
|
satellite.device.set_is_muted(True)
|
||||||
|
|
||||||
return satellite
|
return satellite
|
||||||
|
|
||||||
async def on_disabled(self):
|
async def on_muted(self):
|
||||||
self.device.set_is_enabled(True)
|
self.device.set_is_muted(False)
|
||||||
on_disabled_event.set()
|
on_muted_event.set()
|
||||||
|
|
||||||
with patch(
|
with patch(
|
||||||
"homeassistant.components.wyoming.data.load_wyoming_info",
|
"homeassistant.components.wyoming.data.load_wyoming_info",
|
||||||
return_value=SATELLITE_INFO,
|
return_value=SATELLITE_INFO,
|
||||||
), patch(
|
), patch(
|
||||||
"homeassistant.components.wyoming._make_satellite", make_disabled_satellite
|
"homeassistant.components.wyoming._make_satellite", make_muted_satellite
|
||||||
), patch(
|
), patch(
|
||||||
"homeassistant.components.wyoming.satellite.WyomingSatellite.on_disabled",
|
"homeassistant.components.wyoming.satellite.WyomingSatellite.on_muted",
|
||||||
on_disabled,
|
on_muted,
|
||||||
):
|
):
|
||||||
await setup_config_entry(hass)
|
await setup_config_entry(hass)
|
||||||
async with asyncio.timeout(1):
|
async with asyncio.timeout(1):
|
||||||
await on_disabled_event.wait()
|
await on_muted_event.wait()
|
||||||
|
|
||||||
|
|
||||||
async def test_satellite_restart(hass: HomeAssistant) -> None:
|
async def test_satellite_restart(hass: HomeAssistant) -> None:
|
||||||
|
|
|
@ -5,28 +5,28 @@ from homeassistant.const import STATE_OFF, STATE_ON
|
||||||
from homeassistant.core import HomeAssistant
|
from homeassistant.core import HomeAssistant
|
||||||
|
|
||||||
|
|
||||||
async def test_satellite_enabled(
|
async def test_muted(
|
||||||
hass: HomeAssistant,
|
hass: HomeAssistant,
|
||||||
satellite_config_entry: ConfigEntry,
|
satellite_config_entry: ConfigEntry,
|
||||||
satellite_device: SatelliteDevice,
|
satellite_device: SatelliteDevice,
|
||||||
) -> None:
|
) -> None:
|
||||||
"""Test satellite enabled."""
|
"""Test satellite muted."""
|
||||||
satellite_enabled_id = satellite_device.get_satellite_enabled_entity_id(hass)
|
muted_id = satellite_device.get_muted_entity_id(hass)
|
||||||
assert satellite_enabled_id
|
assert muted_id
|
||||||
|
|
||||||
state = hass.states.get(satellite_enabled_id)
|
state = hass.states.get(muted_id)
|
||||||
assert state is not None
|
assert state is not None
|
||||||
assert state.state == STATE_ON
|
assert state.state == STATE_OFF
|
||||||
assert satellite_device.is_enabled
|
assert not satellite_device.is_muted
|
||||||
|
|
||||||
await hass.services.async_call(
|
await hass.services.async_call(
|
||||||
"switch",
|
"switch",
|
||||||
"turn_off",
|
"turn_on",
|
||||||
{"entity_id": satellite_enabled_id},
|
{"entity_id": muted_id},
|
||||||
blocking=True,
|
blocking=True,
|
||||||
)
|
)
|
||||||
|
|
||||||
state = hass.states.get(satellite_enabled_id)
|
state = hass.states.get(muted_id)
|
||||||
assert state is not None
|
assert state is not None
|
||||||
assert state.state == STATE_OFF
|
assert state.state == STATE_ON
|
||||||
assert not satellite_device.is_enabled
|
assert satellite_device.is_muted
|
||||||
|
|
Loading…
Add table
Reference in a new issue