Skip to content

Commit

Permalink
Merge pull request #106 from WISDEM/dev
Browse files Browse the repository at this point in the history
v1.0.5 Release
  • Loading branch information
JakeNunemaker authored Jun 21, 2021
2 parents 2bf9ebf + e11725b commit 46b371b
Show file tree
Hide file tree
Showing 14 changed files with 452 additions and 108 deletions.
20 changes: 1 addition & 19 deletions ORBIT/core/components.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,12 +8,7 @@
import simpy

from ORBIT.core.defaults import process_times as pt
from ORBIT.core.exceptions import (
ItemNotFound,
CargoMassExceeded,
DeckSpaceExceeded,
InsufficientCable,
)
from ORBIT.core.exceptions import ItemNotFound, InsufficientCable

# TODO: __str__ methods for Components

Expand Down Expand Up @@ -238,19 +233,6 @@ def put_item(self, item):
Dictionary of item properties.
"""

# if any(x not in item.keys() for x in self.required_keys):
# raise ItemPropertyNotDefined(item, self.required_keys)

if self.current_deck_space + item.deck_space > self.max_deck_space:
raise DeckSpaceExceeded(
self.max_deck_space, self.current_deck_space, item
)

if self.current_cargo_mass + item.mass > self.max_cargo_mass:
raise CargoMassExceeded(
self.max_cargo_mass, self.current_cargo_mass, item
)

self.put(item)

def get_item(self, _type):
Expand Down
27 changes: 0 additions & 27 deletions ORBIT/core/exceptions.py
Original file line number Diff line number Diff line change
Expand Up @@ -54,33 +54,6 @@ def __str__(self):
return self.message


class DeckSpaceExceeded(Exception):
"""Error for exceeding vessel maximum deck space"""

def __init__(self, max, current, item):
"""
Creates an instance of DeckSpaceExceeded.
Parameters
----------
max : int | float
Maximum vessel deck space (m2).
current : int | float
Vessel deck space currently in use (m2).
item : dict
Item that exceeded deck space limit.
"""

self.max = max
self.current = current
self.item = item

self.message = f"'{self.item['type']}' will exceed maximum deck space."

def __str__(self):
return self.message


class CargoMassExceeded(Exception):
"""Error for exceeding vessel maximum cargo mass"""

Expand Down
69 changes: 34 additions & 35 deletions ORBIT/core/logic/vessel_logic.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,11 +9,7 @@
from marmot import process

from ORBIT.core.defaults import process_times as pt
from ORBIT.core.exceptions import (
ItemNotFound,
MissingComponent,
VesselCapacityError,
)
from ORBIT.core.exceptions import ItemNotFound, MissingComponent


@process
Expand Down Expand Up @@ -233,12 +229,12 @@ def get_list_of_items_from_port(vessel, port, items, **kwargs):
Parameters
----------
TODO:
vessel : Vessel
port : Port
Port simulation object to retrieve items from.
items : list
List of tuples representing items to get from port.
- ('key': 'value')
port : Port
Port object to get items from.
"""

with port.crane.request() as req:
Expand All @@ -265,42 +261,45 @@ def get_list_of_items_from_port(vessel, port, items, **kwargs):
total_mass = sum([item.mass for item in buffer])
proposed_mass = vessel.storage.current_cargo_mass + total_mass

if proposed_deck_space > vessel.storage.max_deck_space:
vessel.submit_debug_log(message="Full")
if vessel.storage.current_cargo_mass == 0:

for item in buffer:
port.put(item)
if proposed_deck_space > vessel.storage.max_deck_space:

if vessel.storage.current_cargo_mass > 0:
break
msg = (
f"Warning: '{vessel}' Deck Space Capacity Exceeded"
)
vessel.submit_debug_log(message=msg)

else:
raise VesselCapacityError(vessel, items)
if proposed_mass > vessel.storage.max_cargo_mass:

elif proposed_mass > vessel.storage.max_cargo_mass:
vessel.submit_debug_log(message="Full")
msg = (
f"Warning: '{vessel}' Cargo Mass Capacity Exceeded"
)
vessel.submit_debug_log(message=msg)

elif proposed_deck_space > vessel.storage.max_deck_space:
vessel.submit_debug_log(message="Full")
for item in buffer:
port.put(item)
break

if vessel.storage.current_cargo_mass > 0:
break

else:
raise VesselCapacityError(vessel, items)

else:
elif proposed_mass > vessel.storage.max_cargo_mass:
vessel.submit_debug_log(message="Full")
for item in buffer:
action, time = item.fasten(**kwargs)
vessel.storage.put_item(item)

if time > 0:
yield vessel.task_wrapper(
action,
time,
constraints=vessel.transit_limits,
**kwargs,
)
port.put(item)
break

for item in buffer:
action, time = item.fasten(**kwargs)
vessel.storage.put_item(item)

if time > 0:
yield vessel.task_wrapper(
action,
time,
constraints=vessel.transit_limits,
**kwargs,
)

else:
raise ItemNotFound(items)
27 changes: 26 additions & 1 deletion ORBIT/manager.py
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,7 @@
MooringSystemInstallation,
ScourProtectionInstallation,
OffshoreSubstationInstallation,
FloatingSubstationInstallation
)
from ORBIT.core.exceptions import (
PhaseNotFound,
Expand Down Expand Up @@ -81,6 +82,7 @@ class ProjectManager:
MooredSubInstallation,
MooringSystemInstallation,
GravityBasedInstallation,
FloatingSubstationInstallation
]

def __init__(self, config, library_path=None, weather=None):
Expand Down Expand Up @@ -160,6 +162,24 @@ def run(self, **kwargs):
if install_phases:
self.progress = ProjectProgress(self.progress_logs)

self._print_warnings()

def _print_warnings(self):

try:
df = pd.DataFrame(self.logs)
df = df.loc[~df["message"].isnull()]
df = df.loc[df["message"].str.contains("Exceeded")]

for msg in df["message"].unique():

idx = df.loc[df["message"] == msg].index[0]
phase = df.loc[idx, "phase"]
print(f"{phase}:\n\t {msg}")

except KeyError:
pass

@property
def phases(self):
"""Returns dict of phases that have been ran."""
Expand Down Expand Up @@ -1344,7 +1364,12 @@ def project_capex_per_kw(self):
def total_capex(self):
"""Returns total project CapEx including soft costs."""

return self.bos_capex + self.turbine_capex + self.soft_capex
return (
self.bos_capex
+ self.turbine_capex
+ self.soft_capex
+ self.project_capex
)

@property
def total_capex_per_kw(self):
Expand Down
4 changes: 2 additions & 2 deletions ORBIT/parametric.py
Original file line number Diff line number Diff line change
Expand Up @@ -213,10 +213,10 @@ def from_config(cls, data):
key = None

if key is None:
funcs[k] = lambda run: getattr(run, attr)
funcs[k] = lambda run, a=attr: getattr(run, a)

else:
funcs[k] = lambda run: getattr(run, attr)[key]
funcs[k] = lambda run, a=attr, k=key: getattr(run, a)[k]

data["funcs"] = funcs

Expand Down
13 changes: 11 additions & 2 deletions ORBIT/phases/design/_cables.py
Original file line number Diff line number Diff line change
Expand Up @@ -333,6 +333,7 @@ def _get_touchdown_distance(self):

else:
self.touchdown = depth * 0.3
#TODO: Update this scaling function - should be closer to cable bend radius. Unrealistic for deep water

@staticmethod
def _catenary(a, *data):
Expand Down Expand Up @@ -370,12 +371,20 @@ def _get_catenary_length(self, d, h):
def free_cable_length(self):
"""Returns the length of the vertical portion of a cable section in km."""

_design = f"{self.cable_type}_system_design"
depth = self.config["site"]["depth"]
_cable_depth = self.config[_design].get("floating_cable_depth", depth)

# Select prescribed cable depth if it is less than or equal to overall water dpeth
if _cable_depth > depth:
cable_depth = depth
else:
cable_depth = _cable_depth

if not self.touchdown:
return depth / 1000
return cable_depth / 1000

return self._get_catenary_length(depth, self.touchdown) / 1000
return self._get_catenary_length(cable_depth, self.touchdown) / 1000

@property
def cable_lengths_by_type(self):
Expand Down
1 change: 1 addition & 0 deletions ORBIT/phases/design/array_system_design.py
Original file line number Diff line number Diff line change
Expand Up @@ -80,6 +80,7 @@ class ArraySystemDesign(CableSystem):
"cables": "list | str",
"touchdown_distance": "m (optional, default: 0)",
"average_exclusion_percent": "float (optional)",
"floating_cable_depth": "m (optional, default: water depth)",
},
}

Expand Down
5 changes: 4 additions & 1 deletion ORBIT/phases/design/oss_design.py
Original file line number Diff line number Diff line change
Expand Up @@ -145,11 +145,14 @@ def calc_num_mpt_and_rating(self):
"""

_design = self.config.get("substation_design", {})
self.num_substations = _design.get("num_substations", 1)

num_turbines = self.config["plant"]["num_turbines"]
turbine_rating = self.config["turbine"]["turbine_rating"]
capacity = num_turbines * turbine_rating

self.num_substations = _design.get(
"num_substations", int(np.ceil(capacity / 500))
)
self.num_mpt = np.ceil(
num_turbines * turbine_rating / (250 * self.num_substations)
)
Expand Down
5 changes: 4 additions & 1 deletion ORBIT/phases/install/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,10 @@
__email__ = ["[email protected]" "[email protected]"]

from .install_phase import InstallPhase # isort:skip
from .oss_install import OffshoreSubstationInstallation
from .oss_install import (
FloatingSubstationInstallation,
OffshoreSubstationInstallation,
)
from .cable_install import ArrayCableInstallation, ExportCableInstallation
from .mooring_install import MooringSystemInstallation
from .turbine_install import TurbineInstallation
Expand Down
1 change: 1 addition & 0 deletions ORBIT/phases/install/oss_install/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,4 +4,5 @@
__email__ = "[email protected]"


from .floating import FloatingSubstationInstallation
from .standard import OffshoreSubstationInstallation
Loading

0 comments on commit 46b371b

Please sign in to comment.