mirror of
https://github.com/home-assistant/core.git
synced 2026-02-15 07:36:16 +00:00
Add connectivity mode diagnostics sensor for Airthings BLE (#161261)
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> Co-authored-by: Joostlek <joostlek@outlook.com>
This commit is contained in:
committed by
GitHub
parent
36b9234f26
commit
9c07550f40
@@ -1,6 +1,14 @@
|
||||
{
|
||||
"entity": {
|
||||
"sensor": {
|
||||
"connectivity_mode": {
|
||||
"default": "mdi:bluetooth-off",
|
||||
"state": {
|
||||
"bluetooth": "mdi:bluetooth",
|
||||
"not_configured": "mdi:alert-circle",
|
||||
"smartlink": "mdi:hub"
|
||||
}
|
||||
},
|
||||
"radon_1day_avg": {
|
||||
"default": "mdi:radioactive"
|
||||
},
|
||||
|
||||
@@ -5,7 +5,7 @@ from __future__ import annotations
|
||||
import dataclasses
|
||||
import logging
|
||||
|
||||
from airthings_ble import AirthingsDevice
|
||||
from airthings_ble import AirthingsConnectivityMode, AirthingsDevice
|
||||
|
||||
from homeassistant.components.sensor import (
|
||||
SensorDeviceClass,
|
||||
@@ -41,6 +41,12 @@ from .coordinator import AirthingsBLEConfigEntry, AirthingsBLEDataUpdateCoordina
|
||||
|
||||
_LOGGER = logging.getLogger(__name__)
|
||||
|
||||
CONNECTIVITY_MODE_MAP = {
|
||||
AirthingsConnectivityMode.BLE.value: "bluetooth",
|
||||
AirthingsConnectivityMode.SMARTLINK.value: "smartlink",
|
||||
AirthingsConnectivityMode.NOT_CONFIGURED.value: "not_configured",
|
||||
}
|
||||
|
||||
SENSORS_MAPPING_TEMPLATE: dict[str, SensorEntityDescription] = {
|
||||
"radon_1day_avg": SensorEntityDescription(
|
||||
key="radon_1day_avg",
|
||||
@@ -129,6 +135,14 @@ SENSORS_MAPPING_TEMPLATE: dict[str, SensorEntityDescription] = {
|
||||
state_class=SensorStateClass.MEASUREMENT,
|
||||
suggested_display_precision=0,
|
||||
),
|
||||
"connectivity_mode": SensorEntityDescription(
|
||||
key="connectivity_mode",
|
||||
translation_key="connectivity_mode",
|
||||
device_class=SensorDeviceClass.ENUM,
|
||||
options=list(CONNECTIVITY_MODE_MAP.values()),
|
||||
entity_category=EntityCategory.DIAGNOSTIC,
|
||||
entity_registry_enabled_default=False,
|
||||
),
|
||||
}
|
||||
|
||||
PARALLEL_UPDATES = 0
|
||||
@@ -256,4 +270,12 @@ class AirthingsSensor(
|
||||
@property
|
||||
def native_value(self) -> StateType:
|
||||
"""Return the value reported by the sensor."""
|
||||
return self.coordinator.data.sensors[self.entity_description.key]
|
||||
value = self.coordinator.data.sensors[self.entity_description.key]
|
||||
|
||||
# Map connectivity mode to enum values
|
||||
if self.entity_description.key == "connectivity_mode":
|
||||
if not isinstance(value, str):
|
||||
return None
|
||||
return CONNECTIVITY_MODE_MAP.get(value)
|
||||
|
||||
return value
|
||||
|
||||
@@ -30,6 +30,14 @@
|
||||
"ambient_noise": {
|
||||
"name": "Ambient noise"
|
||||
},
|
||||
"connectivity_mode": {
|
||||
"name": "Connectivity mode",
|
||||
"state": {
|
||||
"bluetooth": "Bluetooth",
|
||||
"not_configured": "Not configured",
|
||||
"smartlink": "SmartLink"
|
||||
}
|
||||
},
|
||||
"illuminance": {
|
||||
"name": "[%key:component::sensor::entity_component::illuminance::name%]"
|
||||
},
|
||||
|
||||
@@ -274,6 +274,7 @@ WAVE_ENHANCE_DEVICE_INFO = AirthingsDevice(
|
||||
name="Airthings Wave Enhance",
|
||||
identifier="123456",
|
||||
sensors={
|
||||
"connectivity_mode": "Bluetooth",
|
||||
"lux": 25,
|
||||
"battery": 85,
|
||||
"humidity": 60.0,
|
||||
|
||||
@@ -1,7 +1,9 @@
|
||||
"""Test the Airthings Wave sensor."""
|
||||
|
||||
from copy import deepcopy
|
||||
from datetime import timedelta
|
||||
import logging
|
||||
from typing import Any
|
||||
|
||||
from freezegun.api import FrozenDateTimeFactory
|
||||
import pytest
|
||||
@@ -12,7 +14,7 @@ from homeassistant.components.airthings_ble.const import (
|
||||
DEVICE_SPECIFIC_SCAN_INTERVAL,
|
||||
DOMAIN,
|
||||
)
|
||||
from homeassistant.const import Platform
|
||||
from homeassistant.const import STATE_UNKNOWN, Platform
|
||||
from homeassistant.core import HomeAssistant
|
||||
from homeassistant.helpers import device_registry as dr, entity_registry as er
|
||||
|
||||
@@ -20,6 +22,7 @@ from . import (
|
||||
CO2_V1,
|
||||
CO2_V2,
|
||||
CORENTIUM_HOME_2_DEVICE_INFO,
|
||||
CORENTIUM_HOME_2_SERVICE_INFO,
|
||||
HUMIDITY_V2,
|
||||
TEMPERATURE_V1,
|
||||
VOC_V1,
|
||||
@@ -242,7 +245,7 @@ async def test_migration_with_all_unique_ids(
|
||||
("noise", "Ambient noise"),
|
||||
],
|
||||
)
|
||||
async def test_translation_keys(
|
||||
async def test_translation_keys_wave_enhance(
|
||||
hass: HomeAssistant,
|
||||
entity_registry: er.EntityRegistry,
|
||||
device_registry: dr.DeviceRegistry,
|
||||
@@ -250,7 +253,7 @@ async def test_translation_keys(
|
||||
expected_sensor_name: str,
|
||||
) -> None:
|
||||
"""Test that translated sensor names are correct."""
|
||||
entry = create_entry(hass, WAVE_ENHANCE_SERVICE_INFO, WAVE_DEVICE_INFO)
|
||||
entry = create_entry(hass, WAVE_ENHANCE_SERVICE_INFO, WAVE_ENHANCE_DEVICE_INFO)
|
||||
device = create_device(
|
||||
entry, device_registry, WAVE_ENHANCE_SERVICE_INFO, WAVE_ENHANCE_DEVICE_INFO
|
||||
)
|
||||
@@ -280,6 +283,87 @@ async def test_translation_keys(
|
||||
assert state.attributes.get("friendly_name") == expected_name
|
||||
|
||||
|
||||
async def test_disabled_connectivity_mode_corentium_home_2(
|
||||
hass: HomeAssistant,
|
||||
entity_registry: er.EntityRegistry,
|
||||
device_registry: dr.DeviceRegistry,
|
||||
) -> None:
|
||||
"""Test that translated sensor names are correct for disabled sensors."""
|
||||
entry = create_entry(
|
||||
hass,
|
||||
CORENTIUM_HOME_2_SERVICE_INFO,
|
||||
CORENTIUM_HOME_2_DEVICE_INFO,
|
||||
)
|
||||
device = create_device(
|
||||
entry,
|
||||
device_registry,
|
||||
CORENTIUM_HOME_2_SERVICE_INFO,
|
||||
CORENTIUM_HOME_2_DEVICE_INFO,
|
||||
)
|
||||
|
||||
with (
|
||||
patch_async_ble_device_from_address(CORENTIUM_HOME_2_SERVICE_INFO.device),
|
||||
patch_async_discovered_service_info([CORENTIUM_HOME_2_SERVICE_INFO]),
|
||||
patch_airthings_ble(CORENTIUM_HOME_2_DEVICE_INFO),
|
||||
):
|
||||
await hass.config_entries.async_setup(entry.entry_id)
|
||||
await hass.async_block_till_done()
|
||||
|
||||
assert device is not None
|
||||
assert device.name == "Airthings Corentium Home 2 (123456)"
|
||||
|
||||
unique_id = f"{CORENTIUM_HOME_2_DEVICE_INFO.address}_connectivity_mode"
|
||||
|
||||
entity_id = entity_registry.async_get_entity_id(Platform.SENSOR, DOMAIN, unique_id)
|
||||
assert entity_id is not None
|
||||
|
||||
entity_entry = entity_registry.async_get(entity_id)
|
||||
assert entity_entry is not None
|
||||
assert entity_entry.disabled
|
||||
assert entity_entry.disabled_by is er.RegistryEntryDisabler.INTEGRATION
|
||||
|
||||
|
||||
@pytest.mark.usefixtures("entity_registry_enabled_by_default")
|
||||
@pytest.mark.parametrize(
|
||||
("source_value", "expected_state"),
|
||||
[
|
||||
(None, STATE_UNKNOWN),
|
||||
(123, STATE_UNKNOWN),
|
||||
(45.6, STATE_UNKNOWN),
|
||||
("Bluetooth", "bluetooth"),
|
||||
],
|
||||
)
|
||||
async def test_connectivity_mode(
|
||||
hass: HomeAssistant,
|
||||
entity_registry: er.EntityRegistry,
|
||||
device_registry: dr.DeviceRegistry,
|
||||
source_value: Any,
|
||||
expected_state: str,
|
||||
) -> None:
|
||||
"""Test that non-string connectivity mode values are handled correctly."""
|
||||
test_device = deepcopy(CORENTIUM_HOME_2_DEVICE_INFO)
|
||||
|
||||
# Non-string value, will be mapped to 'unknown' state
|
||||
test_device.sensors["connectivity_mode"] = source_value
|
||||
|
||||
entry = create_entry(hass, CORENTIUM_HOME_2_SERVICE_INFO, test_device)
|
||||
create_device(entry, device_registry, CORENTIUM_HOME_2_SERVICE_INFO, test_device)
|
||||
|
||||
with (
|
||||
patch_async_ble_device_from_address(CORENTIUM_HOME_2_SERVICE_INFO.device),
|
||||
patch_async_discovered_service_info([CORENTIUM_HOME_2_SERVICE_INFO]),
|
||||
patch_airthings_ble(test_device),
|
||||
):
|
||||
await hass.config_entries.async_setup(entry.entry_id)
|
||||
await hass.async_block_till_done()
|
||||
|
||||
state = hass.states.get(
|
||||
"sensor.airthings_corentium_home_2_123456_connectivity_mode"
|
||||
)
|
||||
assert state is not None
|
||||
assert state.state == expected_state
|
||||
|
||||
|
||||
async def test_scan_interval_migration_corentium_home_2(
|
||||
hass: HomeAssistant,
|
||||
freezer: FrozenDateTimeFactory,
|
||||
|
||||
Reference in New Issue
Block a user