From f309064a7fe6414930ef596e8118ce93289443b7 Mon Sep 17 00:00:00 2001 From: Erik Montnemery Date: Fri, 3 May 2024 14:07:38 +0200 Subject: [PATCH] Convert sensor recorder tests to use async API (#116373) * Convert sensor recorder tests to use async API * Fix accidentally renamed test * Avoid unnecessary calls to async_wait_recording_done * Avoid auto-commits for every state change * Make sure recorder patches are set up before hass fixture --- tests/components/sensor/test_recorder.py | 816 ++++++++++++----------- 1 file changed, 438 insertions(+), 378 deletions(-) diff --git a/tests/components/sensor/test_recorder.py b/tests/components/sensor/test_recorder.py index a7aaf938410..ec43d81fc4a 100644 --- a/tests/components/sensor/test_recorder.py +++ b/tests/components/sensor/test_recorder.py @@ -1,9 +1,9 @@ """The tests for sensor recorder platform.""" -from collections.abc import Callable from datetime import datetime, timedelta import math from statistics import mean +from typing import Literal from unittest.mock import patch from freezegun import freeze_time @@ -12,6 +12,7 @@ import pytest from homeassistant import loader from homeassistant.components.recorder import ( + CONF_COMMIT_INTERVAL, DOMAIN as RECORDER_DOMAIN, Recorder, history, @@ -36,7 +37,7 @@ from homeassistant.components.recorder.util import get_instance, session_scope from homeassistant.components.sensor import ATTR_OPTIONS, DOMAIN, SensorDeviceClass from homeassistant.const import ATTR_FRIENDLY_NAME, STATE_UNAVAILABLE from homeassistant.core import HomeAssistant, State -from homeassistant.setup import async_setup_component, setup_component +from homeassistant.setup import async_setup_component import homeassistant.util.dt as dt_util from homeassistant.util.unit_system import METRIC_SYSTEM, US_CUSTOMARY_SYSTEM @@ -48,10 +49,9 @@ from tests.components.recorder.common import ( async_wait_recording_done, do_adhoc_statistics, statistics_during_period, - wait_recording_done, ) from tests.components.sensor.common import MockSensor -from tests.typing import WebSocketGenerator +from tests.typing import RecorderInstanceGenerator, WebSocketGenerator BATTERY_SENSOR_ATTRIBUTES = { "device_class": "battery", @@ -92,14 +92,27 @@ KW_SENSOR_ATTRIBUTES = { } +@pytest.fixture +async def mock_recorder_before_hass( + async_setup_recorder_instance: RecorderInstanceGenerator, +) -> None: + """Set up recorder patches.""" + + @pytest.fixture(autouse=True) -def set_time_zone(): - """Set the time zone for the tests.""" - # Set our timezone to CST/Regina so we can check calculations - # This keeps UTC-6 all year round - dt_util.set_default_time_zone(dt_util.get_time_zone("America/Regina")) - yield - dt_util.set_default_time_zone(dt_util.get_time_zone("UTC")) +def setup_recorder(recorder_mock: Recorder) -> Recorder: + """Set up recorder.""" + + +async def async_list_statistic_ids( + hass: HomeAssistant, + statistic_ids: set[str] | None = None, + statistic_type: Literal["mean", "sum"] | None = None, +) -> list[dict]: + """Return all statistic_ids and unit of measurement.""" + return await hass.async_add_executor_job( + list_statistic_ids, hass, statistic_ids, statistic_type + ) @pytest.mark.parametrize( @@ -136,8 +149,8 @@ def set_time_zone(): ("weight", "oz", "oz", "oz", "mass", 13.050847, -10, 30), ], ) -def test_compile_hourly_statistics( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_statistics( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -150,24 +163,27 @@ def test_compile_hourly_statistics( ) -> None: """Test compiling hourly statistics.""" zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": device_class, "state_class": "measurement", "unit_of_measurement": state_unit, } with freeze_time(zero) as freezer: - four, states = record_states(hass, freezer, zero, "sensor.test1", attributes) + four, states = await async_record_states( + hass, freezer, zero, "sensor.test1", attributes + ) + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, zero, four, hass.states.async_entity_ids() ) assert_dict_of_states_equal_without_context_and_last_changed(states, hist) do_adhoc_statistics(hass, start=zero) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -214,8 +230,8 @@ def test_compile_hourly_statistics( ("temperature", "°F", "°F", "°F", "temperature", 27.796610169491526, -10, 60), ], ) -def test_compile_hourly_statistics_with_some_same_last_updated( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_statistics_with_some_same_last_updated( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -231,9 +247,9 @@ def test_compile_hourly_statistics_with_some_same_last_updated( If the last updated value is the same we will have a zero duration. """ zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) entity_id = "sensor.test1" attributes = { "device_class": device_class, @@ -243,10 +259,10 @@ def test_compile_hourly_statistics_with_some_same_last_updated( attributes = dict(attributes) seq = [-10, 15, 30, 60] - def set_state(entity_id, state, **kwargs): + async def set_state(entity_id, state, **kwargs): """Set the state.""" - hass.states.set(entity_id, state, **kwargs) - wait_recording_done(hass) + hass.states.async_set(entity_id, state, **kwargs) + await async_wait_recording_done(hass) return hass.states.get(entity_id) one = zero + timedelta(seconds=1 * 5) @@ -257,21 +273,21 @@ def test_compile_hourly_statistics_with_some_same_last_updated( states = {entity_id: []} with freeze_time(one) as freezer: states[entity_id].append( - set_state(entity_id, str(seq[0]), attributes=attributes) + await set_state(entity_id, str(seq[0]), attributes=attributes) ) # Record two states at the exact same time freezer.move_to(two) states[entity_id].append( - set_state(entity_id, str(seq[1]), attributes=attributes) + await set_state(entity_id, str(seq[1]), attributes=attributes) ) states[entity_id].append( - set_state(entity_id, str(seq[2]), attributes=attributes) + await set_state(entity_id, str(seq[2]), attributes=attributes) ) freezer.move_to(three) states[entity_id].append( - set_state(entity_id, str(seq[3]), attributes=attributes) + await set_state(entity_id, str(seq[3]), attributes=attributes) ) hist = history.get_significant_states( @@ -280,8 +296,8 @@ def test_compile_hourly_statistics_with_some_same_last_updated( assert_dict_of_states_equal_without_context_and_last_changed(states, hist) do_adhoc_statistics(hass, start=zero) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -328,8 +344,8 @@ def test_compile_hourly_statistics_with_some_same_last_updated( ("temperature", "°F", "°F", "°F", "temperature", 60, -10, 60), ], ) -def test_compile_hourly_statistics_with_all_same_last_updated( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_statistics_with_all_same_last_updated( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -345,9 +361,9 @@ def test_compile_hourly_statistics_with_all_same_last_updated( If the last updated value is the same we will have a zero duration. """ zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) entity_id = "sensor.test1" attributes = { "device_class": device_class, @@ -357,10 +373,10 @@ def test_compile_hourly_statistics_with_all_same_last_updated( attributes = dict(attributes) seq = [-10, 15, 30, 60] - def set_state(entity_id, state, **kwargs): + async def set_state(entity_id, state, **kwargs): """Set the state.""" - hass.states.set(entity_id, state, **kwargs) - wait_recording_done(hass) + hass.states.async_set(entity_id, state, **kwargs) + await async_wait_recording_done(hass) return hass.states.get(entity_id) one = zero + timedelta(seconds=1 * 5) @@ -371,16 +387,16 @@ def test_compile_hourly_statistics_with_all_same_last_updated( states = {entity_id: []} with freeze_time(two): states[entity_id].append( - set_state(entity_id, str(seq[0]), attributes=attributes) + await set_state(entity_id, str(seq[0]), attributes=attributes) ) states[entity_id].append( - set_state(entity_id, str(seq[1]), attributes=attributes) + await set_state(entity_id, str(seq[1]), attributes=attributes) ) states[entity_id].append( - set_state(entity_id, str(seq[2]), attributes=attributes) + await set_state(entity_id, str(seq[2]), attributes=attributes) ) states[entity_id].append( - set_state(entity_id, str(seq[3]), attributes=attributes) + await set_state(entity_id, str(seq[3]), attributes=attributes) ) hist = history.get_significant_states( @@ -389,8 +405,8 @@ def test_compile_hourly_statistics_with_all_same_last_updated( assert_dict_of_states_equal_without_context_and_last_changed(states, hist) do_adhoc_statistics(hass, start=zero) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -437,8 +453,8 @@ def test_compile_hourly_statistics_with_all_same_last_updated( ("temperature", "°F", "°F", "°F", "temperature", 0, 60, 60), ], ) -def test_compile_hourly_statistics_only_state_is_and_end_of_period( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_statistics_only_state_is_and_end_of_period( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -451,9 +467,9 @@ def test_compile_hourly_statistics_only_state_is_and_end_of_period( ) -> None: """Test compiling hourly statistics when the only state at end of period.""" zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) entity_id = "sensor.test1" attributes = { "device_class": device_class, @@ -463,10 +479,10 @@ def test_compile_hourly_statistics_only_state_is_and_end_of_period( attributes = dict(attributes) seq = [-10, 15, 30, 60] - def set_state(entity_id, state, **kwargs): + async def set_state(entity_id, state, **kwargs): """Set the state.""" - hass.states.set(entity_id, state, **kwargs) - wait_recording_done(hass) + hass.states.async_set(entity_id, state, **kwargs) + await async_wait_recording_done(hass) return hass.states.get(entity_id) one = zero + timedelta(seconds=1 * 5) @@ -478,16 +494,16 @@ def test_compile_hourly_statistics_only_state_is_and_end_of_period( states = {entity_id: []} with freeze_time(end): states[entity_id].append( - set_state(entity_id, str(seq[0]), attributes=attributes) + await set_state(entity_id, str(seq[0]), attributes=attributes) ) states[entity_id].append( - set_state(entity_id, str(seq[1]), attributes=attributes) + await set_state(entity_id, str(seq[1]), attributes=attributes) ) states[entity_id].append( - set_state(entity_id, str(seq[2]), attributes=attributes) + await set_state(entity_id, str(seq[2]), attributes=attributes) ) states[entity_id].append( - set_state(entity_id, str(seq[3]), attributes=attributes) + await set_state(entity_id, str(seq[3]), attributes=attributes) ) hist = history.get_significant_states( @@ -496,8 +512,8 @@ def test_compile_hourly_statistics_only_state_is_and_end_of_period( assert_dict_of_states_equal_without_context_and_last_changed(states, hist) do_adhoc_statistics(hass, start=zero) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -534,8 +550,8 @@ def test_compile_hourly_statistics_only_state_is_and_end_of_period( (None, "%", "%", "%", "unitless"), ], ) -def test_compile_hourly_statistics_purged_state_changes( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_statistics_purged_state_changes( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -545,16 +561,19 @@ def test_compile_hourly_statistics_purged_state_changes( ) -> None: """Test compiling hourly statistics.""" zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": device_class, "state_class": "measurement", "unit_of_measurement": state_unit, } with freeze_time(zero) as freezer: - four, states = record_states(hass, freezer, zero, "sensor.test1", attributes) + four, states = await async_record_states( + hass, freezer, zero, "sensor.test1", attributes + ) + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, zero, four, hass.states.async_entity_ids() ) @@ -564,17 +583,17 @@ def test_compile_hourly_statistics_purged_state_changes( # Purge all states from the database with freeze_time(four): - hass.services.call("recorder", "purge", {"keep_days": 0}) - hass.block_till_done() - wait_recording_done(hass) + await hass.services.async_call("recorder", "purge", {"keep_days": 0}) + await hass.async_block_till_done() + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, zero, four, hass.states.async_entity_ids() ) assert not hist do_adhoc_statistics(hass, start=zero) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -606,42 +625,57 @@ def test_compile_hourly_statistics_purged_state_changes( @pytest.mark.parametrize("attributes", [TEMPERATURE_SENSOR_ATTRIBUTES]) -def test_compile_hourly_statistics_wrong_unit( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_statistics_wrong_unit( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, attributes, ) -> None: """Test compiling hourly statistics for sensor with unit not matching device class.""" zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) with freeze_time(zero) as freezer: - four, states = record_states(hass, freezer, zero, "sensor.test1", attributes) + four, states = await async_record_states( + hass, freezer, zero, "sensor.test1", attributes + ) attributes_tmp = dict(attributes) attributes_tmp["unit_of_measurement"] = "invalid" - _, _states = record_states(hass, freezer, zero, "sensor.test2", attributes_tmp) + _, _states = await async_record_states( + hass, freezer, zero, "sensor.test2", attributes_tmp + ) states = {**states, **_states} attributes_tmp.pop("unit_of_measurement") - _, _states = record_states(hass, freezer, zero, "sensor.test3", attributes_tmp) + _, _states = await async_record_states( + hass, freezer, zero, "sensor.test3", attributes_tmp + ) states = {**states, **_states} attributes_tmp = dict(attributes) attributes_tmp["state_class"] = "invalid" - _, _states = record_states(hass, freezer, zero, "sensor.test4", attributes_tmp) + _, _states = await async_record_states( + hass, freezer, zero, "sensor.test4", attributes_tmp + ) states = {**states, **_states} attributes_tmp.pop("state_class") - _, _states = record_states(hass, freezer, zero, "sensor.test5", attributes_tmp) + _, _states = await async_record_states( + hass, freezer, zero, "sensor.test5", attributes_tmp + ) states = {**states, **_states} attributes_tmp = dict(attributes) attributes_tmp["device_class"] = "invalid" - _, _states = record_states(hass, freezer, zero, "sensor.test6", attributes_tmp) + _, _states = await async_record_states( + hass, freezer, zero, "sensor.test6", attributes_tmp + ) states = {**states, **_states} attributes_tmp.pop("device_class") - _, _states = record_states(hass, freezer, zero, "sensor.test7", attributes_tmp) + _, _states = await async_record_states( + hass, freezer, zero, "sensor.test7", attributes_tmp + ) states = {**states, **_states} + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, zero, four, hass.states.async_entity_ids() @@ -649,8 +683,8 @@ def test_compile_hourly_statistics_wrong_unit( assert_dict_of_states_equal_without_context_and_last_changed(states, hist) do_adhoc_statistics(hass, start=zero) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -808,7 +842,6 @@ def test_compile_hourly_statistics_wrong_unit( ], ) async def test_compile_hourly_sum_statistics_amount( - recorder_mock: Recorder, hass: HomeAssistant, hass_ws_client: WebSocketGenerator, caplog: pytest.LogCaptureFixture, @@ -838,8 +871,8 @@ async def test_compile_hourly_sum_statistics_amount( } seq = [10, 15, 20, 10, 30, 40, 50, 60, 70] with freeze_time(period0) as freezer: - four, eight, states = await hass.async_add_executor_job( - record_meter_states, hass, freezer, period0, "sensor.test1", attributes, seq + four, eight, states = await async_record_meter_states( + hass, freezer, period0, "sensor.test1", attributes, seq ) await async_wait_recording_done(hass) hist = history.get_significant_states( @@ -858,7 +891,7 @@ async def test_compile_hourly_sum_statistics_amount( await async_wait_recording_done(hass) do_adhoc_statistics(hass, start=period2) await async_wait_recording_done(hass) - statistic_ids = await hass.async_add_executor_job(list_statistic_ids, hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -994,8 +1027,8 @@ async def test_compile_hourly_sum_statistics_amount( ("weight", "kg", "kg", "kg", "mass", 1), ], ) -def test_compile_hourly_sum_statistics_amount_reset_every_state_change( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_sum_statistics_amount_reset_every_state_change( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, state_class, device_class, @@ -1007,9 +1040,9 @@ def test_compile_hourly_sum_statistics_amount_reset_every_state_change( ) -> None: """Test compiling hourly statistics.""" zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": device_class, "state_class": state_class, @@ -1031,7 +1064,7 @@ def test_compile_hourly_sum_statistics_amount_reset_every_state_change( one = one + timedelta(seconds=5) attributes = dict(attributes) attributes["last_reset"] = dt_util.as_local(one).isoformat() - _states = record_meter_state( + _states = await async_record_meter_state( hass, freezer, one, "sensor.test1", attributes, seq[i : i + 1] ) states["sensor.test1"].extend(_states["sensor.test1"]) @@ -1042,10 +1075,11 @@ def test_compile_hourly_sum_statistics_amount_reset_every_state_change( two = two + timedelta(seconds=5) attributes = dict(attributes) attributes["last_reset"] = dt_util.as_local(two).isoformat() - _states = record_meter_state( + _states = await async_record_meter_state( hass, freezer, two, "sensor.test1", attributes, seq[i : i + 1] ) states["sensor.test1"].extend(_states["sensor.test1"]) + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, @@ -1060,8 +1094,8 @@ def test_compile_hourly_sum_statistics_amount_reset_every_state_change( do_adhoc_statistics(hass, start=zero) do_adhoc_statistics(hass, start=zero + timedelta(minutes=5)) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -1116,8 +1150,8 @@ def test_compile_hourly_sum_statistics_amount_reset_every_state_change( ("energy", "kWh", "kWh", "kWh", "energy", 1), ], ) -def test_compile_hourly_sum_statistics_amount_invalid_last_reset( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_sum_statistics_amount_invalid_last_reset( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, state_class, device_class, @@ -1129,9 +1163,9 @@ def test_compile_hourly_sum_statistics_amount_invalid_last_reset( ) -> None: """Test compiling hourly statistics.""" zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": device_class, "state_class": state_class, @@ -1151,10 +1185,11 @@ def test_compile_hourly_sum_statistics_amount_invalid_last_reset( attributes["last_reset"] = dt_util.as_local(one).isoformat() if i == 3: attributes["last_reset"] = "festivus" # not a valid time - _states = record_meter_state( + _states = await async_record_meter_state( hass, freezer, one, "sensor.test1", attributes, seq[i : i + 1] ) states["sensor.test1"].extend(_states["sensor.test1"]) + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, @@ -1168,8 +1203,8 @@ def test_compile_hourly_sum_statistics_amount_invalid_last_reset( ) do_adhoc_statistics(hass, start=zero) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -1215,8 +1250,8 @@ def test_compile_hourly_sum_statistics_amount_invalid_last_reset( ("energy", "kWh", "kWh", "kWh", "energy", 1), ], ) -def test_compile_hourly_sum_statistics_nan_inf_state( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_sum_statistics_nan_inf_state( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, state_class, device_class, @@ -1228,9 +1263,9 @@ def test_compile_hourly_sum_statistics_nan_inf_state( ) -> None: """Test compiling hourly statistics with nan and inf states.""" zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": device_class, "state_class": state_class, @@ -1246,10 +1281,11 @@ def test_compile_hourly_sum_statistics_nan_inf_state( one = one + timedelta(seconds=5) attributes = dict(attributes) attributes["last_reset"] = dt_util.as_local(one).isoformat() - _states = record_meter_state( + _states = await async_record_meter_state( hass, freezer, one, "sensor.test1", attributes, seq[i : i + 1] ) states["sensor.test1"].extend(_states["sensor.test1"]) + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, @@ -1263,8 +1299,8 @@ def test_compile_hourly_sum_statistics_nan_inf_state( ) do_adhoc_statistics(hass, start=zero) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -1346,8 +1382,8 @@ def test_compile_hourly_sum_statistics_nan_inf_state( ], ) @pytest.mark.parametrize("state_class", ["total_increasing"]) -def test_compile_hourly_sum_statistics_negative_state( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_sum_statistics_negative_state( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, entity_id, warning_1, @@ -1362,18 +1398,17 @@ def test_compile_hourly_sum_statistics_negative_state( ) -> None: """Test compiling hourly statistics with negative states.""" zero = dt_util.utcnow() - hass = hass_recorder() hass.data.pop(loader.DATA_CUSTOM_COMPONENTS) mocksensor = MockSensor(name="custom_sensor") mocksensor._attr_should_poll = False setup_test_component_platform(hass, DOMAIN, [mocksensor], built_in=False) - setup_component(hass, "homeassistant", {}) - setup_component( + await async_setup_component(hass, "homeassistant", {}) + await async_setup_component( hass, "sensor", {"sensor": [{"platform": "demo"}, {"platform": "test"}]} ) - hass.block_till_done() + await hass.async_block_till_done() attributes = { "device_class": device_class, "state_class": state_class, @@ -1390,10 +1425,11 @@ def test_compile_hourly_sum_statistics_negative_state( with freeze_time(zero) as freezer: for i in range(len(seq)): one = one + timedelta(seconds=5) - _states = record_meter_state( + _states = await async_record_meter_state( hass, freezer, one, entity_id, attributes, seq[i : i + 1] ) states[entity_id].extend(_states[entity_id]) + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, @@ -1407,8 +1443,8 @@ def test_compile_hourly_sum_statistics_negative_state( ) do_adhoc_statistics(hass, start=zero) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert { "display_unit_of_measurement": display_unit, "has_mean": False, @@ -1462,8 +1498,8 @@ def test_compile_hourly_sum_statistics_negative_state( ("weight", "kg", "kg", "kg", "mass", 1), ], ) -def test_compile_hourly_sum_statistics_total_no_reset( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_sum_statistics_total_no_reset( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -1477,9 +1513,9 @@ def test_compile_hourly_sum_statistics_total_no_reset( period0_end = period1 = period0 + timedelta(minutes=5) period1_end = period2 = period0 + timedelta(minutes=10) period2_end = period0 + timedelta(minutes=15) - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": device_class, "state_class": "total", @@ -1487,10 +1523,10 @@ def test_compile_hourly_sum_statistics_total_no_reset( } seq = [10, 15, 20, 10, 30, 40, 50, 60, 70] with freeze_time(period0) as freezer: - four, eight, states = record_meter_states( + four, eight, states = await async_record_meter_states( hass, freezer, period0, "sensor.test1", attributes, seq ) - wait_recording_done(hass) + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, period0 - timedelta.resolution, @@ -1502,12 +1538,12 @@ def test_compile_hourly_sum_statistics_total_no_reset( ) do_adhoc_statistics(hass, start=period0) - wait_recording_done(hass) + await async_wait_recording_done(hass) do_adhoc_statistics(hass, start=period1) - wait_recording_done(hass) + await async_wait_recording_done(hass) do_adhoc_statistics(hass, start=period2) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -1575,8 +1611,8 @@ def test_compile_hourly_sum_statistics_total_no_reset( ("weight", "kg", "kg", "kg", "mass", 1), ], ) -def test_compile_hourly_sum_statistics_total_increasing( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_sum_statistics_total_increasing( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -1590,9 +1626,9 @@ def test_compile_hourly_sum_statistics_total_increasing( period0_end = period1 = period0 + timedelta(minutes=5) period1_end = period2 = period0 + timedelta(minutes=10) period2_end = period0 + timedelta(minutes=15) - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": device_class, "state_class": "total_increasing", @@ -1600,10 +1636,10 @@ def test_compile_hourly_sum_statistics_total_increasing( } seq = [10, 15, 20, 10, 30, 40, 50, 60, 70] with freeze_time(period0) as freezer: - four, eight, states = record_meter_states( + four, eight, states = await async_record_meter_states( hass, freezer, period0, "sensor.test1", attributes, seq ) - wait_recording_done(hass) + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, period0 - timedelta.resolution, @@ -1615,12 +1651,12 @@ def test_compile_hourly_sum_statistics_total_increasing( ) do_adhoc_statistics(hass, start=period0) - wait_recording_done(hass) + await async_wait_recording_done(hass) do_adhoc_statistics(hass, start=period1) - wait_recording_done(hass) + await async_wait_recording_done(hass) do_adhoc_statistics(hass, start=period2) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -1688,8 +1724,8 @@ def test_compile_hourly_sum_statistics_total_increasing( ("weight", "kg", "kg", "kg", "mass", 1), ], ) -def test_compile_hourly_sum_statistics_total_increasing_small_dip( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_sum_statistics_total_increasing_small_dip( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -1703,9 +1739,9 @@ def test_compile_hourly_sum_statistics_total_increasing_small_dip( period0_end = period1 = period0 + timedelta(minutes=5) period1_end = period2 = period0 + timedelta(minutes=10) period2_end = period0 + timedelta(minutes=15) - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": device_class, "state_class": "total_increasing", @@ -1713,10 +1749,10 @@ def test_compile_hourly_sum_statistics_total_increasing_small_dip( } seq = [10, 15, 20, 19, 30, 40, 39, 60, 70] with freeze_time(period0) as freezer: - four, eight, states = record_meter_states( + four, eight, states = await async_record_meter_states( hass, freezer, period0, "sensor.test1", attributes, seq ) - wait_recording_done(hass) + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, period0 - timedelta.resolution, @@ -1728,15 +1764,15 @@ def test_compile_hourly_sum_statistics_total_increasing_small_dip( ) do_adhoc_statistics(hass, start=period0) - wait_recording_done(hass) + await async_wait_recording_done(hass) do_adhoc_statistics(hass, start=period1) - wait_recording_done(hass) + await async_wait_recording_done(hass) assert ( "Entity sensor.test1 has state class total_increasing, but its state is not " "strictly increasing." ) not in caplog.text do_adhoc_statistics(hass, start=period2) - wait_recording_done(hass) + await async_wait_recording_done(hass) state = states["sensor.test1"][6].state previous_state = float(states["sensor.test1"][5].state) last_updated = states["sensor.test1"][6].last_updated.isoformat() @@ -1746,7 +1782,7 @@ def test_compile_hourly_sum_statistics_total_increasing_small_dip( f"last_updated set to {last_updated}. Please create a bug report at " "https://github.com/home-assistant/core/issues?q=is%3Aopen+is%3Aissue" ) in caplog.text - statistic_ids = list_statistic_ids(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -1797,17 +1833,17 @@ def test_compile_hourly_sum_statistics_total_increasing_small_dip( assert "Error while processing event StatisticsTask" not in caplog.text -def test_compile_hourly_energy_statistics_unsupported( - hass_recorder: Callable[..., HomeAssistant], caplog: pytest.LogCaptureFixture +async def test_compile_hourly_energy_statistics_unsupported( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture ) -> None: """Test compiling hourly statistics.""" period0 = dt_util.utcnow() period0_end = period1 = period0 + timedelta(minutes=5) period1_end = period2 = period0 + timedelta(minutes=10) period2_end = period0 + timedelta(minutes=15) - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) sns1_attr = { "device_class": "energy", "state_class": "total", @@ -1821,18 +1857,18 @@ def test_compile_hourly_energy_statistics_unsupported( seq3 = [0, 0, 5, 10, 30, 50, 60, 80, 90] with freeze_time(period0) as freezer: - four, eight, states = record_meter_states( + four, eight, states = await async_record_meter_states( hass, freezer, period0, "sensor.test1", sns1_attr, seq1 ) - _, _, _states = record_meter_states( + _, _, _states = await async_record_meter_states( hass, freezer, period0, "sensor.test2", sns2_attr, seq2 ) states = {**states, **_states} - _, _, _states = record_meter_states( + _, _, _states = await async_record_meter_states( hass, freezer, period0, "sensor.test3", sns3_attr, seq3 ) states = {**states, **_states} - wait_recording_done(hass) + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, @@ -1845,12 +1881,12 @@ def test_compile_hourly_energy_statistics_unsupported( ) do_adhoc_statistics(hass, start=period0) - wait_recording_done(hass) + await async_wait_recording_done(hass) do_adhoc_statistics(hass, start=period1) - wait_recording_done(hass) + await async_wait_recording_done(hass) do_adhoc_statistics(hass, start=period2) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -1901,17 +1937,17 @@ def test_compile_hourly_energy_statistics_unsupported( assert "Error while processing event StatisticsTask" not in caplog.text -def test_compile_hourly_energy_statistics_multiple( - hass_recorder: Callable[..., HomeAssistant], caplog: pytest.LogCaptureFixture +async def test_compile_hourly_energy_statistics_multiple( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture ) -> None: """Test compiling multiple hourly statistics.""" period0 = dt_util.utcnow() period0_end = period1 = period0 + timedelta(minutes=5) period1_end = period2 = period0 + timedelta(minutes=10) period2_end = period0 + timedelta(minutes=15) - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) sns1_attr = {**ENERGY_SENSOR_ATTRIBUTES, "last_reset": None} sns2_attr = {**ENERGY_SENSOR_ATTRIBUTES, "last_reset": None} sns3_attr = { @@ -1924,18 +1960,18 @@ def test_compile_hourly_energy_statistics_multiple( seq3 = [0, 0, 5, 10, 30, 50, 60, 80, 90] with freeze_time(period0) as freezer: - four, eight, states = record_meter_states( + four, eight, states = await async_record_meter_states( hass, freezer, period0, "sensor.test1", sns1_attr, seq1 ) - _, _, _states = record_meter_states( + _, _, _states = await async_record_meter_states( hass, freezer, period0, "sensor.test2", sns2_attr, seq2 ) states = {**states, **_states} - _, _, _states = record_meter_states( + _, _, _states = await async_record_meter_states( hass, freezer, period0, "sensor.test3", sns3_attr, seq3 ) states = {**states, **_states} - wait_recording_done(hass) + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, period0 - timedelta.resolution, @@ -1947,12 +1983,12 @@ def test_compile_hourly_energy_statistics_multiple( ) do_adhoc_statistics(hass, start=period0) - wait_recording_done(hass) + await async_wait_recording_done(hass) do_adhoc_statistics(hass, start=period1) - wait_recording_done(hass) + await async_wait_recording_done(hass) do_adhoc_statistics(hass, start=period2) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -2111,8 +2147,8 @@ def test_compile_hourly_energy_statistics_multiple( ("weight", "oz", 30), ], ) -def test_compile_hourly_statistics_unchanged( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_statistics_unchanged( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -2120,23 +2156,26 @@ def test_compile_hourly_statistics_unchanged( ) -> None: """Test compiling hourly statistics, with no changes during the hour.""" zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": device_class, "state_class": "measurement", "unit_of_measurement": state_unit, } with freeze_time(zero) as freezer: - four, states = record_states(hass, freezer, zero, "sensor.test1", attributes) + four, states = await async_record_states( + hass, freezer, zero, "sensor.test1", attributes + ) + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, zero, four, hass.states.async_entity_ids() ) assert_dict_of_states_equal_without_context_and_last_changed(states, hist) do_adhoc_statistics(hass, start=four) - wait_recording_done(hass) + await async_wait_recording_done(hass) stats = statistics_during_period(hass, four, period="5minute") assert stats == { "sensor.test1": [ @@ -2155,24 +2194,25 @@ def test_compile_hourly_statistics_unchanged( assert "Error while processing event StatisticsTask" not in caplog.text -def test_compile_hourly_statistics_partially_unavailable( - hass_recorder: Callable[..., HomeAssistant], caplog: pytest.LogCaptureFixture +async def test_compile_hourly_statistics_partially_unavailable( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture ) -> None: """Test compiling hourly statistics, with the sensor being partially unavailable.""" zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added - four, states = record_states_partially_unavailable( + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) + four, states = await async_record_states_partially_unavailable( hass, zero, "sensor.test1", TEMPERATURE_SENSOR_ATTRIBUTES ) + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, zero, four, hass.states.async_entity_ids() ) assert_dict_of_states_equal_without_context_and_last_changed(states, hist) do_adhoc_statistics(hass, start=zero) - wait_recording_done(hass) + await async_wait_recording_done(hass) stats = statistics_during_period(hass, zero, period="5minute") assert stats == { "sensor.test1": [ @@ -2215,8 +2255,8 @@ def test_compile_hourly_statistics_partially_unavailable( ("weight", "oz", 30), ], ) -def test_compile_hourly_statistics_unavailable( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_statistics_unavailable( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -2228,19 +2268,22 @@ def test_compile_hourly_statistics_unavailable( sensor.test2 should have statistics generated """ zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": device_class, "state_class": "measurement", "unit_of_measurement": state_unit, } - four, states = record_states_partially_unavailable( + four, states = await async_record_states_partially_unavailable( hass, zero, "sensor.test1", attributes ) with freeze_time(zero) as freezer: - _, _states = record_states(hass, freezer, zero, "sensor.test2", attributes) + _, _states = await async_record_states( + hass, freezer, zero, "sensor.test2", attributes + ) + await async_wait_recording_done(hass) states = {**states, **_states} hist = history.get_significant_states( hass, zero, four, hass.states.async_entity_ids() @@ -2248,7 +2291,7 @@ def test_compile_hourly_statistics_unavailable( assert_dict_of_states_equal_without_context_and_last_changed(states, hist) do_adhoc_statistics(hass, start=four) - wait_recording_done(hass) + await async_wait_recording_done(hass) stats = statistics_during_period(hass, four, period="5minute") assert stats == { "sensor.test2": [ @@ -2267,20 +2310,20 @@ def test_compile_hourly_statistics_unavailable( assert "Error while processing event StatisticsTask" not in caplog.text -def test_compile_hourly_statistics_fails( - hass_recorder: Callable[..., HomeAssistant], caplog: pytest.LogCaptureFixture +async def test_compile_hourly_statistics_fails( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture ) -> None: """Test compiling hourly statistics throws.""" zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) with patch( "homeassistant.components.sensor.recorder.compile_statistics", side_effect=Exception, ): do_adhoc_statistics(hass, start=zero) - wait_recording_done(hass) + await async_wait_recording_done(hass) assert "Error while processing event StatisticsTask" in caplog.text @@ -2334,8 +2377,8 @@ def test_compile_hourly_statistics_fails( ("total", "weight", "oz", "oz", "oz", "mass", "sum"), ], ) -def test_list_statistic_ids( - hass_recorder: Callable[..., HomeAssistant], +async def test_list_statistic_ids( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, state_class, device_class, @@ -2346,17 +2389,17 @@ def test_list_statistic_ids( statistic_type, ) -> None: """Test listing future statistic ids.""" - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": device_class, "last_reset": 0, "state_class": state_class, "unit_of_measurement": state_unit, } - hass.states.set("sensor.test1", 0, attributes=attributes) - statistic_ids = list_statistic_ids(hass) + hass.states.async_set("sensor.test1", 0, attributes=attributes) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -2370,7 +2413,7 @@ def test_list_statistic_ids( }, ] for stat_type in ["mean", "sum", "dogs"]: - statistic_ids = list_statistic_ids(hass, statistic_type=stat_type) + statistic_ids = await async_list_statistic_ids(hass, statistic_type=stat_type) if statistic_type == stat_type: assert statistic_ids == [ { @@ -2392,31 +2435,31 @@ def test_list_statistic_ids( "_attributes", [{**ENERGY_SENSOR_ATTRIBUTES, "last_reset": 0}, TEMPERATURE_SENSOR_ATTRIBUTES], ) -def test_list_statistic_ids_unsupported( - hass_recorder: Callable[..., HomeAssistant], +async def test_list_statistic_ids_unsupported( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, _attributes, ) -> None: """Test listing future statistic ids for unsupported sensor.""" - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = dict(_attributes) - hass.states.set("sensor.test1", 0, attributes=attributes) + hass.states.async_set("sensor.test1", 0, attributes=attributes) if "last_reset" in attributes: attributes.pop("unit_of_measurement") - hass.states.set("last_reset.test2", 0, attributes=attributes) + hass.states.async_set("last_reset.test2", 0, attributes=attributes) attributes = dict(_attributes) if "unit_of_measurement" in attributes: attributes["unit_of_measurement"] = "invalid" - hass.states.set("sensor.test3", 0, attributes=attributes) + hass.states.async_set("sensor.test3", 0, attributes=attributes) attributes.pop("unit_of_measurement") - hass.states.set("sensor.test4", 0, attributes=attributes) + hass.states.async_set("sensor.test4", 0, attributes=attributes) attributes = dict(_attributes) attributes["state_class"] = "invalid" - hass.states.set("sensor.test5", 0, attributes=attributes) + hass.states.async_set("sensor.test5", 0, attributes=attributes) attributes.pop("state_class") - hass.states.set("sensor.test6", 0, attributes=attributes) + hass.states.async_set("sensor.test6", 0, attributes=attributes) @pytest.mark.parametrize( @@ -2433,8 +2476,8 @@ def test_list_statistic_ids_unsupported( (None, "m³", "m3", "volume", 13.050847, -10, 30), ], ) -def test_compile_hourly_statistics_changing_units_1( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_statistics_changing_units_1( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -2449,34 +2492,37 @@ def test_compile_hourly_statistics_changing_units_1( This tests the case where the recorder cannot convert between the units. """ zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": device_class, "state_class": "measurement", "unit_of_measurement": state_unit, } with freeze_time(zero) as freezer: - four, states = record_states(hass, freezer, zero, "sensor.test1", attributes) + four, states = await async_record_states( + hass, freezer, zero, "sensor.test1", attributes + ) attributes["unit_of_measurement"] = state_unit2 - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, zero + timedelta(minutes=5), "sensor.test1", attributes ) states["sensor.test1"] += _states["sensor.test1"] - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, zero + timedelta(minutes=10), "sensor.test1", attributes ) states["sensor.test1"] += _states["sensor.test1"] + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, zero, four, hass.states.async_entity_ids() ) assert_dict_of_states_equal_without_context_and_last_changed(states, hist) do_adhoc_statistics(hass, start=zero) - wait_recording_done(hass) + await async_wait_recording_done(hass) assert "cannot be converted to the unit of previously" not in caplog.text - statistic_ids = list_statistic_ids(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -2506,12 +2552,12 @@ def test_compile_hourly_statistics_changing_units_1( } do_adhoc_statistics(hass, start=zero + timedelta(minutes=10)) - wait_recording_done(hass) + await async_wait_recording_done(hass) assert ( f"The unit of sensor.test1 ({state_unit2}) cannot be converted to the unit of " f"previously compiled statistics ({state_unit})" in caplog.text ) - statistic_ids = list_statistic_ids(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -2557,8 +2603,8 @@ def test_compile_hourly_statistics_changing_units_1( (None, "dogs", "dogs", "dogs", None, 13.050847, -10, 30), ], ) -def test_compile_hourly_statistics_changing_units_2( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_statistics_changing_units_2( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -2575,31 +2621,34 @@ def test_compile_hourly_statistics_changing_units_2( converter. """ zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": device_class, "state_class": "measurement", "unit_of_measurement": state_unit, } with freeze_time(zero) as freezer: - four, states = record_states(hass, freezer, zero, "sensor.test1", attributes) + four, states = await async_record_states( + hass, freezer, zero, "sensor.test1", attributes + ) attributes["unit_of_measurement"] = "cats" - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, zero + timedelta(minutes=5), "sensor.test1", attributes ) states["sensor.test1"] += _states["sensor.test1"] + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, zero, four, hass.states.async_entity_ids() ) assert_dict_of_states_equal_without_context_and_last_changed(states, hist) do_adhoc_statistics(hass, start=zero + timedelta(seconds=30 * 5)) - wait_recording_done(hass) + await async_wait_recording_done(hass) assert "The unit of sensor.test1 is changing" in caplog.text assert "and matches the unit of already compiled statistics" not in caplog.text - statistic_ids = list_statistic_ids(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -2633,8 +2682,8 @@ def test_compile_hourly_statistics_changing_units_2( (None, "dogs", "dogs", "dogs", None, 13.050847, -10, 30), ], ) -def test_compile_hourly_statistics_changing_units_3( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_statistics_changing_units_3( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -2651,34 +2700,37 @@ def test_compile_hourly_statistics_changing_units_3( converter. """ zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": device_class, "state_class": "measurement", "unit_of_measurement": state_unit, } with freeze_time(zero) as freezer: - four, states = record_states(hass, freezer, zero, "sensor.test1", attributes) - four, _states = record_states( + four, states = await async_record_states( + hass, freezer, zero, "sensor.test1", attributes + ) + four, _states = await async_record_states( hass, freezer, zero + timedelta(minutes=5), "sensor.test1", attributes ) states["sensor.test1"] += _states["sensor.test1"] attributes["unit_of_measurement"] = "cats" - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, zero + timedelta(minutes=10), "sensor.test1", attributes ) states["sensor.test1"] += _states["sensor.test1"] + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, zero, four, hass.states.async_entity_ids() ) assert_dict_of_states_equal_without_context_and_last_changed(states, hist) do_adhoc_statistics(hass, start=zero) - wait_recording_done(hass) + await async_wait_recording_done(hass) assert "does not match the unit of already compiled" not in caplog.text - statistic_ids = list_statistic_ids(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -2708,12 +2760,12 @@ def test_compile_hourly_statistics_changing_units_3( } do_adhoc_statistics(hass, start=zero + timedelta(minutes=10)) - wait_recording_done(hass) + await async_wait_recording_done(hass) assert "The unit of sensor.test1 is changing" in caplog.text assert ( f"matches the unit of already compiled statistics ({state_unit})" in caplog.text ) - statistic_ids = list_statistic_ids(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -2753,8 +2805,8 @@ def test_compile_hourly_statistics_changing_units_3( ("kW", "W", "power", 13.050847, -10, 30, 1000), ], ) -def test_compile_hourly_statistics_convert_units_1( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_statistics_convert_units_1( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, state_unit_1, state_unit_2, @@ -2769,17 +2821,19 @@ def test_compile_hourly_statistics_convert_units_1( This tests the case where the recorder can convert between the units. """ zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": None, "state_class": "measurement", "unit_of_measurement": state_unit_1, } with freeze_time(zero) as freezer: - four, states = record_states(hass, freezer, zero, "sensor.test1", attributes) - four, _states = record_states( + four, states = await async_record_states( + hass, freezer, zero, "sensor.test1", attributes + ) + four, _states = await async_record_states( hass, freezer, zero + timedelta(minutes=5), @@ -2787,12 +2841,13 @@ def test_compile_hourly_statistics_convert_units_1( attributes, seq=[0, 1, None], ) + await async_wait_recording_done(hass) states["sensor.test1"] += _states["sensor.test1"] do_adhoc_statistics(hass, start=zero) - wait_recording_done(hass) + await async_wait_recording_done(hass) assert "does not match the unit of already compiled" not in caplog.text - statistic_ids = list_statistic_ids(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -2823,22 +2878,23 @@ def test_compile_hourly_statistics_convert_units_1( attributes["unit_of_measurement"] = state_unit_2 with freeze_time(four) as freezer: - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, zero + timedelta(minutes=10), "sensor.test1", attributes ) + await async_wait_recording_done(hass) states["sensor.test1"] += _states["sensor.test1"] hist = history.get_significant_states( hass, zero, four, hass.states.async_entity_ids() ) assert_dict_of_states_equal_without_context_and_last_changed(states, hist) do_adhoc_statistics(hass, start=zero + timedelta(minutes=10)) - wait_recording_done(hass) + await async_wait_recording_done(hass) assert "The unit of sensor.test1 is changing" not in caplog.text assert ( f"matches the unit of already compiled statistics ({state_unit_1})" not in caplog.text ) - statistic_ids = list_statistic_ids(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -2909,8 +2965,8 @@ def test_compile_hourly_statistics_convert_units_1( (None, "m3", "m³", None, "volume", 13.050847, 13.333333, -10, 30), ], ) -def test_compile_hourly_statistics_equivalent_units_1( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_statistics_equivalent_units_1( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -2924,24 +2980,27 @@ def test_compile_hourly_statistics_equivalent_units_1( ) -> None: """Test compiling hourly statistics where units change from one hour to the next.""" zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": device_class, "state_class": "measurement", "unit_of_measurement": state_unit, } with freeze_time(zero) as freezer: - four, states = record_states(hass, freezer, zero, "sensor.test1", attributes) + four, states = await async_record_states( + hass, freezer, zero, "sensor.test1", attributes + ) attributes["unit_of_measurement"] = state_unit2 - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, zero + timedelta(minutes=5), "sensor.test1", attributes ) states["sensor.test1"] += _states["sensor.test1"] - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, zero + timedelta(minutes=10), "sensor.test1", attributes ) + await async_wait_recording_done(hass) states["sensor.test1"] += _states["sensor.test1"] hist = history.get_significant_states( hass, zero, four, hass.states.async_entity_ids() @@ -2949,9 +3008,9 @@ def test_compile_hourly_statistics_equivalent_units_1( assert_dict_of_states_equal_without_context_and_last_changed(states, hist) do_adhoc_statistics(hass, start=zero) - wait_recording_done(hass) + await async_wait_recording_done(hass) assert "cannot be converted to the unit of previously" not in caplog.text - statistic_ids = list_statistic_ids(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -2981,8 +3040,8 @@ def test_compile_hourly_statistics_equivalent_units_1( } do_adhoc_statistics(hass, start=zero + timedelta(minutes=10)) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -3033,8 +3092,8 @@ def test_compile_hourly_statistics_equivalent_units_1( (None, "m3", "m³", None, 13.333333, -10, 30), ], ) -def test_compile_hourly_statistics_equivalent_units_2( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_statistics_equivalent_units_2( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -3046,20 +3105,23 @@ def test_compile_hourly_statistics_equivalent_units_2( ) -> None: """Test compiling hourly statistics where units change during an hour.""" zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": device_class, "state_class": "measurement", "unit_of_measurement": state_unit, } with freeze_time(zero) as freezer: - four, states = record_states(hass, freezer, zero, "sensor.test1", attributes) + four, states = await async_record_states( + hass, freezer, zero, "sensor.test1", attributes + ) attributes["unit_of_measurement"] = state_unit2 - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, zero + timedelta(minutes=5), "sensor.test1", attributes ) + await async_wait_recording_done(hass) states["sensor.test1"] += _states["sensor.test1"] hist = history.get_significant_states( hass, zero, four, hass.states.async_entity_ids() @@ -3067,10 +3129,10 @@ def test_compile_hourly_statistics_equivalent_units_2( assert_dict_of_states_equal_without_context_and_last_changed(states, hist) do_adhoc_statistics(hass, start=zero + timedelta(seconds=30 * 5)) - wait_recording_done(hass) + await async_wait_recording_done(hass) assert "The unit of sensor.test1 is changing" not in caplog.text assert "and matches the unit of already compiled statistics" not in caplog.text - statistic_ids = list_statistic_ids(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -3119,8 +3181,8 @@ def test_compile_hourly_statistics_equivalent_units_2( ("power", "kW", "kW", "power", 13.050847, 13.333333, -10, 30), ], ) -def test_compile_hourly_statistics_changing_device_class_1( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_statistics_changing_device_class_1( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -3136,9 +3198,9 @@ def test_compile_hourly_statistics_changing_device_class_1( Device class is ignored, meaning changing device class should not influence the statistics. """ zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) # Record some states for an initial period, the entity has no device class attributes = { @@ -3146,12 +3208,15 @@ def test_compile_hourly_statistics_changing_device_class_1( "unit_of_measurement": state_unit, } with freeze_time(zero) as freezer: - four, states = record_states(hass, freezer, zero, "sensor.test1", attributes) + four, states = await async_record_states( + hass, freezer, zero, "sensor.test1", attributes + ) + await async_wait_recording_done(hass) do_adhoc_statistics(hass, start=zero) - wait_recording_done(hass) + await async_wait_recording_done(hass) assert "does not match the unit of already compiled" not in caplog.text - statistic_ids = list_statistic_ids(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -3183,13 +3248,14 @@ def test_compile_hourly_statistics_changing_device_class_1( # Update device class and record additional states in the original UoM attributes["device_class"] = device_class with freeze_time(zero) as freezer: - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, zero + timedelta(minutes=5), "sensor.test1", attributes ) states["sensor.test1"] += _states["sensor.test1"] - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, zero + timedelta(minutes=10), "sensor.test1", attributes ) + await async_wait_recording_done(hass) states["sensor.test1"] += _states["sensor.test1"] hist = history.get_significant_states( hass, zero, four, hass.states.async_entity_ids() @@ -3198,8 +3264,8 @@ def test_compile_hourly_statistics_changing_device_class_1( # Run statistics again, additional statistics is generated do_adhoc_statistics(hass, start=zero + timedelta(minutes=10)) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -3241,13 +3307,14 @@ def test_compile_hourly_statistics_changing_device_class_1( # Update device class and record additional states in a different UoM attributes["unit_of_measurement"] = statistic_unit with freeze_time(zero) as freezer: - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, zero + timedelta(minutes=15), "sensor.test1", attributes ) states["sensor.test1"] += _states["sensor.test1"] - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, zero + timedelta(minutes=20), "sensor.test1", attributes ) + await async_wait_recording_done(hass) states["sensor.test1"] += _states["sensor.test1"] hist = history.get_significant_states( hass, zero, four, hass.states.async_entity_ids() @@ -3256,8 +3323,8 @@ def test_compile_hourly_statistics_changing_device_class_1( # Run statistics again, additional statistics is generated do_adhoc_statistics(hass, start=zero + timedelta(minutes=20)) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -3324,8 +3391,8 @@ def test_compile_hourly_statistics_changing_device_class_1( ("power", "kW", "kW", "kW", "power", 13.050847, 13.333333, -10, 30), ], ) -def test_compile_hourly_statistics_changing_device_class_2( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_statistics_changing_device_class_2( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -3342,9 +3409,9 @@ def test_compile_hourly_statistics_changing_device_class_2( Device class is ignored, meaning changing device class should not influence the statistics. """ zero = dt_util.utcnow() - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) # Record some states for an initial period, the entity has a device class attributes = { @@ -3353,12 +3420,15 @@ def test_compile_hourly_statistics_changing_device_class_2( "unit_of_measurement": state_unit, } with freeze_time(zero) as freezer: - four, states = record_states(hass, freezer, zero, "sensor.test1", attributes) + four, states = await async_record_states( + hass, freezer, zero, "sensor.test1", attributes + ) + await async_wait_recording_done(hass) do_adhoc_statistics(hass, start=zero) - wait_recording_done(hass) + await async_wait_recording_done(hass) assert "does not match the unit of already compiled" not in caplog.text - statistic_ids = list_statistic_ids(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -3390,13 +3460,14 @@ def test_compile_hourly_statistics_changing_device_class_2( # Remove device class and record additional states attributes.pop("device_class") with freeze_time(zero) as freezer: - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, zero + timedelta(minutes=5), "sensor.test1", attributes ) states["sensor.test1"] += _states["sensor.test1"] - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, zero + timedelta(minutes=10), "sensor.test1", attributes ) + await async_wait_recording_done(hass) states["sensor.test1"] += _states["sensor.test1"] hist = history.get_significant_states( hass, zero, four, hass.states.async_entity_ids() @@ -3405,8 +3476,8 @@ def test_compile_hourly_statistics_changing_device_class_2( # Run statistics again, additional statistics is generated do_adhoc_statistics(hass, start=zero + timedelta(minutes=10)) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -3462,8 +3533,8 @@ def test_compile_hourly_statistics_changing_device_class_2( (None, None, None, None, "unitless", 13.050847, -10, 30), ], ) -def test_compile_hourly_statistics_changing_state_class( - hass_recorder: Callable[..., HomeAssistant], +async def test_compile_hourly_statistics_changing_state_class( + hass: HomeAssistant, caplog: pytest.LogCaptureFixture, device_class, state_unit, @@ -3478,9 +3549,9 @@ def test_compile_hourly_statistics_changing_state_class( period0 = dt_util.utcnow() period0_end = period1 = period0 + timedelta(minutes=5) period1_end = period0 + timedelta(minutes=10) - hass = hass_recorder() - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes_1 = { "device_class": device_class, "state_class": "measurement", @@ -3492,12 +3563,13 @@ def test_compile_hourly_statistics_changing_state_class( "unit_of_measurement": state_unit, } with freeze_time(period0) as freezer: - four, states = record_states( + four, states = await async_record_states( hass, freezer, period0, "sensor.test1", attributes_1 ) + await async_wait_recording_done(hass) do_adhoc_statistics(hass, start=period0) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -3527,9 +3599,10 @@ def test_compile_hourly_statistics_changing_state_class( # Add more states, with changed state class with freeze_time(period1) as freezer: - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, period1, "sensor.test1", attributes_2 ) + await async_wait_recording_done(hass) states["sensor.test1"] += _states["sensor.test1"] hist = history.get_significant_states( hass, period0, four, hass.states.async_entity_ids() @@ -3537,8 +3610,8 @@ def test_compile_hourly_statistics_changing_state_class( assert_dict_of_states_equal_without_context_and_last_changed(states, hist) do_adhoc_statistics(hass, start=period1) - wait_recording_done(hass) - statistic_ids = list_statistic_ids(hass) + await async_wait_recording_done(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -3595,22 +3668,21 @@ def test_compile_hourly_statistics_changing_state_class( @pytest.mark.timeout(25) -def test_compile_statistics_hourly_daily_monthly_summary( - hass_recorder: Callable[..., HomeAssistant], caplog: pytest.LogCaptureFixture +@pytest.mark.parametrize("recorder_config", [{CONF_COMMIT_INTERVAL: 3600 * 4}]) +@pytest.mark.freeze_time("2021-09-01 05:00") # August 31st, 23:00 local time +async def test_compile_statistics_hourly_daily_monthly_summary( + hass: HomeAssistant, + freezer: FrozenDateTimeFactory, + caplog: pytest.LogCaptureFixture, ) -> None: """Test compiling hourly statistics + monthly and daily summary.""" + dt_util.set_default_time_zone(dt_util.get_time_zone("America/Regina")) + zero = dt_util.utcnow() - # August 31st, 23:00 local time - zero = zero.replace( - year=2021, month=9, day=1, hour=5, minute=0, second=0, microsecond=0 - ) - with freeze_time(zero): - hass = hass_recorder() - # Remove this after dropping the use of the hass_recorder fixture - hass.config.set_time_zone("America/Regina") instance = get_instance(hass) - setup_component(hass, "sensor", {}) - wait_recording_done(hass) # Wait for the sensor recorder platform to be added + await async_setup_component(hass, "sensor", {}) + # Wait for the sensor recorder platform to be added + await async_recorder_block_till_done(hass) attributes = { "device_class": None, "state_class": "measurement", @@ -3673,7 +3745,7 @@ def test_compile_statistics_hourly_daily_monthly_summary( for i in range(24): seq = [-10, 15, 30] # test1 has same value in every period - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, start, "sensor.test1", attributes, seq ) states["sensor.test1"] += _states["sensor.test1"] @@ -3686,7 +3758,7 @@ def test_compile_statistics_hourly_daily_monthly_summary( last_states["sensor.test1"] = seq[-1] # test2 values change: min/max at the last state seq = [-10 * (i + 1), 15 * (i + 1), 30 * (i + 1)] - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, start, "sensor.test2", attributes, seq ) states["sensor.test2"] += _states["sensor.test2"] @@ -3699,7 +3771,7 @@ def test_compile_statistics_hourly_daily_monthly_summary( last_states["sensor.test2"] = seq[-1] # test3 values change: min/max at the first state seq = [-10 * (23 - i + 1), 15 * (23 - i + 1), 30 * (23 - i + 1)] - four, _states = record_states( + four, _states = await async_record_states( hass, freezer, start, "sensor.test3", attributes, seq ) states["sensor.test3"] += _states["sensor.test3"] @@ -3714,7 +3786,7 @@ def test_compile_statistics_hourly_daily_monthly_summary( seq = [i, i + 0.5, i + 0.75] start_meter = start for j in range(len(seq)): - _states = record_meter_state( + _states = await async_record_meter_state( hass, freezer, start_meter, @@ -3732,6 +3804,7 @@ def test_compile_statistics_hourly_daily_monthly_summary( last_states["sensor.test4"] = seq[-1] start += timedelta(minutes=5) + await async_wait_recording_done(hass) hist = history.get_significant_states( hass, zero - timedelta.resolution, @@ -3740,16 +3813,16 @@ def test_compile_statistics_hourly_daily_monthly_summary( significant_changes_only=False, ) assert_dict_of_states_equal_without_context_and_last_changed(states, hist) - wait_recording_done(hass) + await async_wait_recording_done(hass) # Generate 5-minute statistics for two hours start = zero for _ in range(24): do_adhoc_statistics(hass, start=start) - wait_recording_done(hass) + await async_wait_recording_done(hass) start += timedelta(minutes=5) - statistic_ids = list_statistic_ids(hass) + statistic_ids = await async_list_statistic_ids(hass) assert statistic_ids == [ { "statistic_id": "sensor.test1", @@ -3801,7 +3874,7 @@ def test_compile_statistics_hourly_daily_monthly_summary( instance.async_adjust_statistics( "sensor.test4", sum_adjustement_start, sum_adjustment, "EUR" ) - wait_recording_done(hass) + await async_wait_recording_done(hass) stats = statistics_during_period(hass, zero, period="5minute") expected_stats = { @@ -4026,7 +4099,7 @@ def test_compile_statistics_hourly_daily_monthly_summary( assert "Error while processing event StatisticsTask" not in caplog.text -def record_states( +async def async_record_states( hass: HomeAssistant, freezer: FrozenDateTimeFactory, zero: datetime, @@ -4044,8 +4117,7 @@ def record_states( def set_state(entity_id, state, **kwargs): """Set the state.""" - hass.states.set(entity_id, state, **kwargs) - wait_recording_done(hass) + hass.states.async_set(entity_id, state, **kwargs) return hass.states.get(entity_id) one = zero + timedelta(seconds=1 * 5) @@ -4096,7 +4168,6 @@ def record_states( ], ) async def test_validate_unit_change_convertible( - recorder_mock: Recorder, hass: HomeAssistant, hass_ws_client: WebSocketGenerator, units, @@ -4218,7 +4289,6 @@ async def test_validate_unit_change_convertible( ], ) async def test_validate_statistics_unit_ignore_device_class( - recorder_mock: Recorder, hass: HomeAssistant, hass_ws_client: WebSocketGenerator, units, @@ -4306,7 +4376,6 @@ async def test_validate_statistics_unit_ignore_device_class( ], ) async def test_validate_statistics_unit_change_no_device_class( - recorder_mock: Recorder, hass: HomeAssistant, hass_ws_client: WebSocketGenerator, units, @@ -4428,7 +4497,6 @@ async def test_validate_statistics_unit_change_no_device_class( ], ) async def test_validate_statistics_unsupported_state_class( - recorder_mock: Recorder, hass: HomeAssistant, hass_ws_client: WebSocketGenerator, units, @@ -4497,7 +4565,6 @@ async def test_validate_statistics_unsupported_state_class( ], ) async def test_validate_statistics_sensor_no_longer_recorded( - recorder_mock: Recorder, hass: HomeAssistant, hass_ws_client: WebSocketGenerator, units, @@ -4565,7 +4632,6 @@ async def test_validate_statistics_sensor_no_longer_recorded( ], ) async def test_validate_statistics_sensor_not_recorded( - recorder_mock: Recorder, hass: HomeAssistant, hass_ws_client: WebSocketGenerator, units, @@ -4630,7 +4696,6 @@ async def test_validate_statistics_sensor_not_recorded( ], ) async def test_validate_statistics_sensor_removed( - recorder_mock: Recorder, hass: HomeAssistant, hass_ws_client: WebSocketGenerator, units, @@ -4694,7 +4759,6 @@ async def test_validate_statistics_sensor_removed( ], ) async def test_validate_statistics_unit_change_no_conversion( - recorder_mock: Recorder, hass: HomeAssistant, hass_ws_client: WebSocketGenerator, attributes, @@ -4825,7 +4889,6 @@ async def test_validate_statistics_unit_change_no_conversion( ], ) async def test_validate_statistics_unit_change_equivalent_units( - recorder_mock: Recorder, hass: HomeAssistant, hass_ws_client: WebSocketGenerator, attributes, @@ -4909,7 +4972,6 @@ async def test_validate_statistics_unit_change_equivalent_units( ], ) async def test_validate_statistics_unit_change_equivalent_units_2( - recorder_mock: Recorder, hass: HomeAssistant, hass_ws_client: WebSocketGenerator, attributes, @@ -5002,7 +5064,7 @@ async def test_validate_statistics_unit_change_equivalent_units_2( async def test_validate_statistics_other_domain( - recorder_mock: Recorder, hass: HomeAssistant, hass_ws_client: WebSocketGenerator + hass: HomeAssistant, hass_ws_client: WebSocketGenerator ) -> None: """Test sensor does not raise issues for statistics for other domains.""" msg_id = 1 @@ -5049,7 +5111,7 @@ async def test_validate_statistics_other_domain( await assert_validation_result(client, {}) -def record_meter_states( +async def async_record_meter_states( hass: HomeAssistant, freezer: FrozenDateTimeFactory, zero: datetime, @@ -5064,7 +5126,7 @@ def record_meter_states( def set_state(entity_id, state, **kwargs): """Set the state.""" - hass.states.set(entity_id, state, **kwargs) + hass.states.async_set(entity_id, state, **kwargs) return hass.states.get(entity_id) one = zero + timedelta(seconds=15 * 5) # 00:01:15 @@ -5116,7 +5178,7 @@ def record_meter_states( return four, eight, states -def record_meter_state( +async def async_record_meter_state( hass: HomeAssistant, freezer: FrozenDateTimeFactory, zero: datetime, @@ -5131,8 +5193,7 @@ def record_meter_state( def set_state(entity_id, state, **kwargs): """Set the state.""" - hass.states.set(entity_id, state, **kwargs) - wait_recording_done(hass) + hass.states.async_set(entity_id, state, **kwargs) return hass.states.get(entity_id) states = {entity_id: []} @@ -5142,7 +5203,7 @@ def record_meter_state( return states -def record_states_partially_unavailable(hass, zero, entity_id, attributes): +async def async_record_states_partially_unavailable(hass, zero, entity_id, attributes): """Record some test states. We inject a bunch of state updates temperature sensors. @@ -5150,8 +5211,7 @@ def record_states_partially_unavailable(hass, zero, entity_id, attributes): def set_state(entity_id, state, **kwargs): """Set the state.""" - hass.states.set(entity_id, state, **kwargs) - wait_recording_done(hass) + hass.states.async_set(entity_id, state, **kwargs) return hass.states.get(entity_id) one = zero + timedelta(seconds=1 * 5) @@ -5175,7 +5235,7 @@ def record_states_partially_unavailable(hass, zero, entity_id, attributes): async def test_exclude_attributes( - recorder_mock: Recorder, hass: HomeAssistant, enable_custom_integrations: None + hass: HomeAssistant, enable_custom_integrations: None ) -> None: """Test sensor attributes to be excluded.""" entity0 = MockSensor(