[rtems-central commit] items: Add Item parent() and child() methods

Sebastian Huber sebh at rtems.org
Wed Oct 21 17:43:23 UTC 2020


Module:    rtems-central
Branch:    master
Commit:    a8ba97d18dc79113dd8e0cc0a649274bf935a88d
Changeset: http://git.rtems.org/rtems-central/commit/?id=a8ba97d18dc79113dd8e0cc0a649274bf935a88d

Author:    Sebastian Huber <sebastian.huber at embedded-brains.de>
Date:      Wed Oct 21 18:22:22 2020 +0200

items: Add Item parent() and child() methods

---

 rtemsspec/interface.py             |  8 ++++----
 rtemsspec/interfacedoc.py          |  2 +-
 rtemsspec/items.py                 | 20 ++++++++++++++++++++
 rtemsspec/tests/test_items_item.py |  6 ++++++
 4 files changed, 31 insertions(+), 5 deletions(-)

diff --git a/rtemsspec/interface.py b/rtemsspec/interface.py
index 502cc96..24eb463 100644
--- a/rtemsspec/interface.py
+++ b/rtemsspec/interface.py
@@ -50,7 +50,7 @@ def _get_group_identifiers(groups: ItemMap) -> List[str]:
 
 
 def _forward_declaration(item: Item) -> str:
-    target = next(item.parents("interface-target"))
+    target = item.parent("interface-target")
     return f"{target['interface-type']} {target['name']}"
 
 
@@ -187,8 +187,8 @@ class Node:
         self.content = CContent()
         self.mapper = _InterfaceMapper(self)
         try:
-            group = next(item.children("placement-order"))
-        except StopIteration:
+            group = item.child("placement-order")
+        except IndexError:
             self.index = None
         else:
             self.index = (group.uid,
@@ -581,7 +581,7 @@ class _HeaderFile:
 
 def _generate_header_file(item: Item, domains: Dict[str, str],
                           enabled_by_defined: Dict[str, str]) -> None:
-    domain = next(item.parents("interface-placement"))
+    domain = item.parent("interface-placement")
     assert domain["interface-type"] == "domain"
     domain_path = domains.get(domain.uid, None)
     if domain_path is None:
diff --git a/rtemsspec/interfacedoc.py b/rtemsspec/interfacedoc.py
index 5abc8b5..e77bd67 100644
--- a/rtemsspec/interfacedoc.py
+++ b/rtemsspec/interfacedoc.py
@@ -42,7 +42,7 @@ INTERFACE = "Interface"
 
 
 def _forward_declaration(item: Item) -> str:
-    target = next(item.parents("interface-target"))
+    target = item.parent("interface-target")
     return f"{target['interface-type']} {target['name']}"
 
 
diff --git a/rtemsspec/items.py b/rtemsspec/items.py
index 658b68c..9dd741f 100644
--- a/rtemsspec/items.py
+++ b/rtemsspec/items.py
@@ -139,6 +139,8 @@ def normalize_key_path(key_path: str, prefix: str = "") -> str:
 
 class Item:
     """ Objects of this class represent a specification item. """
+
+    # pylint: disable=too-many-public-methods
     def __init__(self, item_cache: "ItemCache", uid: str, data: Any):
         self._item_cache = item_cache
         self._uid = uid
@@ -256,6 +258,15 @@ class Item:
                 if link.role in role:
                     yield link.item
 
+    def parent(self,
+               role: Optional[Union[str, Iterable[str]]] = None,
+               index: Optional[int] = 0) -> "Item":
+        """ Returns the parent with the specified role and index. """
+        for item_index, item in enumerate(self.parents(role)):
+            if item_index == index:
+                return item
+        raise IndexError
+
     def links_to_children(self) -> Iterator[Link]:
         """ Yields the links to the children of this items. """
         yield from self._links_to_children
@@ -277,6 +288,15 @@ class Item:
                 if link.role in role:
                     yield link.item
 
+    def child(self,
+              role: Optional[Union[str, Iterable[str]]] = None,
+              index: Optional[int] = 0) -> "Item":
+        """ Returns the child with the specified role and index. """
+        for item_index, item in enumerate(self.children(role)):
+            if item_index == index:
+                return item
+        raise IndexError
+
     def init_parents(self, item_cache: "ItemCache"):
         """ Initializes the list of links to parents of this items. """
         for data in self._data["links"]:
diff --git a/rtemsspec/tests/test_items_item.py b/rtemsspec/tests/test_items_item.py
index fcc2258..bb9b085 100644
--- a/rtemsspec/tests/test_items_item.py
+++ b/rtemsspec/tests/test_items_item.py
@@ -149,6 +149,9 @@ def test_children():
     assert links[0].item == child
     assert links[0]["a"] == "b"
     assert links[0].role == "c"
+    assert parent.child("c") == child
+    with pytest.raises(IndexError):
+        parent.child("c", 1)
 
 
 def test_parents():
@@ -182,6 +185,9 @@ def test_parents():
     assert links[0].item == parent
     assert links[0]["a"] == "b"
     assert links[0].role == "c"
+    assert child.parent("c") == parent
+    with pytest.raises(IndexError):
+        child.parent("c", 1)
 
 
 def _is_enabled(enabled, enabled_by):



More information about the vc mailing list