odys.domain.validation¶
System-level validation rules. They run automatically when an EnergySystem is created, and check that every profile references an entity of the system, every load and market has its required profile in every scenario, every profile fits the horizon, and supply can meet demand. The rules treat entities alike through their capability queries (max_supply, min_demand, max_energy_supply, validate_horizon), so a new asset type only needs to override them and be listed as supported. Rules about a single entity or profile run when that object is built.
Energy system input validation.
This module holds the rules that span entities and scenarios. Rules about a
single entity or profile live on that object and run when it is built. The
rules here treat every entity alike through its capability queries
(max_supply, min_demand, max_energy_supply, validate_horizon) and
every profile through its type's entity_types and required flags and its
number_of_steps and operating_values. A new
asset type is covered by overriding those queries (that the optimizer models
it is checked against its formulations, in odys.optimization.formulations);
a new profile type by adding it to AnyProfile and PROFILE_TYPES in
profiles.py. Conditions are checked through their own queries
(validate_horizon, validate_operating_conditions) and required per asset
through each initial condition type's required_for; a new initial condition
type is added to INITIAL_CONDITION_TYPES in conditions.py.
validate_conditions_fit_the_run(condition_set, scenarios, horizon)
¶
Validate every condition against the horizon and what its asset faces in each scenario.
Conditions are reached through their validate_horizon and
validate_operating_conditions queries, like entities through theirs.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
condition_set
|
ConditionSet
|
The initial and final conditions of the run. |
required |
scenarios
|
Sequence[Scenario]
|
The scenarios of the problem, whose profiles have one value per timestep. |
required |
horizon
|
Horizon
|
The time grid of the optimization. |
required |
Raises:
| Type | Description |
|---|---|
OdysValidationError
|
If a condition does not fit the horizon or cannot be met in a scenario. |
Source code in src/odys/domain/validation.py
164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 | |
validate_conditions_reference_system_assets(condition_set, portfolio)
¶
Validate that each condition references an asset of the energy system.
A condition whose asset is missing from the portfolio, or differs from the portfolio's asset of that name, would describe an asset that is not being optimized.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
condition_set
|
ConditionSet
|
The initial and final conditions of the run. |
required |
portfolio
|
AssetPortfolio
|
The asset portfolio. |
required |
Raises:
| Type | Description |
|---|---|
OdysValidationError
|
If a condition's asset is not the portfolio's asset of that name. |
Source code in src/odys/domain/validation.py
113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 | |
validate_energy_system_inputs(portfolio, scenario_set, markets, horizon, condition_set)
¶
Run all cross-domain validation checks on the energy system.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
portfolio
|
AssetPortfolio
|
The asset portfolio to validate against. |
required |
scenario_set
|
ScenarioSet
|
The scenarios of the problem. |
required |
markets
|
Sequence[EnergyMarket]
|
Normalized sequence of energy markets. |
required |
horizon
|
Horizon
|
The time grid of the optimization. |
required |
condition_set
|
ConditionSet
|
The initial and final conditions of the run. |
required |
Raises:
| Type | Description |
|---|---|
OdysValidationError
|
If any validation check fails. |
Source code in src/odys/domain/validation.py
30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 | |
validate_enough_energy_to_meet_demand(scenario, entities, horizon)
¶
Validate that the energy available over the horizon can meet the minimum energy demand.
A coarser, horizon-level counterpart to validate_enough_power_to_meet_demand:
a system can pass every per-timestep power check and still be infeasible
over the horizon, for example when a battery is too small for a long
horizon. Every entity's max_energy_supply is an optimistic bound
(storage is emptied once, generators run at their available capacity
throughout), so this check can miss infeasibility but does not raise
false positives.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
scenario
|
Scenario
|
Scenario to check. |
required |
entities
|
Sequence[EnergyEntity]
|
All assets and markets of the energy system. |
required |
horizon
|
Horizon
|
The time grid of the optimization. |
required |
Raises:
| Type | Description |
|---|---|
OdysValidationError
|
If total minimum energy demand exceeds total available energy. |
Source code in src/odys/domain/validation.py
304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 | |
validate_enough_power_to_meet_demand(scenario, entities, horizon)
¶
Validate that the maximum supply can meet the minimum demand at every timestep.
Sums, per timestep, every entity's max_supply (generation, storage and
EV discharge, market volume) and every entity's min_demand (fixed loads,
flexible loads after their maximum decrease).
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
scenario
|
Scenario
|
Scenario to check. |
required |
entities
|
Sequence[EnergyEntity]
|
All assets and markets of the energy system. |
required |
horizon
|
Horizon
|
The time grid of the optimization. |
required |
Raises:
| Type | Description |
|---|---|
OdysValidationError
|
If the minimum demand exceeds the maximum supply at any timestep. |
Source code in src/odys/domain/validation.py
267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 | |
validate_has_load_or_market(scenario, markets)
¶
Validate that the scenario has a load to serve or a market to trade in.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
scenario
|
Scenario
|
Scenario to check. |
required |
markets
|
Sequence[EnergyMarket]
|
The energy markets. |
required |
Raises:
| Type | Description |
|---|---|
OdysValidationError
|
If the scenario has no load profile and there is no market. |
Source code in src/odys/domain/validation.py
245 246 247 248 249 250 251 252 253 254 255 256 257 258 | |
validate_profile_lengths(scenarios, horizon)
¶
Validate that every profile has one value per timestep.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
scenarios
|
Sequence[Scenario]
|
Scenarios whose profiles to check. |
required |
horizon
|
Horizon
|
The time grid of the optimization. |
required |
Raises:
| Type | Description |
|---|---|
OdysValidationError
|
If a profile's length differs from the number of timesteps. |
Source code in src/odys/domain/validation.py
224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 | |
validate_profiles_reference_system_entities(scenarios, portfolio, markets)
¶
Validate that each profile references an entity of the energy system.
Assets and markets are looked up separately, since a market may share a name with an asset. A profile whose entity is missing from the system, or differs from the system's entity of that name (for example a copy with other parameters), would describe an entity that is not being optimized.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
scenarios
|
Sequence[Scenario]
|
Scenarios whose profiles to check. |
required |
portfolio
|
AssetPortfolio
|
The asset portfolio. |
required |
markets
|
Sequence[EnergyMarket]
|
The energy markets. |
required |
Raises:
| Type | Description |
|---|---|
OdysValidationError
|
If a profile's entity is not the system's entity of that name. |
Source code in src/odys/domain/validation.py
70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 | |
validate_required_initial_conditions_present(condition_set, portfolio)
¶
Validate that every asset whose results depend on its starting state has an initial condition.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
condition_set
|
ConditionSet
|
The initial and final conditions of the run. |
required |
portfolio
|
AssetPortfolio
|
The asset portfolio. |
required |
Raises:
| Type | Description |
|---|---|
OdysValidationError
|
If an asset lacks an initial condition it requires. |
Source code in src/odys/domain/validation.py
143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 | |
validate_required_profiles_present(scenarios, entities)
¶
Validate that every scenario has each required profile for every entity that needs one.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
scenarios
|
Sequence[Scenario]
|
Scenarios to check. |
required |
entities
|
Sequence[EnergyEntity]
|
All assets and markets of the energy system. |
required |
Raises:
| Type | Description |
|---|---|
OdysValidationError
|
If a scenario lacks a required profile. |
Source code in src/odys/domain/validation.py
193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 | |