fix(genetic): allow optimization without fresh SoC (#1403)

This commit is contained in:
Andreas
2026-10-13 19:02:19 +02:00
committed by GitHub
parent fab3e17446
commit 49ea062dc8
8 changed files with 103 additions and 26 deletions
+1 -1
View File
@@ -188,7 +188,7 @@
| horizon_hours | `int` | `rw` | `24` | The general time window within which the energy optimization goal shall be achieved [h]. Defaults to 24 hours. |
| individuals | `Optional[int]` | `rw` | `300` | Number of individuals (solutions) in the population [>= 10]. Defaults to 300. |
| interval_sec | `Literal[900, 3600]` | `rw` | `3600` | The optimization interval [sec]. Defaults to 3600 seconds (1 hour) |
| measurement_max_age_seconds | `int` | `rw` | `300` | Maximum age of SoC measurements for configuration-based optimization [s]. |
| measurement_max_age_seconds | `int` | `rw` | `300` | Maximum age of SoC measurements used for configuration-based optimization [s]. Without an explicit SoC or usable measurement, the initial SoC defaults to 0%. |
| penalties | `dict[str, Union[float, int, str]]` | `rw` | `required` | Penalty parameters used in fitness evaluation. |
| pin_workers | `bool` | `rw` | `True` | Pin the evaluation workers to the last 'workers' CPU cores. The server process stays unpinned and keeps a core that is not busy with the optimization, so it answers requests during a run, and the run never uses more than 'workers' cores. Needs at least one core more than workers; Linux only. |
| seed | `Optional[int]` | `rw` | `None` | Random seed for reproducibility. None = random. |
+3 -1
View File
@@ -1385,7 +1385,9 @@ Optimize GENETIC using configured devices and optional fresh runtime inputs.
Static settings belong in configuration; query overrides are rejected.
Forecast arrays start at local
midnight and contain Wh per configured GENETIC slot; prices are currency/Wh.
An empty body uses configured providers and fresh measured states of charge.
An empty body uses configured providers. Explicit SoC values take precedence over
fresh measured states of charge; missing usable measurements default to an assumed
initial SoC of 0% without blocking a plan.
The deprecated /optimize endpoint continues to run hourly GENETIC0.
"""
```
+11 -5
View File
@@ -53,22 +53,28 @@ the old feature branch migrate into the GENETIC section; explicit nested setting
The new request accepts `soc`, `forecasts`, `start_solution` and
`start_solution_datetime`. Hardware, device limits and schedules belong in configuration.
An empty JSON object uses configured providers and fresh measurements. Hardware overrides
An empty JSON object uses configured providers and measured or assumed initial SoC. Hardware overrides
in the body and query-string overrides are rejected. Do not migrate by changing only the URL.
The legacy endpoint remains available, but the surrounding configuration has changed.
That is not a promise that every old script works unchanged.
### 3. Fresh measurements and complete forecasts are required
### 3. SoC measurements are optional; complete forecasts are required
Request SoC values are integer percentages from 0 to 100, keyed by device ID. Automatic
measurement lookup instead reads a factor from 0 to 1 using the configured measurement
key, by default `<device_id>-soc-factor`. For example, 50% is `50` in the request and
`0.5` in that measurement channel.
Without a request override, a missing, future, invalid or stale SoC cancels the run.
The default freshness limit is 300 seconds, controlled by
`optimization.genetic.measurement_max_age_seconds`. Check the measurement update rate.
Explicit request SoC values take precedence over measurements. Without an override,
EOS uses the latest valid fresh measurement. If the measurement is missing, future,
invalid or stale, the run assumes **0% initial SoC** for that battery or EV and continues.
The fallback is logged as an assumption and is never written as a measurement or a
configuration change. SoC updates are therefore optional for planning.
The default measurement freshness limit is 300 seconds, controlled by
`optimization.genetic.measurement_max_age_seconds`. This limit determines whether a
measurement can be used; it does not require an update before every run.
Missing forecasts within the control period also stop the run. A shorter forecast
continuation is allowed and reported. Failed calls return an error; they no longer look