uprava vypoctu slotu
Some checks failed
CI and deploy / migration-check (push) Failing after 16s
CI and deploy / deploy (push) Has been skipped

This commit is contained in:
Dusan Vojacek
2026-05-21 12:36:03 +02:00
parent 08f1b6741a
commit b78597fdda
8 changed files with 346 additions and 6 deletions

View File

@@ -30,7 +30,9 @@ returns table (
safety_soc_target_wh numeric,
future_avoided_buy_czk_kwh numeric,
future_sell_opportunity_czk_kwh numeric,
is_daytime_pv_surplus_slot boolean
is_daytime_pv_surplus_slot boolean,
charge_acquisition_buy_czk_kwh numeric,
charge_acquisition_cutoff_at timestamptz
)
language plpgsql
volatile
@@ -69,6 +71,12 @@ declare
v_buy_lookahead_eps numeric := 0.05;
v_grid_slots_am int := 0;
v_grid_slots_pm int := 0;
v_acquisition_cutoff timestamptz;
v_charge_acquisition numeric;
v_est_grid_wh numeric;
v_est_pv_wh numeric;
v_est_grid_cost numeric;
v_est_pv_cost numeric;
begin
drop table if exists _ems_plan_slot_wk;
create temp table _ems_plan_slot_wk on commit drop as
@@ -428,6 +436,73 @@ begin
end loop;
end if;
-- Vážená acquisition cena zásoby (grid + FVE opportunity) jen pro sloty PŘED prvním
-- plánovaným exportem z baterie — nepočítá nákup po večerním/nočním vybití do sítě.
select min(wk.interval_start)
into v_acquisition_cutoff
from _ems_plan_slot_wk wk
where wk.allow_discharge_export;
select
coalesce(sum(
case
when wk.allow_charge
and (
v_acquisition_cutoff is null
or wk.interval_start < v_acquisition_cutoff
)
then v_per_slot_charge_wh
else 0
end
), 0),
coalesce(sum(
case
when wk.pv_surplus_w > 0
and (
v_acquisition_cutoff is null
or wk.interval_start < v_acquisition_cutoff
)
then least(wk.pv_surplus_w, v_max_charge_w) * v_charge_eff * 0.25
else 0
end
), 0),
coalesce(sum(
case
when wk.allow_charge
and (
v_acquisition_cutoff is null
or wk.interval_start < v_acquisition_cutoff
)
then wk.buy_price * v_per_slot_charge_wh
else 0
end
), 0),
coalesce(sum(
case
when wk.pv_surplus_w > 0
and (
v_acquisition_cutoff is null
or wk.interval_start < v_acquisition_cutoff
)
then coalesce(wk.future_sell_lookahead, wk.sell_price)
* least(wk.pv_surplus_w, v_max_charge_w) * v_charge_eff * 0.25
else 0
end
), 0)
into
v_est_grid_wh,
v_est_pv_wh,
v_est_grid_cost,
v_est_pv_cost
from _ems_plan_slot_wk wk;
if (v_est_grid_wh + v_est_pv_wh) > 0 then
v_charge_acquisition := (v_est_grid_cost + v_est_pv_cost)
/ (v_est_grid_wh + v_est_pv_wh);
else
v_charge_acquisition := v_ref_buy_czk_kwh;
end if;
return query
with night_tot as (
select coalesce(sum(w2.load_baseline_w), 0) * 0.25 as night_wh
@@ -511,7 +586,9 @@ begin
e.safety_soc_target_wh,
e.future_avoided_buy_czk_kwh,
e.future_sell_opportunity_czk_kwh,
e.is_daytime_pv_surplus_slot
e.is_daytime_pv_surplus_slot,
v_charge_acquisition as charge_acquisition_buy_czk_kwh,
v_acquisition_cutoff as charge_acquisition_cutoff_at
from enriched e
order by e.slot_ord;
end;
@@ -524,4 +601,6 @@ comment on function ems.fn_load_planning_slots_full is
'ref_buy = min(buy) horizontu. Discharge-export: nejdražší sell kde sell>ref_buy+degrad (spot). '
'Strop SoC pro výpočet energie k dobití: coalesce(planner_max_soc_percent, max_soc_percent). '
'Denní safety vstupy: night_baseload_* (20:0006:00 Europe/Prague), safety_soc_target_wh (619), '
'lookahead max buy/sell pro měkké LP penalizace.';
'lookahead max buy/sell pro měkké LP penalizace. '
'charge_acquisition_buy_czk_kwh: vážený průměr grid (allow_charge) + FVE (pv_surplus, opportunity future_sell) '
'jen pro sloty před charge_acquisition_cutoff_at (= začátek prvního allow_discharge_export).';