Merge origin/master (0.20.1) into release/1.0
Brings OPT-36 (#229) and TEST-37 (#231) onto release/1.0, which keeps SAFETY-128 (#228). No textual conflicts. CHANGELOG: the SAFETY-128 entry moved out of the released 0.20.0 section into "Not in a release yet" above ## 0.20.1; the 0.20.0 and 0.20.1 sections are identical to master. Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
@@ -6,6 +6,7 @@
|
||||
|
||||
- **Shortfall.** `sum_h max(0, house_h - trust x sun_h)` over every expensive hour, `/ EFF`, from the floor. It replaces the use over the run with no sun counted, which on a day and night tariff bought for the whole day (G1, `reports/UX-69-design-report.md`). The sun before the run is unchanged. A run with its dear hours after sunset gives the old number.
|
||||
- **House use.** An hour with sun is read at no less than the night base, as the sun sum reads it (the profile is net of the sun). An hour without is read as measured. An hour with no forecast counts no sun.
|
||||
- **Several batteries.** One total, shared by capacity with the ceiling passed on (`dayplan._spread()`). With the same floor and ceiling for all, they reach the ceiling together, so a shortfall that one battery cannot hold fills both to the same level, not one first. More than all hold: all go to the ceiling, `Plan.uncovered_kwh` is the rest, carried by another battery (Cheap hours, Solar first) or the grid, as the screen says.
|
||||
- **Cheap hours** still fills up and is not counted in the share; **Solar first** still never charges from the grid. The mode help says so.
|
||||
- **Not done:** the run length (OPT-25); netting what a Cheap hours or Solar first battery will hold against the shortfall.
|
||||
- **Several batteries.** One total, shared by capacity with the ceiling passed on (`dayplan._spread()`). With the same floor and ceiling for all, they reach the ceiling together, so a shortfall that one battery cannot hold fills both to the same level, not one first. More than all hold: all go to the ceiling, `Plan.uncovered_kwh` is the rest, carried by the grid (OPT-36 counts the other batteries first), as the screen says.
|
||||
- **Cheap hours** still fills up; **Solar first** still never charges from the grid. The mode help says so.
|
||||
- **OPT-36 (0.20.1):** Cheap hours and Solar first batteries give first; Leftover solar shares only the rest of the shortfall (`dayplan._cheap_give_kwh()`, `_solar_first_give_kwh()`). A Cheap hours battery counts the level its charge reaches: the cheap run, then later slots still worth charging in and no dearer than any slot from the expensive hours on, under the peak aim, x EFF stored. A Solar first battery counts what is left after the house's use until the hours start, each hour at no less than the night base. Live, 2026-11-02: A at 60 % went to 95 % while B at 94 % covered the hours. Owner, 2026-11-02: Solar first counts too. Test: `test_opt36.py`.
|
||||
- **Not done:** the run length (OPT-25). On a dynamic tariff the Cheap hours count guesses where control will charge; a counted slot can still go unused, and that gap comes from the grid.
|
||||
|
||||
Reference in New Issue
Block a user