mirror of
https://github.com/Akkudoktor-EOS/EOS.git
synced 2026-08-10 02:46:11 +00:00
chore: adapt deprecated endpoints to 15-minutes predictions (#1195)
Bump Version / Bump Version Workflow (push) Canceled after 0s
CodeQL Advanced / Analyze (actions) (push) Canceled after 0s
CodeQL Advanced / Analyze (python) (push) Canceled after 0s
docker-build / platform-excludes (push) Canceled after 0s
pre-commit / pre-commit (push) Canceled after 0s
Run Pytest on Pull Request / test (push) Canceled after 0s
docker-build / build (push) Canceled after 0s
docker-build / merge (push) Canceled after 0s
Bump Version / Bump Version Workflow (push) Canceled after 0s
CodeQL Advanced / Analyze (actions) (push) Canceled after 0s
CodeQL Advanced / Analyze (python) (push) Canceled after 0s
docker-build / platform-excludes (push) Canceled after 0s
pre-commit / pre-commit (push) Canceled after 0s
Run Pytest on Pull Request / test (push) Canceled after 0s
docker-build / build (push) Canceled after 0s
docker-build / merge (push) Canceled after 0s
Ensure the deprecated endpoints get /strompreis, post /gesamtlast, get /gesamtlast_simple,
get /pvforecast to work on 1-hour intervalls even if the prediction provides 15-minutes
intervall data. This keeps the interface compliant to the legacy functionality.
Besides this adaptations several other improvements and fixes are included in this PR.
* feat: extend data management method key_to array by resample_method
One can now define the resample method on how to aggregate the values in an interval
for resampling. Three methods are provided:
- "first": Use the first value in each interval.
- "mean": Compute the arithmetic mean of all samples in each interval.
- "interval_mean": Compute the time-weighted mean assuming each value remains valid
until the next timestamp (piecewise-constant signal).
* feat: extend the get /v1/prediction/dataframe endpoint with resampling parameters
Make all parameters for resampling available at the endpoint.
* feat: extend the get /v1/prediction/list endpoint with resampling parameters
Make all parameters for resampling available at the endpoint.
* feat: add new delete /v1/prediction/range endpoint
The endpoint allows to delete prediction values for a given time span.
* fix: adapt for PVForecastAkkudoktor server side cache handling
/api.akkudoktor/forecast does it's own caching on requests. Call it with slightly
randomized request values to avoid getting cached values in the case we need fresh
data. The requests are anyway rate limited to one request per hour on our side.
* chore: add core.types
This module centralizes reusable type definitions shared across multiple
packages. Defining common types here avoids duplication of complex type
annotations (such as Literal aliases), ensures consistent typing across the
code base, and helps prevent circular import dependencies between modules.
* chore: extend cache testing
* chore: add system test for deprecated /strompreis endpoint
* chore: add unit test module for server endpoints
Add a new test module to do unit tests on server endpoints. First test added
for deprecated get /strompreis endpoint.
Signed-off-by: Bobby Noelte <b0661n0e17e@gmail.com>
This commit is contained in:
@@ -427,6 +427,34 @@ class TestDataSequence:
|
||||
fill_method="invalid",
|
||||
)
|
||||
|
||||
async def test_key_to_array_resample_first(self, sequence):
|
||||
"""Test that resample_method='first' returns the first sample in each interval."""
|
||||
interval = to_duration("1 hour")
|
||||
|
||||
for minute, value in (
|
||||
(0, 1.0),
|
||||
(15, 2.0),
|
||||
(30, 3.0),
|
||||
(45, 4.0),
|
||||
):
|
||||
await sequence.insert_by_datetime(
|
||||
self.create_test_record(
|
||||
pendulum.datetime(2023, 11, 6, 0, minute),
|
||||
value,
|
||||
)
|
||||
)
|
||||
|
||||
array = await sequence.key_to_array(
|
||||
key="data_value",
|
||||
start_datetime=pendulum.datetime(2023, 11, 6, 0),
|
||||
end_datetime=pendulum.datetime(2023, 11, 6, 1),
|
||||
interval=interval,
|
||||
resample_method="first",
|
||||
)
|
||||
|
||||
assert len(array) == 1
|
||||
assert array[0] == 1.0
|
||||
|
||||
async def test_key_to_array_resample_mean(self, sequence):
|
||||
"""Test that numeric resampling uses mean when multiple values fall into one interval."""
|
||||
interval = to_duration("1 hour")
|
||||
@@ -447,6 +475,7 @@ class TestDataSequence:
|
||||
start_datetime=pendulum.datetime(2023, 11, 6, 0),
|
||||
end_datetime=pendulum.datetime(2023, 11, 6, 1),
|
||||
interval=interval,
|
||||
resample_method="mean",
|
||||
)
|
||||
|
||||
assert isinstance(array, np.ndarray)
|
||||
@@ -454,6 +483,70 @@ class TestDataSequence:
|
||||
# The first interval mean = (1+2+3+4)/4 = 2.5
|
||||
assert array[0] == pytest.approx(2.5)
|
||||
|
||||
async def test_key_to_array_resample_interval_mean(self, sequence):
|
||||
"""Test that interval_mean computes a time-weighted mean."""
|
||||
|
||||
interval = to_duration("1 hour")
|
||||
|
||||
await sequence.insert_by_datetime(
|
||||
self.create_test_record(
|
||||
pendulum.datetime(2023, 11, 6, 0, 0),
|
||||
10.0,
|
||||
)
|
||||
)
|
||||
await sequence.insert_by_datetime(
|
||||
self.create_test_record(
|
||||
pendulum.datetime(2023, 11, 6, 0, 45),
|
||||
20.0,
|
||||
)
|
||||
)
|
||||
await sequence.insert_by_datetime(
|
||||
self.create_test_record(
|
||||
pendulum.datetime(2023, 11, 6, 1, 0),
|
||||
20.0,
|
||||
)
|
||||
)
|
||||
|
||||
array = await sequence.key_to_array(
|
||||
key="data_value",
|
||||
start_datetime=pendulum.datetime(2023, 11, 6, 0),
|
||||
end_datetime=pendulum.datetime(2023, 11, 6, 1),
|
||||
interval=interval,
|
||||
resample_method="interval_mean",
|
||||
fill_method="none",
|
||||
)
|
||||
|
||||
assert len(array) == 1
|
||||
|
||||
# 10 for 45 min, 20 for 15 min
|
||||
expected = (10 * 45 + 20 * 15) / 60
|
||||
|
||||
assert array[0] == pytest.approx(expected)
|
||||
|
||||
async def test_key_to_array_invalid_resample_method(self, sequence):
|
||||
"""Test invalid resample_method raises an error."""
|
||||
|
||||
interval = to_duration("1 hour")
|
||||
|
||||
await sequence.insert_by_datetime(
|
||||
self.create_test_record(
|
||||
pendulum.datetime(2023, 11, 6),
|
||||
1.0,
|
||||
)
|
||||
)
|
||||
|
||||
with pytest.raises(
|
||||
ValueError,
|
||||
match="Unsupported resample method: invalid",
|
||||
):
|
||||
await sequence.key_to_array(
|
||||
key="data_value",
|
||||
start_datetime=pendulum.datetime(2023, 11, 6),
|
||||
end_datetime=pendulum.datetime(2023, 11, 6, 1),
|
||||
interval=interval,
|
||||
resample_method="invalid",
|
||||
)
|
||||
|
||||
# ------------------------------------------------------------------
|
||||
# key_to_array — align_to_interval parameter
|
||||
# ------------------------------------------------------------------
|
||||
|
||||
Reference in New Issue
Block a user