From d04e3844a0e5391a933546e128289c89b08e3363 Mon Sep 17 00:00:00 2001 From: Rob Hammond <13874373+RHammond2@users.noreply.github.com> Date: Tue, 7 May 2024 16:03:46 -0700 Subject: [PATCH] Bug fix: Duplicated array design result (#8) * update pinned versions and waves version * fix typos * add in workflow diagrams * add a changelog * fix bug causing ~duplicated array installation costs --- CHANGELOG.md | 15 +++++++++ docs/diagrams/input_flow.mmd | 42 +++++++++++++++++++++++++ docs/diagrams/input_flow.svg | 1 + docs/diagrams/results_flow.mmd | 57 ++++++++++++++++++++++++++++++++++ docs/diagrams/results_flow.svg | 1 + docs/user_guide.md | 12 +++++++ pyproject.toml | 13 +++----- waves/__init__.py | 2 +- waves/project.py | 7 +++-- 9 files changed, 138 insertions(+), 12 deletions(-) create mode 100644 CHANGELOG.md create mode 100644 docs/diagrams/input_flow.mmd create mode 100644 docs/diagrams/input_flow.svg create mode 100644 docs/diagrams/results_flow.mmd create mode 100644 docs/diagrams/results_flow.svg diff --git a/CHANGELOG.md b/CHANGELOG.md new file mode 100644 index 0000000..b0b61bb --- /dev/null +++ b/CHANGELOG.md @@ -0,0 +1,15 @@ +# CHANGELOG + +## Unreleased + +- A bug was fixed where the array system installation costs were nearly doubled when compared + to a direct ORBIT run. This was the result of a duplicated design result when calling both + `Project.connect_orbit_cable_lengths()` and `Project.orbit.run()`. + +## 0.5.2 (9 April 2024) + +- Pins FLORIS to v3.6 to avoid workarounds for previous versions, and to avoid issues with + adopting v4. +- Updates WOMBAT to 0.9.3 to account for the latest bug fixes. +- Fixes minor typos. +- Adds in mermaid markdown workflow diagrams for the documentation. diff --git a/docs/diagrams/input_flow.mmd b/docs/diagrams/input_flow.mmd new file mode 100644 index 0000000..a5f85bc --- /dev/null +++ b/docs/diagrams/input_flow.mmd @@ -0,0 +1,42 @@ +flowchart TD + + subgraph Configuration + + ConfigA[orbit_config] + ConfigB[wombat_config] + ConfigC[floris_config] + ConfigD[Additional\nConfigurations] + ConfigE[fa:fa-code fa:fa-file WAVES Configuration] + + ConfigE ---|fa:fa-file file name or \n fa:fa-code settings| ConfigB + ConfigE ---|fa:fa-file file name or \n fa:fa-code settings| ConfigA + ConfigE ---|fa:fa-file file name or \n fa:fa-code settings| ConfigC + ConfigE ---|fa:fa-code settings| ConfigD + + ConfigD --- ConfigF(Shared ORBIT settings and \n ORBIT tie-ins for weather) + ConfigD --- ConfigG(FLORIS tie-ins for weather) + ConfigD --- ConfigH(Detailed CapEx breakdowns) + ConfigD --- ConfigI(High level financial variables) + ConfigD --- ConfigJ(Indicators to connect any \n of ORBIT or FLORIS \n to WOMBAT configurations) + end + + subgraph Initialization + InitA(Create ORBIT ProjectManager) + InitB(Create WOMBAT Simulation) + InitC(Create FLORIS FlorisInterface) + InitD[Connect layouts\nand weather profiles] + InitE[Project] + InitF[Project.orbit --> ProjectManager] + InitG[Project.wombat --> Simulation] + InitH[Project.floris --> FlorisInterface] + + InitA --> InitD + InitB --> InitD + InitC --> InitD + InitD --> InitE + InitE --- InitF + InitE --- InitG + InitE --- InitH + end + + Configuration --> Initialization diff --git a/docs/diagrams/input_flow.svg b/docs/diagrams/input_flow.svg new file mode 100644 index 0000000..bf42c66 --- /dev/null +++ b/docs/diagrams/input_flow.svg @@ -0,0 +1 @@ +
Initialization
Create ORBIT ProjectManager
Connect layouts
and weather profiles
Create WOMBAT Simulation
Create FLORIS FlorisInterface
Project
Project.orbit --> ProjectManager
Project.wombat --> Simulation
Project.floris --> FlorisInterface
Configuration
file name or
settings
file name or
settings
file name or
settings
settings
orbit_config
WAVES Configuration
wombat_config
floris_config
Additional
Configurations
Shared ORBIT settings and
ORBIT tie-ins for weather
FLORIS tie-ins for weather
Detailed CapEx breakdowns
High level financial variables
Indicators to connect any
of ORBIT or FLORIS
to WOMBAT configurations
diff --git a/docs/diagrams/results_flow.mmd b/docs/diagrams/results_flow.mmd new file mode 100644 index 0000000..4d10358 --- /dev/null +++ b/docs/diagrams/results_flow.mmd @@ -0,0 +1,57 @@ +flowchart LR + + A("Project.run()") + A --> B("Project.orbit.run()") + A --> C("Project.wombat.run()") + A --> D("Project.run_floris()") + + B --> ORBIT + C --> WOMBAT + D --> FLORIS + + + subgraph Independent + + NT[n_turbines] + NOSS[n_substations] + TurbRat[turbine_rating] + + subgraph ORBIT + ArrayLen[total_array_length] + ExpLen[total_export_length] + CapEx[capex_breakdown] + end + + subgraph WOMBAT + Avail[availability] + OpEx[opex] + end + + subgraph FLORIS + TurbPotential[turbine_potential_energy] + ProjPotential[project_potential_energy] + TurbProd[turbine_production_energy] + ProjProd[project_production_energy] + end + + end + + subgraph Combined + EnergyPotential[energy_potential] --> EnergyLoss[energy_losses] + EnergyProd[energy_production] --> EnergyLoss + EnergyPotential --> CF[capacity_factor] + EnergyProd --> CF + EnergyProd --> Revenue[revenue] + Revenue --> CashFlow[cash_flow] + CashFlow --> NPV[npv] + CashFlow --> IRR[irr] + CashFlow --> LCOE[lcoe] + + TurbPotential --> EnergyPotential + ProjPotential --> EnergyPotential + TurbProd --> EnergyProd + ProjProd --> EnergyProd + Avail --> EnergyProd + OpEx --> CashFlow + CapEx --> CashFlow + end diff --git a/docs/diagrams/results_flow.svg b/docs/diagrams/results_flow.svg new file mode 100644 index 0000000..1c76efa --- /dev/null +++ b/docs/diagrams/results_flow.svg @@ -0,0 +1 @@ +
Combined
Independent
ORBIT
WOMBAT
FLORIS
energy_losses
energy_potential
energy_production
capacity_factor
revenue
cash_flow
npv
irr
lcoe
n_turbines
n_substations
turbine_rating
turbine_potential_energy
project_potential_energy
turbine_production_energy
project_production_energy
availability
opex
total_array_length
total_export_length
capex_breakdown
Project.run()
Project.orbit.run()
Project.wombat.run()
Project.run_floris()
diff --git a/docs/user_guide.md b/docs/user_guide.md index 84d1ba3..10e0bae 100644 --- a/docs/user_guide.md +++ b/docs/user_guide.md @@ -120,6 +120,12 @@ The following method is run on intialization when ``Project.connect_floris_to_la :noindex: ``` +Visually, this looks like the following workflow: + +```{image} diagrams/input_flow.svg +:align: center +``` + ### Updating Configurations Sometimes, additional configurations may need to be connected prior to running an analysis. For @@ -199,6 +205,12 @@ For the following set of methods, users only need to create a ``Project`` object ## Results +Visually, the following is a general flow of operations for combining each model's outputs: + +```{image} diagrams/results_flow.svg +:align: center +``` + To quickly produce any of the high-level outputs to a single `DataFrame`, the below method can be used in place of individually calculating each metric and combining into a report. Additionally, users can refer to the [COWER 2022 example](example_cower_2022:results) for the reported results, diff --git a/pyproject.toml b/pyproject.toml index 831feca..33ade6f 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -2,9 +2,6 @@ requires = ["setuptools", "setuptools-scm"] build-backend = "setuptools.build_meta" -[metadata] -version = "attr: waves.__version__" - [project] name = "WAVES" dynamic = ["version"] @@ -19,10 +16,10 @@ dependencies = [ "pyyaml", "matplotlib>=3.6", "numpy-financial>=1.0.0", - "floris>=3.3", - "wombat>=0.9.1", + "floris==3.6", # TODO: upgrade to FLORIS v4 + "wombat>=0.9.3", "orbit-nrel>=1.0.8", - "typer[all]", + "typer>=0.12.3", ] keywords = [ "python3", @@ -54,9 +51,6 @@ classifiers = [ "Typing :: Typed", ] -[console_scripts] -waves = "waves:__main__" - [project.scripts] waves = "waves.__main__:app" @@ -87,6 +81,7 @@ examples=[ "jupyterlab", "jupyterlab-myst", ] +all = ["waves[dev,docs,examples]"] [tool.setuptools] include-package-data = true diff --git a/waves/__init__.py b/waves/__init__.py index ff4b8b1..1747e9c 100644 --- a/waves/__init__.py +++ b/waves/__init__.py @@ -3,4 +3,4 @@ from waves.project import Project -__version__ = "0.5.1" +__version__ = "0.5.2" diff --git a/waves/project.py b/waves/project.py index f438202..9f44d3a 100644 --- a/waves/project.py +++ b/waves/project.py @@ -607,6 +607,9 @@ def connect_orbit_cable_lengths(self, save_results: bool = True) -> None: index=False, ) + # Unset the ORBIT settings to ensure the design result isn't double counted + self.setup_orbit() + def generate_floris_positions_from_layout( self, x_col: str = "easting", @@ -1154,7 +1157,7 @@ def n_turbines(self) -> int: return len(self.wombat.windfarm.turbine_id) if self.floris_config is not None: return self.floris.farm.n_turbines - raise RuntimeError("No models wer provided, cannot calculate value.") + raise RuntimeError("No models were provided, cannot calculate value.") def turbine_rating(self) -> float: """Calculates the average turbine rating, in MW, of all the turbines in the project. @@ -1173,7 +1176,7 @@ def turbine_rating(self) -> float: return self.orbit.turbine_rating if self.wombat_config is not None: return self.wombat.windfarm.capacity / 1000 / self.n_turbines - raise RuntimeError("No models wer provided, cannot calculate value.") + raise RuntimeError("No models were provided, cannot calculate value.") def n_substations(self) -> int: """Calculates the number of subsations in the project.