Skip to content

Commit d6002a6

Browse files
Merge branch 'main' into reorder_relationships
2 parents 2989a50 + 89e17c7 commit d6002a6

File tree

2 files changed

+69
-0
lines changed

2 files changed

+69
-0
lines changed

linkml_runtime/utils/schemaview.py

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1192,6 +1192,17 @@ def permissible_value_descendants(
11921192
**kwargs,
11931193
)
11941194

1195+
@lru_cache(None)
1196+
def type_roots(self, imports: bool = True) -> list[TypeDefinitionName]:
1197+
"""Return all types that have no parents.
1198+
1199+
:param imports: whether or not to include imports, defaults to True
1200+
:type imports: bool, optional
1201+
:return: list of all root types
1202+
:rtype: list[TypeDefinitionName]
1203+
"""
1204+
return [t for t in self.all_types(imports=imports) if not self.type_parents(t, imports=imports)]
1205+
11951206
@lru_cache(None)
11961207
def is_multivalued(self, slot_name: SlotDefinition) -> bool:
11971208
"""Return True if slot is multivalued, else returns False.

tests/test_utils/test_schemaview.py

Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -957,6 +957,64 @@ def test_all_types_induced_types(schema_view_with_imports: SchemaView) -> None:
957957
assert len(view.type_ancestors("SymbolString")) == len(["SymbolString", "string"])
958958

959959

960+
@pytest.mark.parametrize(
961+
("schema", "type_roots"),
962+
[
963+
(
964+
"""
965+
string:
966+
uri: xsd:string
967+
base: str
968+
integer:
969+
uri: xsd:integer
970+
base: int
971+
boolean:
972+
uri: xsd:boolean
973+
base: Bool
974+
""",
975+
{"string", "integer", "boolean"},
976+
),
977+
(
978+
"""
979+
string:
980+
uri: xsd:string
981+
base: str
982+
acronym:
983+
typeof: string
984+
TLA:
985+
typeof: acronym
986+
even_number:
987+
typeof: integer
988+
integer:
989+
uri: xsd:integer
990+
base: int
991+
""",
992+
{"string", "integer"},
993+
),
994+
(
995+
"""
996+
circular_type:
997+
uri: xsd:Circle
998+
typeof: type_circle
999+
1000+
type_circle:
1001+
typeof: circular_type
1002+
1003+
semi_circular_type:
1004+
typeof: circular_type
1005+
""",
1006+
set(),
1007+
),
1008+
],
1009+
)
1010+
def test_type_roots(schema: str, type_roots: set[str]) -> None:
1011+
"""Test the retrieval of types with no parent type."""
1012+
schema_head = "id: https://w3id.org/linkml/tests/types\nname: types\ntypes:\n"
1013+
1014+
sv = SchemaView(f"{schema_head}\n{schema}")
1015+
assert set(sv.type_roots()) == type_roots
1016+
1017+
9601018
def test_all_enums(schema_view_with_imports: SchemaView) -> None:
9611019
"""Test all_enums"""
9621020
view = schema_view_with_imports

0 commit comments

Comments
 (0)