Skip to content

Commit

Permalink
Merge branch 'develop' into fall-2024-docs
Browse files Browse the repository at this point in the history
  • Loading branch information
vtnate committed Dec 9, 2024
2 parents 1ac1196 + f4f0129 commit caff23f
Show file tree
Hide file tree
Showing 70 changed files with 1,364 additions and 2,410 deletions.
1 change: 1 addition & 0 deletions .cspell.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
"version": "0.2",
"language": "en",
"words": [
"armhf",
"autoload",
"borefield",
"buildingspy",
Expand Down
4 changes: 2 additions & 2 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -17,9 +17,9 @@ jobs:
fail-fast: false
matrix:
os: [ubuntu-latest, windows-latest]
python-version: ["3.10", "3.12"]
python-version: ["3.10", "3.13"]
test_env: [python, docs, mypy]
mbl_tag: [v10.0.0]
mbl_tag: [v11.0.0]
exclude:
# only test mypy on linux for all versions of python
- os: windows-latest
Expand Down
7 changes: 4 additions & 3 deletions .pre-commit-config.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ exclude: |
repos:
- repo: https://github.com/pre-commit/pre-commit-hooks
rev: v4.6.0
rev: v5.0.0
hooks:
- id: check-ast
- id: check-added-large-files
Expand Down Expand Up @@ -44,10 +44,11 @@ repos:
pass_filenames: false
# https://docs.astral.sh/ruff/integrations/#pre-commit
- repo: https://github.com/astral-sh/ruff-pre-commit
rev: v0.6.4
rev: v0.6.9
hooks:
# Run the linter
- id: ruff
args: [--fix, --exit-non-zero-on-fix, --output-format=full]
# unsafe fixes: https://docs.astral.sh/ruff/linter/#fixes
args: [--fix, --exit-non-zero-on-fix, --output-format=full, --unsafe-fixes]
# Run the formatter
- id: ruff-format
22 changes: 22 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,27 @@
# Change Log

## Version 0.8.0

### Exciting New Features 🎉
* Add default cop values for 5G district heat pump efficiencies by @vtnate in https://github.com/urbanopt/geojson-modelica-translator/pull/640
* Support international weather locations by @vtnate in https://github.com/urbanopt/geojson-modelica-translator/pull/654
* Support multiple GHEs in a single district by @vtnate in https://github.com/urbanopt/geojson-modelica-translator/pull/644
* Adds method to process modelica results by @tanushree04 in https://github.com/urbanopt/geojson-modelica-translator/pull/646
* Simplify sys params to closer match reality by @vtnate in https://github.com/urbanopt/geojson-modelica-translator/pull/659
* Templates and tests for horizontal piping modeling by @JingWang-CUB in https://github.com/urbanopt/geojson-modelica-translator/pull/627
* Support single building DES templates by @nllong in https://github.com/urbanopt/geojson-modelica-translator/pull/670

### Other Changes
* Improve cli typing & validation by @vtnate in https://github.com/urbanopt/geojson-modelica-translator/pull/662
* Add detail to Docker setup docs for Windows users by @vtnate in https://github.com/urbanopt/geojson-modelica-translator/pull/643
* Use the correct ETS heat pump COP by @vtnate in https://github.com/urbanopt/geojson-modelica-translator/pull/642
* Use feature ids in load names instead of simple_uuid by @vtnate in https://github.com/urbanopt/geojson-modelica-translator/pull/652
* Remove alfalfa from conftest.py by @nllong in https://github.com/urbanopt/geojson-modelica-translator/pull/665
* Update version of Jinja by @nllong in https://github.com/urbanopt/geojson-modelica-translator/pull/667
* Clean up sys-param code that reads parameters by @vtnate in https://github.com/urbanopt/geojson-modelica-translator/pull/668

**Full Changelog**: https://github.com/urbanopt/geojson-modelica-translator/compare/v0.7.0...v0.8.0

## Version 0.7.0

### Exciting New Features 🎉
Expand Down
8 changes: 4 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -55,9 +55,9 @@ The building loads can be defined multiple ways depending on the fidelity of the

## Release Instructions

1. Create a branch named `prep-0.x.y Release`
1. Create a branch named `Release 0.x.`
1. Update version in pyproject.toml
2. Update CHANGELOG using GitHub's "Autogenerate Change Log" feature
3. After tests pass, merge branch into develop
4. Create new PR from develop into main named `Release 0.x.y`
5. Using GitHub squash-merge into main
6. From local repo, immediately merge main into develop (as a merge commit) and push. This can only be done with users that have bypass privileges on GitHub.
4. From command line, merge develop into main with: `git checkout main; git pull; git merge --ff-only origin develop; git push`
5. In GitHub, tag the release against main. Copy and paste the changelog entry into the notes. Verify the release is posted to PyPI.
1 change: 0 additions & 1 deletion docs/conf.py
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,6 @@
# |version| and |release|, also used in various other places throughout the
# built documents.
#
# TODO: grab version from pyproject.toml
poetry_file = toml.load("../pyproject.toml")

# The short X.Y version.
Expand Down
16 changes: 11 additions & 5 deletions geojson_modelica_translator/geojson_modelica_translator.py
Original file line number Diff line number Diff line change
Expand Up @@ -126,8 +126,7 @@ def _parse_couplings(geojson, sys_params, sys_param_district_type):
class ModelicaPackage:
"""Represents a modelica package which can be simulated"""

def __init__(self, file_to_run, project_path, project_name):
self._file_to_run = file_to_run
def __init__(self, project_path, project_name):
self._project_path = project_path
self._project_name = project_name

Expand All @@ -137,9 +136,16 @@ def simulate(self):
:return: tuple(bool, pathlib.Path), True or False depending on simulation success
followed by the path to the results directory
"""
_log.debug(f"Model name: {self._project_name}.Districts.DistrictEnergySystem")
_log.debug(f"file to load: {self._project_path / self._project_name / 'package.mo'}")
_log.debug(f"run path: {self._project_path / self._project_name}")

modelica_runner = ModelicaRunner()
return modelica_runner.run_in_docker(
self._file_to_run, run_path=self._project_path, project_name=self._project_name
action="compile_and_run",
model_name=f"{self._project_name}.Districts.DistrictEnergySystem",
file_to_load=self._project_path / self._project_name / "package.mo",
run_path=self._project_path / self._project_name,
)


Expand Down Expand Up @@ -167,7 +173,7 @@ def __init__(

self._system_parameters = SystemParameters(sys_params_filepath)

geojson_ids = self._system_parameters.get_default("$.buildings.[*].geojson_id", [])
geojson_ids = self._system_parameters.get_param("$.buildings.[*].geojson_id")
self._geojson = UrbanOptGeoJson(geojson_filepath, geojson_ids)

# Use different couplings for each district system type
Expand All @@ -194,4 +200,4 @@ def to_modelica(self):
"""
self._district.to_modelica()

return ModelicaPackage(self._district.district_model_filepath, self._root_dir, self._project_name)
return ModelicaPackage(self._root_dir, self._project_name)

This file was deleted.

This file was deleted.

Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,9 @@
{% endraw %}
connect({{ coupling.load.id }}.port_bSerAmb, {{ coupling.network.id }}.ports_aCon[{{ bldg_num+1 }}])
{% raw %}annotation (Line(points={{80,30},{92,30},{92,6},{82,6},{82,0}}, color={0,127,255}));
{% endraw %}{% set sum_bldg = loop_order.data[:group_num]|map(attribute='list_bldg_ids_in_group')|map('length')|sum %}
connect({{ coupling.load.id }}.QCoo_flow, conPum.QCoo_flow[{{ sum_bldg+bldg_num+1 }}])
{% raw %}annotation (Line(points={{67,-12},{128,-12},{128,-112},{-124,-112},{-124,-96},{-121.692,-96}}, color={0,0,127}));
{% endraw %}
{% endif %}
{% endfor %}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,3 +8,12 @@ redeclare final package Medium = {{ globals.medium_w }},
m_flow_nominal=datDes.mPumDis_flow_nominal)
{% raw %}annotation (Placement(transformation(extent={{-10,10},{10,-10}},rotation=0,origin={16,10})));
{% endraw %}
Buildings.Fluid.Sensors.TemperatureTwoPort TDisSup_{{ coupling.id }}(
redeclare final package Medium = {{ globals.medium_w }},
m_flow_nominal=datDes.mPumDis_flow_nominal)
{% raw %}annotation (Placement(transformation(extent={{-10,10},{10,-10}},rotation=0,origin={34,10})));
{% endraw %}Buildings.Fluid.Sensors.TemperatureTwoPort TDisRet_{{ coupling.id }}(
redeclare final package Medium = {{ globals.medium_w }},
m_flow_nominal=datDes.mPumDis_flow_nominal)
{% raw %}annotation (Placement(transformation(extent={{-10,10},{10,-10}},rotation=-90,origin={100,-30})));
{% endraw %}
Original file line number Diff line number Diff line change
@@ -1,33 +1,58 @@
// Borefield and distribution coupling connections
{% if graph.get_ghe_id(coupling.id) == loop_order.data[0].list_ghe_ids_in_group[0] %}
connect(pumDis.port_b, TIn_{{ coupling.id }}.port_a)
connect(pumDis.port_b, TDisSup_{{ coupling.id }}.port_a)
{% raw %}annotation (Line(points={{-44,-50},{-44,10},{-40,10}}, color={0,127,255}));
{% endraw %}
{% endif %}
connect(TIn_{{ coupling.id }}.port_b, {{ coupling.plant.id }}.port_a)
connect(TIn_{{ coupling.id }}.port_b, conSto_{{ coupling.plant.id }}.port_aDis)
{% raw %}annotation (Line(points={{-20,10},{-10,10}}, color={0,127,255}));
{% endraw %}connect({{ coupling.plant.id }}.port_b, TOut_{{ coupling.id }}.port_a)
{% endraw %}connect(conSto_{{ coupling.plant.id }}.port_bDis, TOut_{{ coupling.id }}.port_a)
{% raw %}annotation (Line(points={{10,10},{6,10}}, color={0,127,255}));
{% endraw %}connect(TOut_{{ coupling.id }}.port_b, {{ coupling.network.id }}.port_aDisSup)
{% raw %}annotation (Line(points={{26,10},{38,10},{38,-10},{50,-10}}, color={0,127,255}));
{% endraw %}connect(conSto_{{ coupling.plant.id }}.port_bCon, pumSto_{{ coupling.plant.id }}.port_a)
{% raw %}annotation (Line(points={{-18,20},{-18,32},{-50,32},{-50,50},{-40,50}}, color={0,127,255}));
{% endraw %}connect(pumSto_{{ coupling.plant.id }}.port_b, {{ coupling.plant.id }}.port_a)
{% raw %}annotation (Line(points={{-20,50},{-10,50}}, color={0,127,255}));
{% endraw %}connect({{ coupling.plant.id }}.port_b, conSto_{{ coupling.plant.id }}.port_aCon)
{% raw %}annotation (Line(points={{10,50},{20,50},{20,32},{-12,32},{-12,20}}, color={0,127,255}));
{% endraw %}connect(TDisRet_{{ coupling.id }}.port_b, TIn_{{ coupling.id }}.port_a)
{% raw %}annotation (Line(points={{20,10},{24,10}}, color={0,127,255}));
{% endraw %}connect(TDisSup_{{ coupling.id }}.port_b, {{ coupling.network.id }}.port_aDisSup)
{% raw %}annotation (Line(points={{44,10},{50,10}}, color={0,127,255}));
{% endraw %}connect({{ coupling.network.id }}.port_bDisSup, TDisRet_{{ coupling.id }}.port_a)
{% raw %}annotation (Line(points={{90,10},{100,10},{100,-20}}, color={0,127,255}));
{% endraw %}
{% for group_num in range(loop_order.number_of_loops) %}
{% if graph.get_ghe_id(coupling.id) == loop_order.data[group_num].list_ghe_ids_in_group[0] %}
{% if group_num == loop_order.number_of_loops-1 %}
connect({{ coupling.network.id }}.port_bDisSup, pumDis.port_a)
{% raw %}annotation (Line(points={{90,-10},{110,-10},{110,-20}}, color={0,127,255}));
connect(TOut_{{ coupling.id }}.port_b, pumDis.port_a)
{% raw %}annotation (Line(points={{100,-40},{100,-74},{-72,-74},{-72,-70}}, color={0,127,255}));
{% endraw %}
{% else %}
{% set ground_id = graph.couplings_by_type(coupling.network.id).network_couplings[0].network.id %}
{% set next_borefield_id = graph.couplings_by_type(ground_id).plant_couplings[group_num+1].plant.id %}
{% set next_dis_id = graph.couplings_by_type(next_borefield_id).network_couplings[0].network.id %}
connect({{ coupling.network.id }}.port_bDisSup, TIn_{{ graph.couplings_by_type(next_dis_id).plant_couplings[0].id }}.port_a)
connect(TOut_{{ coupling.id }}.port_b, TDisSup_{{ graph.couplings_by_type(next_dis_id).plant_couplings[0].id }}.port_a)
{% raw %}annotation (Line(points={{-44,-50},{-44,10},{-40,10}}, color={0,127,255}));
{% endraw %}
{% endif %}
{% endif %}
{% endfor %}
// control related connections
connect(conBor_{{ coupling.plant.id }}.y, gai1_{{ coupling.plant.id }}.u)
{% raw %}annotation (Line(points={{-38.4615,90},{-32,90}}, color={0,0,127}));
{% endraw %}connect(gai1_{{ coupling.plant.id }}.y, pumSto_{{ coupling.plant.id }}.m_flow_in)
{% raw %}annotation (Line(points={{-8,90},{0,90},{0,70},{-30,70},{-30,62}}, color={0,0,127}));
{% endraw %}connect({{ coupling.plant.id }}.TBorAve, conBor_{{ coupling.plant.id }}.TSou)
{% raw %}annotation (Line(points={{11,54.4},{22,54.4},{22,70},{-78,70},{-78,93},{-61.5385,93}}, color={0,0,127}));
{% endraw %}connect(TIn_{{ coupling.id }}.T, conBor_{{ coupling.plant.id }}.TSouIn)
{% raw %}annotation (Line(points={{-58,-1},{-58,-4},{-78,-4},{-78,97},{-61.5385,97}}, color={0,0,127}));
{% endraw %}connect(TOut_{{ coupling.id }}.T, conBor_{{ coupling.plant.id }}.TSouOut)
{% raw %}annotation (Line(points={{10,-1},{10,-4},{-78,-4},{-78,89},{-61.5385,89}}, color={0,0,127}));
{% endraw %}connect(TDisSup_{{ coupling.id }}.T, conBor_{{ coupling.plant.id }}.TSupDis)
{% raw %}annotation (Line(points={{34,-1},{34,-30},{-78,-30},{-78,82},{-61.5385,82}}, color={0,0,127}));
{% endraw %}connect(TDisRet_{{ coupling.id }}.T, conBor_{{ coupling.plant.id }}.TRetDis)
{% raw %}annotation (Line(points={{89,-30},{-78,-30},{-78,85},{-61.5385,85}}, color={0,0,127}));
{% endraw %}
{% for group_num in range(loop_order.number_of_loops) %}
{% if graph.get_ghe_id(coupling.id) == loop_order.data[group_num].list_ghe_ids_in_group[0] %}
{% if group_num == 0 %}
Expand Down
49 changes: 34 additions & 15 deletions geojson_modelica_translator/model_connectors/districts/district.py
Original file line number Diff line number Diff line change
Expand Up @@ -37,9 +37,9 @@ class District:

def __init__(self, root_dir, project_name, system_parameters, coupling_graph, geojson_file=None):
self._scaffold = Scaffold(root_dir, project_name)
self.system_parameters = system_parameters
self.gj = geojson_file
self._coupling_graph = coupling_graph
self.system_parameters = system_parameters # SystemParameters object
self.gj = geojson_file # UrbanOptGeoJson object
self._coupling_graph = coupling_graph # CouplingGraph object
self.district_model_filepath = None
# Modelica can't handle spaces in project name or path
if (len(str(root_dir).split()) > 1) or (len(str(project_name).split()) > 1):
Expand Down Expand Up @@ -105,18 +105,37 @@ def to_modelica(self):
"data": loop_order,
}

if self.gj:
# get horizontal pipe lengths from geojson, starting from the outlet of the (first) ghe
# TODO: only check for total_length if type==ThermalConnector
# I thought this was the right syntax, but not quite: .properties[?type=ThermalConnector].total_length
# TODO: make sure the list of lengths is starting from the outlet of the ghe
list_of_pipe_lengths = self.gj.get_feature("$.features.[*].properties.total_length")
for i in range(len(list_of_pipe_lengths)):
list_of_pipe_lengths[i] = convert_ft_to_m(list_of_pipe_lengths[i])
common_template_params["globals"]["lDis"] = (
str(list_of_pipe_lengths[:-1]).replace("[", "{").replace("]", "}")
)
common_template_params["globals"]["lEnd"] = list_of_pipe_lengths[-1]
# This indent level requires the District to include a GHE, because the only way we get a loop_order
# is by running ThermalNetwork for sizing.
# TODO: determine loop order some other way, so thermal networks without GHEs can have horizontal piping
# or: Ensure TN is used for all networks, so loop order is generated that way.
if self.gj:
# get horizontal pipe lengths from geojson, starting from the beginning of the loop
feature_properties = self.gj.get_feature("$.features.[*].properties")
dict_of_pipe_lengths = {
feature_prop.get("startFeatureId"): feature_prop["total_length"]
for feature_prop in feature_properties
if feature_prop["type"] == "ThermalConnector"
}
ordered_feature_list = []
ordered_pipe_list = []
for loop in loop_order:
ordered_feature_list.extend(loop["list_bldg_ids_in_group"])
ordered_feature_list.extend(loop["list_ghe_ids_in_group"])

for feature in ordered_feature_list:
for dict_feature, pipe_length in dict_of_pipe_lengths.items():
if dict_feature == feature:
ordered_pipe_list.append(pipe_length)

for i in range(len(ordered_pipe_list)):
ordered_pipe_list[i] = convert_ft_to_m(ordered_pipe_list[i])
common_template_params["globals"]["lDis"] = (
str(ordered_pipe_list[:-1]).replace("[", "{").replace("]", "}")
)
common_template_params["globals"]["lEnd"] = ordered_pipe_list[-1]
else:
raise SystemExit("No geojson file provided, unable to determine thermal network loop order")

# render each coupling
load_num = 1
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ model DistrictEnergySystem
parameter Modelica.Units.SI.TemperatureDifference delHeaWatTemDis(displayUnit="degC")=12;
parameter Modelica.Units.SI.TemperatureDifference delHeaWatTemBui(displayUnit="degC")=5;
parameter Integer numberofchillers = 2;
inner parameter Buildings.Experimental.DHC.Examples.Combined.BaseClasses.DesignDataSeries datDes(
inner parameter Buildings.DHC.Examples.Combined.BaseClasses.DesignDataSeries datDes(
nBui=1,
mPumDis_flow_nominal=95,
mPipDis_flow_nominal=95,
Expand Down
Loading

0 comments on commit caff23f

Please sign in to comment.