Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
79 commits
Select commit Hold shift + click to select a range
a6c74d0
initial commit
Jan 7, 2025
bb9cbfb
Merge branch 'develop' into bess-export
Feb 7, 2025
3cebd7e
start adding inputs
Feb 10, 2025
1575a9b
Merge branch 'develop' into bess-export
adfarth May 27, 2025
b211b44
rm can_grid_charge
adfarth May 27, 2025
e065d2f
set up framework
adfarth May 28, 2025
a8b2dca
Merge branch 'develop' into bess-export
adfarth May 30, 2025
52f036b
update electric_utility_constraints
adfarth May 30, 2025
47bfc79
make discharge from storage total discharge
adfarth May 30, 2025
8d9be52
update results
adfarth May 30, 2025
b897e47
fix reopt_inputs
adfarth Jun 2, 2025
946f8a0
Merge branch 'develop' into bess-export
adfarth Jun 2, 2025
5ac4c84
fix indexing
adfarth Jun 2, 2025
a302d7f
Update inputs.jl
adfarth Jun 2, 2025
ae2f872
add todo
hdunham Jun 4, 2025
f823ae4
Update CHANGELOG.md
hdunham Jun 10, 2025
9322adf
condense 4 constraints into 1
hdunham Jun 10, 2025
1e0b211
Update storage_constraints.jl
hdunham Jun 10, 2025
7743683
rm commented out refs to can_export_to_grid
hdunham Jun 10, 2025
48c270d
rm resolved TODOs on defining dvStorageToGrid
hdunham Jun 10, 2025
041d759
rmv extra constraint
adfarth Jun 11, 2025
cd67b3f
updt CUR to EXC
adfarth Jun 11, 2025
42a4937
rmv todos and infos
adfarth Jun 11, 2025
827647a
add todos, rm unneeded if
hdunham Jun 12, 2025
547d1bd
MPC storage export
hdunham Jun 12, 2025
daf8d1d
Merge branch 'bess-export' of https://github.com/NREL/REopt.jl into b…
hdunham Jun 12, 2025
7da2839
replace NEM_techs & WHL_techs w techs_by_exportbin elem, same for sto…
hdunham Jun 12, 2025
e19efe6
remove infos
hdunham Jun 16, 2025
61aba35
Revert "replace NEM_techs & WHL_techs w techs_by_exportbin elem, same…
hdunham Jun 16, 2025
1d05bec
rm todo
hdunham Jun 16, 2025
335acee
reformat RE sums/comments for clarity
hdunham Jun 16, 2025
056106f
fix MPC convert error
hdunham Jun 16, 2025
fae0ff8
combine 2 tests
hdunham Jun 17, 2025
5c31eeb
correct constraint (4d) loop
hdunham Jun 17, 2025
f45fe81
Update runtests.jl
hdunham Jun 17, 2025
55ce586
start bess export testing
hdunham Jun 17, 2025
0a7c831
update bess export testing
hdunham Jun 17, 2025
d522d0f
add comment to clarify bound
hdunham Jun 17, 2025
dbb5b17
update bess export testing
hdunham Jun 18, 2025
cbecb6b
ex update
adfarth Jun 25, 2025
1b5e9eb
export in emissions
adfarth Jun 25, 2025
63a214b
Update emissions_constraints.jl
adfarth Jul 3, 2025
0026738
bigM_hourly_load_plus_battery
adfarth Jul 3, 2025
875cbd2
Update electric_storage.jl
adfarth Jul 3, 2025
e689e0f
try multi_node
adfarth Jul 3, 2025
adc7828
Merge branch 'develop' into bess-export
adfarth Jul 3, 2025
6336466
t to b
adfarth Jul 3, 2025
ee1a4f1
Update electric_storage.jl
adfarth Jul 7, 2025
3adec5b
Merge branch 'fixed-bess-soc' into bess-export
adfarth Jul 7, 2025
e1a504d
updt soc_init and add tol input
adfarth Jul 9, 2025
dfe1ed0
output name
adfarth Jul 17, 2025
809f079
initial add of grid cost
adfarth Aug 6, 2025
e8793c7
updt documentation
adfarth Aug 6, 2025
027fb3a
Update utils.jl
adfarth Aug 21, 2025
8c996cd
Merge branch 'develop' into bess-export
adfarth Sep 5, 2025
f5f5d21
Merge branch 'develop' into bess-export
adfarth Nov 17, 2025
07e8a3f
Merge branch 'develop' into bess-export
lixiangk1 Mar 12, 2026
d89dda1
Merge branch 'develop' into bess-export
adfarth May 5, 2026
a974c66
rm grid cost
adfarth May 5, 2026
5557084
rm grid cost
adfarth May 5, 2026
e19b304
Merge branch 'develop' into bess-export
adfarth Jun 2, 2026
5062cea
fix NEM issue
adfarth Jun 2, 2026
1ffa3de
add BESS export to transmission limit
adfarth Jun 8, 2026
3e5552e
add warning about onsite RE
adfarth Jun 8, 2026
f982862
rmv net load calc
adfarth Jun 9, 2026
1280413
Update load_balance.jl
adfarth Jun 9, 2026
d2c346b
fix WHL max_ben
adfarth Jun 9, 2026
b099bb3
Update electric_utility_constraints.jl
adfarth Jun 9, 2026
9e1d300
add tests
adfarth Jun 9, 2026
96df208
comment out development_tests
adfarth Jun 10, 2026
576d16b
Merge branch 'develop' into bess-export
adfarth Jul 7, 2026
88a0f43
Update electric_utility_constraints.jl
adfarth Jul 9, 2026
63601f0
rmv ununsed units
adfarth Jul 9, 2026
8cb3e92
Update electric_tariff.jl
adfarth Jul 10, 2026
c5a452c
Update constraints.jl
adfarth Jul 10, 2026
3e53764
Update structs.jl
adfarth Jul 10, 2026
d6014ca
Update electric_utility_constraints.jl
adfarth Jul 10, 2026
9daa25d
update cst test values
adfarth Jul 16, 2026
c9305d4
Update electric_storage.jl
adfarth Jul 16, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,13 @@ Classify the change according to the following categories:
### Deprecated
### Removed

## bess-export
### Added
- Allow **ElectricStorage** to export to the grid with input options for grid export: `can_net_meter`, `can_wholesale`, `can_export_beyond_nem_limit`and associated decision variable **dvStorageToGrid**
- Add result **ElectricStorage** `storage_to_grid_series_kw`
### Fixed
- Bug in max benefit constraint for WHL export; bug allowing for both WHL and NEM to be used

## v0.59.3
### Changed
- Updated Julia environment variable names from "NREL_DEVELOPER_API_KEY" and "NREL_DEVELOPER_EMAIL" to "NLR_DEVELOPER_API_KEY" and "NLR_DEVELOPER_EMAIL"
Expand Down
2 changes: 1 addition & 1 deletion docs/src/developer/inputs.md
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ end
The set maps are best explained with an example. The `techs_by_exportbin` map uses each technology'sattributes (eg. `PV`) to map each technology to which export bins that technology can access. The export bins include:
1. `:NEM` (Net Energy Metering)
2. `:WHL` (Wholesale)
3. `:EXC` (Excess, beyond NEM))
3. `:EXC` (Excess, beyond NEM)
The bins that a technology can access are determined by the technologies attributes `can_net_meter`, `can_wholesale`, and `can_export_beyond_nem_limit`. So if `PV.can_net_meter = true`, `Wind.can_net_meter = true` and all the other attributes are `false` then the `techs_by_exportbin` will only have one non-empty key:
```julia
techs_by_exportbin = Dict(
Expand Down
123 changes: 89 additions & 34 deletions src/constraints/electric_utility_constraints.jl

Large diffs are not rendered by default.

29 changes: 20 additions & 9 deletions src/constraints/emissions_constraints.jl
Original file line number Diff line number Diff line change
Expand Up @@ -120,24 +120,35 @@ function calc_yr1_emissions_offset_from_elec_exports(m, p)
return 0.0, 0.0, 0.0, 0.0
end
yr1_emissions_offset_from_elec_exports_lbs_CO2 = @expression(m, p.hours_per_time_step *
sum(m[:dvProductionToGrid][t,u,ts] * (p.s.electric_utility.emissions_factor_series_lb_CO2_per_kwh[ts])
for t in p.techs.elec, ts in p.time_steps, u in p.export_bins_by_tech[t])
sum( p.s.electric_utility.emissions_factor_series_lb_CO2_per_kwh[ts] * (
sum(m[:dvProductionToGrid][t,u,ts] for t in p.techs.elec, u in p.export_bins_by_tech[t])
+ sum(m[:dvStorageToGrid][b, u, ts] for b in p.s.storage.types.elec, u in p.export_bins_by_storage[b])
) for ts in p.time_steps
)
)
# if battery ends up being able to discharge to grid, need to incorporate here- might require complex tracking of what's charging battery

yr1_emissions_offset_from_elec_exports_lbs_NOx = @expression(m, p.hours_per_time_step *
sum(m[:dvProductionToGrid][t,u,ts] * (p.s.electric_utility.emissions_factor_series_lb_NOx_per_kwh[ts])
for t in p.techs.elec, ts in p.time_steps, u in p.export_bins_by_tech[t])
sum( p.s.electric_utility.emissions_factor_series_lb_NOx_per_kwh[ts] * (
sum(m[:dvProductionToGrid][t,u,ts] for t in p.techs.elec, u in p.export_bins_by_tech[t])
+ sum(m[:dvStorageToGrid][b, u, ts] for b in p.s.storage.types.elec, u in p.export_bins_by_storage[b])
) for ts in p.time_steps
)
)

yr1_emissions_offset_from_elec_exports_lbs_SO2 = @expression(m, p.hours_per_time_step *
sum(m[:dvProductionToGrid][t,u,ts] * (p.s.electric_utility.emissions_factor_series_lb_SO2_per_kwh[ts])
for t in p.techs.elec, ts in p.time_steps, u in p.export_bins_by_tech[t])
sum( p.s.electric_utility.emissions_factor_series_lb_SO2_per_kwh[ts] * (
sum(m[:dvProductionToGrid][t,u,ts] for t in p.techs.elec, u in p.export_bins_by_tech[t])
+ sum(m[:dvStorageToGrid][b, u, ts] for b in p.s.storage.types.elec, u in p.export_bins_by_storage[b])
) for ts in p.time_steps
)
)

yr1_emissions_offset_from_elec_exports_lbs_PM25 = @expression(m, p.hours_per_time_step *
sum(m[:dvProductionToGrid][t,u,ts] * (p.s.electric_utility.emissions_factor_series_lb_PM25_per_kwh[ts])
for t in p.techs.elec, ts in p.time_steps, u in p.export_bins_by_tech[t])
sum( p.s.electric_utility.emissions_factor_series_lb_PM25_per_kwh[ts] * (
sum(m[:dvProductionToGrid][t,u,ts] for t in p.techs.elec, u in p.export_bins_by_tech[t])
+ sum(m[:dvStorageToGrid][b, u, ts] for b in p.s.storage.types.elec, u in p.export_bins_by_storage[b])
) for ts in p.time_steps
)
)

return yr1_emissions_offset_from_elec_exports_lbs_CO2,
Expand Down
2 changes: 1 addition & 1 deletion src/constraints/load_balance.jl
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ function add_elec_load_balance_constraints(m, p; _n="")
sum(sum(m[Symbol("dvProductionToStorage"*_n)][b, t, ts] for b in p.s.storage.types.elec)
+ sum(m[Symbol("dvProductionToGrid"*_n)][t, u, ts] for u in p.export_bins_by_tech[t])
+ m[Symbol("dvCurtail"*_n)][t, ts] for t in p.techs.elec)
+ sum(m[Symbol("dvStorageToGrid"*_n)][b, u, ts] for b in p.s.storage.types.elec, u in p.export_bins_by_storage[b])
+ sum(m[Symbol("dvGridToStorage"*_n)][b, ts] for b in p.s.storage.types.elec)
+ sum(m[Symbol("dvCoolingProduction"*_n)][t, ts] / p.cooling_cop[t][ts] for t in setdiff(p.techs.cooling,p.techs.ghp))
+ sum(m[Symbol("dvHeatingProduction"*_n)][t, q, ts] / p.heating_cop[t][ts] for q in p.heating_loads, t in p.techs.electric_heater)
Expand Down Expand Up @@ -96,7 +97,6 @@ function add_production_constraints(m, p; _n="")
<=
p.production_factor[t, ts] * p.levelization_factor[t] * m[Symbol("dvRatedProduction"*_n)][t, ts]
)

end


Expand Down
33 changes: 20 additions & 13 deletions src/constraints/renewable_energy_constraints.jl
Original file line number Diff line number Diff line change
Expand Up @@ -58,36 +58,43 @@ function add_re_elec_calcs(m,p)
@warn("The presence of a steam turbine may cause the renewable energy fraction to be inaccurate.")
end

# Note: when we add capability for battery to discharge to grid, need to make sure only RE that is being consumed
# onsite is counted so battery doesn't become a back door for RE to grid.
m[:AnnualOnsiteREEleckWh] = @expression(m, p.hours_per_time_step * (
#total RE elec generation, excl steam turbine
sum(p.production_factor[t,ts] * p.levelization_factor[t] * m[:dvRatedProduction][t,ts] *
p.tech_renewable_energy_fraction[t] for t in setdiff(p.techs.elec, p.techs.steam_turbine), ts in p.time_steps
) - #total RE elec generation, excl steam turbine
sum(m[:dvProductionToStorage][b,t,ts]*p.tech_renewable_energy_fraction[t]*(
)
#minus battery efficiency losses
- sum(m[:dvProductionToStorage][b,t,ts]*p.tech_renewable_energy_fraction[t]*(
1-p.s.storage.attr[b].charge_efficiency*p.s.storage.attr[b].discharge_efficiency)
for t in setdiff(p.techs.elec, p.techs.steam_turbine), b in p.s.storage.types.elec, ts in p.time_steps
) - #minus battery efficiency losses
sum(m[:dvCurtail][t,ts] * p.tech_renewable_energy_fraction[t]
)
# minus curtailment
- sum(m[:dvCurtail][t,ts] * p.tech_renewable_energy_fraction[t]
for t in setdiff(p.techs.elec, p.techs.steam_turbine), ts in p.time_steps
) - # minus curtailment
(1 - p.s.site.include_exported_renewable_electricity_in_total) *
)
# minus exported RE, if RE accounting method = 0.
- (1 - p.s.site.include_exported_renewable_electricity_in_total) *
sum(m[:dvProductionToGrid][t,u,ts]*p.tech_renewable_energy_fraction[t]
for t in setdiff(p.techs.elec, p.techs.steam_turbine), u in p.export_bins_by_tech[t], ts in p.time_steps
) # minus exported RE, if RE accounting method = 0.
)
# TODO: battery can now discharge to the grid, but this export is not yet accounted for in the RE calculation.
# This is only relevant if include_exported_renewable_electricity_in_total = false. If false, the
# battery could become a "back door" for export of RE to the grid since it's not subtracted here. Will require tracking of onsite vs grid RE in BESS.
)
Comment thread
adfarth marked this conversation as resolved.
# + SteamTurbineAnnualREEleckWh # SteamTurbine RE Elec, already adjusted for p.hours_per_time_step
)

# Note: when we add capability for battery to discharge to grid, need to subtract out *grid RE* discharged from battery
# back to grid so that loop doesn't become a back door for increasing RE. This will require some careful thought!
m[:AnnualGridREEleckWh] = @expression(m, p.hours_per_time_step * (
# renewable energy from grid
sum(m[:dvGridPurchase][ts, tier] * p.s.electric_utility.renewable_energy_fraction_series[ts]
for ts in p.time_steps, tier in 1:p.s.electric_tariff.n_energy_tiers) # renewable energy from grid
for ts in p.time_steps, tier in 1:p.s.electric_tariff.n_energy_tiers)
# minus battery efficiency losses from grid charging storage (assumes all that is charged is discharged)
- sum(m[:dvGridToStorage][b, ts] * p.s.electric_utility.renewable_energy_fraction_series[ts] *
(1 - p.s.storage.attr[b].charge_efficiency * p.s.storage.attr[b].discharge_efficiency)
for ts in p.time_steps, b in p.s.storage.types.elec
) # minus battery efficiency losses from grid charging storage (assumes all that is charged is discharged)
)
# TODO: battery can now discharge to the grid, but this export is not yet accounted for in the RE calculation.
# Need to subtract out *grid RE* discharged from battery back to grid so that loop doesn't become a back door for increasing RE. Will require tracking of onsite vs grid RE in BESS.
)
)

Expand Down
14 changes: 11 additions & 3 deletions src/constraints/storage_constraints.jl
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,6 @@ function add_storage_size_constraints(m, p, b; _n="")
)
end


end


Expand Down Expand Up @@ -74,12 +73,21 @@ end

function add_elec_storage_dispatch_constraints(m, p, b; _n="")

# Constraint (4g)-1: state-of-charge for electrical storage - with grid
# Constraint (4d): Storage export must be less than total storage dispatch
if !isempty(p.export_bins_by_storage[b])
@constraint(m, [ts in p.time_steps_with_grid],
sum(m[Symbol("dvStorageToGrid"*_n)][b, u, ts] for u in p.export_bins_by_storage[b])
<=
m[Symbol("dvDischargeFromStorage"*_n)][b, ts]
)
end

# Constraint (4g)-1: state-of-charge for electrical storage - with grid
@constraint(m, [ts in p.time_steps_with_grid],
m[Symbol("dvStoredEnergy"*_n)][b, ts] == m[Symbol("dvStoredEnergy"*_n)][b, ts-1] + p.hours_per_time_step * (
sum(p.s.storage.attr[b].charge_efficiency * m[Symbol("dvProductionToStorage"*_n)][b, t, ts] for t in p.techs.elec)
+ p.s.storage.attr[b].grid_charge_efficiency * m[Symbol("dvGridToStorage"*_n)][b, ts]
- m[Symbol("dvDischargeFromStorage"*_n)][b,ts] / p.s.storage.attr[b].discharge_efficiency
- (m[Symbol("dvDischargeFromStorage"*_n)][b,ts] / p.s.storage.attr[b].discharge_efficiency)
)
)
# Constraint (4g)-2: state-of-charge for electrical storage - no grid
Expand Down
4 changes: 4 additions & 0 deletions src/core/bau_inputs.jl
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,8 @@ function BAUInputs(p::REoptInputs)
# export related inputs
techs_by_exportbin = Dict{Symbol, AbstractArray}(k => [] for k in p.s.electric_tariff.export_bins)
export_bins_by_tech = Dict{String, Array{Symbol, 1}}()
storage_by_exportbin = Dict{Symbol, AbstractArray}(k => [] for k in p.s.electric_tariff.export_bins) # Empty for BAU since cannot model "existing storage"
export_bins_by_storage = Dict{String, Array{Symbol, 1}}()

# REoptInputs indexed on techs.segmented
n_segs_by_tech = Dict{String, Int}()
Expand Down Expand Up @@ -197,6 +199,8 @@ function BAUInputs(p::REoptInputs)
p.ratchets,
techs_by_exportbin,
export_bins_by_tech,
storage_by_exportbin,
export_bins_by_storage,
n_segs_by_tech,
seg_min_size,
seg_max_size,
Expand Down
9 changes: 4 additions & 5 deletions src/core/electric_utility.jl
Original file line number Diff line number Diff line change
Expand Up @@ -138,10 +138,9 @@ struct ElectricUtility
outage_time_steps::Union{Nothing, UnitRange}
scenarios::Union{Nothing, UnitRange}
net_metering_limit_kw::Real
interconnection_limit_kw::Real
interconnection_limit_kw::Real
transmission_limit_kw::Real


function ElectricUtility(;

# Fields from other models
Expand Down Expand Up @@ -198,9 +197,9 @@ struct ElectricUtility

### Grid Clean Energy Fraction Inputs ###
cambium_cef_metric::String = "cef_load", # Options = ["cef_load", "cef_gen"] # cef_load is the fraction of generation that is clean, for the generation that is allocated to a region’s end-use load; cef_gen is the fraction of generation that is clean within a region
renewable_energy_fraction_series::Union{Real,Array{<:Real,1}} = Float64[], # Fraction of energy supplied by the grid that is renewable. Can be scalar or timeseries (aligned with time_steps_per_hour)
)

renewable_energy_fraction_series::Union{Real,Array{<:Real,1}} = Float64[] # Fraction of energy supplied by the grid that is renewable. Can be scalar or timeseries (aligned with time_steps_per_hour)
)
is_MPC = isnothing(latitude) || isnothing(longitude)
cambium_region = "NA - Cambium data not used" # will be overwritten if Cambium is used

Expand Down
26 changes: 26 additions & 0 deletions src/core/energy_storage/electric_storage.jl
Original file line number Diff line number Diff line change
Expand Up @@ -176,6 +176,9 @@ end
soc_min_applies_during_outages::Bool = false
soc_init_fraction::Float64 = off_grid_flag ? 1.0 : 0.5
can_grid_charge::Bool = off_grid_flag ? false : true
can_net_meter::Bool = false
can_wholesale::Bool = false
can_export_beyond_nem_limit::Bool = false
installed_cost_per_kw::Real = 968.0 # Cost of power components (e.g., inverter and BOS)
installed_cost_per_kwh::Real = 253.0 # Cost of energy components (e.g., battery pack)
installed_cost_constant::Real = 222115.0 # "+c" constant cost that is added to total ElectricStorage installed costs if a battery is included. Accounts for costs not expected to scale with power or energy capacity.
Expand Down Expand Up @@ -219,6 +222,9 @@ Base.@kwdef struct ElectricStorageDefaults
soc_min_applies_during_outages::Bool = false
soc_init_fraction::Float64 = off_grid_flag ? 1.0 : 0.5
can_grid_charge::Bool = off_grid_flag ? false : true
can_net_meter::Bool = false
can_wholesale::Bool = false
can_export_beyond_nem_limit::Bool = false
installed_cost_per_kw::Real = 968.0
installed_cost_per_kwh::Real = 253.0
installed_cost_constant::Real = 222115.0
Expand Down Expand Up @@ -267,6 +273,9 @@ struct ElectricStorage <: AbstractElectricStorage
soc_min_applies_during_outages::Bool
soc_init_fraction::Float64
can_grid_charge::Bool
can_net_meter::Bool
can_wholesale::Bool
can_export_beyond_nem_limit::Bool
installed_cost_per_kw::Real
installed_cost_per_kwh::Real
installed_cost_constant::Real
Expand Down Expand Up @@ -311,6 +320,20 @@ struct ElectricStorage <: AbstractElectricStorage
@warn "Battery replacement costs (per_kwh) will not be considered because battery_replacement_year is greater than or equal to analysis_years."
end

if !s.include_exported_renewable_electricity_in_total && (stor.can_net_meter || stor.can_wholesale)
@warn "include_exported_renewable_electricity_in_total = false, but ElectricStorage can_net_meter or can_wholesale is true. REopt's calculation of onsite renewable electricity does not currently accurately account for exported renewable electricity via the battery and will thus overestimate onsite renewable electricity."
end

can_net_meter = stor.can_net_meter
can_wholesale = stor.can_wholesale
can_export_beyond_nem_limit = stor.can_export_beyond_nem_limit
if stor.off_grid_flag && (can_net_meter || can_wholesale || can_export_beyond_nem_limit)
@warn "Setting ElectricStorage can_net_meter, can_wholesale, and can_export_beyond_nem_limit to False because `off_grid_flag` is true."
can_net_meter = false
can_wholesale = false
can_export_beyond_nem_limit = false
end

if stor.min_duration_hours > stor.max_duration_hours
throw(@error("ElectricStorage min_duration_hours must be less than max_duration_hours."))
end
Expand Down Expand Up @@ -422,6 +445,9 @@ struct ElectricStorage <: AbstractElectricStorage
stor.soc_min_applies_during_outages,
soc_init_fraction,
stor.can_grid_charge,
can_net_meter,
can_wholesale,
can_export_beyond_nem_limit,
stor.installed_cost_per_kw,
stor.installed_cost_per_kwh,
stor.installed_cost_constant,
Expand Down
4 changes: 2 additions & 2 deletions src/core/generator.jl
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@
sells_energy_back_to_grid::Bool = false,
can_net_meter::Bool = false,
can_wholesale::Bool = false,
can_export_beyond_nem_limit = false,
can_export_beyond_nem_limit::Bool = false,
can_curtail::Bool = false,
macrs_option_years::Int = 0,
macrs_bonus_fraction::Real = 0.0,
Expand Down Expand Up @@ -116,7 +116,7 @@ struct Generator <: AbstractGenerator
sells_energy_back_to_grid::Bool = false,
can_net_meter::Bool = false,
can_wholesale::Bool = false,
can_export_beyond_nem_limit = false,
can_export_beyond_nem_limit::Bool = false,
can_curtail::Bool = false,
macrs_option_years::Int = 0,
macrs_bonus_fraction::Real = 0.0,
Expand Down
6 changes: 5 additions & 1 deletion src/core/reopt.jl
Original file line number Diff line number Diff line change
Expand Up @@ -199,6 +199,9 @@ function build_reopt!(m::JuMP.AbstractModel, p::REoptInputs)
if !isempty(p.s.electric_tariff.export_bins)
for t in p.techs.elec, u in p.export_bins_by_tech[t]
fix(m[:dvProductionToGrid][t, u, ts], 0.0, force=true)
end
for b in p.s.storage.types.elec, u in p.export_bins_by_storage[b]
fix(m[:dvStorageToGrid][b, u, ts], 0.0, force=true)
end
end
end
Expand Down Expand Up @@ -500,7 +503,7 @@ function build_reopt!(m::JuMP.AbstractModel, p::REoptInputs)
initial_capex_no_incentives(m, p)
if !isnothing(p.s.financial.min_initial_capital_costs_before_incentives) || !isnothing(p.s.financial.max_initial_capital_costs_before_incentives)
add_capex_constraints(m, p)
end
end

################################# Objective Function ########################################
@expression(m, Costs,
Expand Down Expand Up @@ -682,6 +685,7 @@ function add_variables!(m::JuMP.AbstractModel, p::REoptInputs)

if !isempty(p.s.electric_tariff.export_bins)
@variable(m, dvProductionToGrid[p.techs.elec, p.s.electric_tariff.export_bins, p.time_steps] >= 0)
@variable(m, dvStorageToGrid[p.s.storage.types.elec, p.s.electric_tariff.export_bins, p.time_steps] >= 0)
end

if !(p.s.electric_utility.allow_simultaneous_export_import) & !isempty(p.s.electric_tariff.export_bins)
Expand Down
Loading
Loading