Skip to content

Commit

Permalink
Fix statistic_during_period after core restart (#119323)
Browse files Browse the repository at this point in the history
  • Loading branch information
emontnemery authored and frenck committed Jun 11, 2024
1 parent a0ac9fe commit 6ea18a7
Show file tree
Hide file tree
Showing 2 changed files with 39 additions and 4 deletions.
25 changes: 23 additions & 2 deletions homeassistant/components/recorder/statistics.py
Original file line number Diff line number Diff line change
Expand Up @@ -1245,7 +1245,7 @@ def _first_statistic(
table: type[StatisticsBase],
metadata_id: int,
) -> datetime | None:
"""Return the data of the oldest statistic row for a given metadata id."""
"""Return the date of the oldest statistic row for a given metadata id."""
stmt = lambda_stmt(
lambda: select(table.start_ts)
.filter(table.metadata_id == metadata_id)
Expand All @@ -1257,6 +1257,23 @@ def _first_statistic(
return None


def _last_statistic(
session: Session,
table: type[StatisticsBase],
metadata_id: int,
) -> datetime | None:
"""Return the date of the newest statistic row for a given metadata id."""
stmt = lambda_stmt(
lambda: select(table.start_ts)
.filter(table.metadata_id == metadata_id)
.order_by(table.start_ts.desc())
.limit(1)
)
if stats := cast(Sequence[Row], execute_stmt_lambda_element(session, stmt)):
return dt_util.utc_from_timestamp(stats[0].start_ts)
return None


def _get_oldest_sum_statistic(
session: Session,
head_start_time: datetime | None,
Expand Down Expand Up @@ -1487,7 +1504,11 @@ def statistic_during_period(
tail_start_time: datetime | None = None
tail_end_time: datetime | None = None
if end_time is None:
tail_start_time = now.replace(minute=0, second=0, microsecond=0)
tail_start_time = _last_statistic(session, Statistics, metadata_id)
if tail_start_time:
tail_start_time += Statistics.duration
else:
tail_start_time = now.replace(minute=0, second=0, microsecond=0)
elif tail_only:
tail_start_time = start_time
tail_end_time = end_time
Expand Down
18 changes: 16 additions & 2 deletions tests/components/recorder/test_websocket_api.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
from unittest.mock import ANY, patch

from freezegun import freeze_time
from freezegun.api import FrozenDateTimeFactory
import pytest

from homeassistant.components import recorder
Expand Down Expand Up @@ -794,17 +795,30 @@ def next_id():
}


@pytest.mark.freeze_time(datetime.datetime(2022, 10, 21, 6, 31, tzinfo=datetime.UTC))
@pytest.mark.parametrize(
"frozen_time",
[
# This is the normal case, all statistics runs are available
datetime.datetime(2022, 10, 21, 6, 31, tzinfo=datetime.UTC),
# Statistic only available up until 6:25, this can happen if
# core has been shut down for an hour
datetime.datetime(2022, 10, 21, 7, 31, tzinfo=datetime.UTC),
],
)
async def test_statistic_during_period_partial_overlap(
recorder_mock: Recorder,
hass: HomeAssistant,
hass_ws_client: WebSocketGenerator,
freezer: FrozenDateTimeFactory,
frozen_time: datetime,
) -> None:
"""Test statistic_during_period."""
client = await hass_ws_client()

freezer.move_to(frozen_time)
now = dt_util.utcnow()

await async_recorder_block_till_done(hass)
client = await hass_ws_client()

zero = now
start = zero.replace(hour=0, minute=0, second=0, microsecond=0)
Expand Down

0 comments on commit 6ea18a7

Please sign in to comment.