Skip to content

Commit 738d708

Browse files
yt-msMidnighter
authored andcommitted
feat(DeploymentView): add ability to add a relationship to the view
1 parent 9016929 commit 738d708

File tree

3 files changed

+53
-11
lines changed

3 files changed

+53
-11
lines changed

src/structurizr/view/deployment_view.py

Lines changed: 8 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -76,13 +76,12 @@ def add_all_deployment_nodes(self):
7676
If the environment is set in this view, then only nodes from the same
7777
environment will be added.
7878
"""
79-
for deployment_node in self.model.deployment_nodes:
80-
if deployment_node.parent is None:
81-
if (
82-
self.environment is None
83-
or self.environment == deployment_node.environment
84-
):
85-
self.add(deployment_node)
79+
for deployment_node in self.model.deployment_nodes: # This returns top-level
80+
if (
81+
self.environment is None
82+
or self.environment == deployment_node.environment
83+
):
84+
self.add(deployment_node)
8685

8786
def add(
8887
self, item: Union[DeploymentNode, Relationship], add_relationships: bool = True
@@ -95,9 +94,9 @@ def add(
9594
self._add_element(parent, add_relationships)
9695
parent = parent.parent
9796
else:
98-
pass # TODO
97+
self._add_relationship(item)
9998

100-
def __iadd__(self, item: Union[DeploymentNode, Relationship]):
99+
def __iadd__(self, item: Union[DeploymentNode, Relationship]) -> "DeploymentView":
101100
"""Add a deployment node or relationship to this view."""
102101
self.add(item)
103102
return self

src/structurizr/view/view.py

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@
2424
from ..abstract_base import AbstractBase
2525
from ..base_model import BaseModel
2626
from ..mixin import ViewSetRefMixin
27-
from ..model import Element, Model, SoftwareSystem
27+
from ..model import Element, Model, Relationship, SoftwareSystem
2828
from .automatic_layout import AutomaticLayout, AutomaticLayoutIO
2929
from .element_view import ElementView, ElementViewIO
3030
from .paper_size import PaperSize
@@ -169,6 +169,21 @@ def _remove_element(self, element: Element) -> None:
169169
):
170170
self.relationship_views.remove(relationship_view)
171171

172+
def _add_relationship(self, relationship: Relationship) -> RelationshipView:
173+
"""Add a single relationship to this view.
174+
175+
Returns:
176+
The new view if both the source and destination for the relationship are
177+
in this view, else `None`.
178+
"""
179+
if self.is_element_in_view(relationship.source) and self.is_element_in_view(
180+
relationship.destination
181+
):
182+
view = RelationshipView(relationship=relationship)
183+
self.relationship_views.add(view)
184+
return view
185+
return None
186+
172187
def _add_relationships(self, element: Element) -> None:
173188
"""
174189
Add all relationships involving the given element to this view.

tests/unit/view/test_deployment_view.py

Lines changed: 29 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -114,7 +114,7 @@ def test_deployment_view_add_all_deployment_nodes_with_container_instances(
114114
key="deployment",
115115
description="Description",
116116
)
117-
deployment_view.add_all_deployment_nodes()
117+
deployment_view.add_default_elements()
118118
element_views = deployment_view.element_views
119119
assert len(element_views) == 2
120120
assert any([x.element is deployment_node for x in element_views])
@@ -196,6 +196,34 @@ def test_deployment_view_add_deployment_node_adds_parent(empty_workspace: Worksp
196196
assert any([x.element is container_instance for x in element_views])
197197

198198

199+
def test_deployment_view_add_relationship(empty_workspace: Workspace):
200+
"""Check adding a relationship to the deployment view."""
201+
model = empty_workspace.model
202+
software_system = model.add_software_system("Software System")
203+
container1 = software_system.add_container("Container1")
204+
container2 = software_system.add_container("Container2")
205+
rel = container1.uses(container2)
206+
parent_deployment_node = model.add_deployment_node("Deployment Node")
207+
child_deployment_node1 = parent_deployment_node.add_deployment_node("Child1")
208+
child_deployment_node1 += container1
209+
child_deployment_node2 = parent_deployment_node.add_deployment_node("Child2")
210+
child_deployment_node2 += container2
211+
212+
deployment_view = empty_workspace.views.create_deployment_view(
213+
software_system=software_system, key="deployment", description="Description"
214+
)
215+
deployment_view += child_deployment_node1
216+
217+
# First try before we have the destination in the view
218+
deployment_view += rel
219+
assert len(deployment_view.relationship_views) == 0
220+
221+
# Now try with it in
222+
deployment_view += child_deployment_node2
223+
deployment_view += rel
224+
assert len(deployment_view.relationship_views) == 1
225+
226+
199227
def test_add_animation_step_raises_if_no_elements(empty_workspace: Workspace):
200228
"""Check error handling if no elements passed."""
201229
deployment_view = empty_workspace.views.create_deployment_view(

0 commit comments

Comments
 (0)