diff --git a/cffi/cdefs.h b/cffi/cdefs.h index aa75004..4f68d4e 100644 --- a/cffi/cdefs.h +++ b/cffi/cdefs.h @@ -361,6 +361,14 @@ LY_ERR lys_print_module(struct ly_out *, const struct lys_module *, LYS_OUTFORMA #define LYS_PRINT_NO_SUBSTMT ... #define LYS_PRINT_SHRINK ... +struct lysc_module { + struct lys_module *mod; + struct lysc_node *data; + struct lysc_node_action *rpcs; + struct lysc_node_notif *notifs; + struct lysc_ext_instance *exts; +}; + struct lys_module { struct ly_ctx *ctx; const char *name; diff --git a/libyang/schema.py b/libyang/schema.py index 3f3bd4d..d90289e 100644 --- a/libyang/schema.py +++ b/libyang/schema.py @@ -180,6 +180,29 @@ def parsed_identities(self) -> Iterator["PIdentity"]: for i in ly_array_iter(self.cdata.parsed.identities): yield PIdentity(self.context, i, self) + def extensions(self) -> Iterator["ExtensionCompiled"]: + compiled = ffi.cast("struct lysc_module *", self.cdata.compiled) + if compiled == ffi.NULL: + return + exts = ffi.cast("struct lysc_ext_instance *", self.cdata.compiled.exts) + if exts == ffi.NULL: + return + for extension in ly_array_iter(exts): + yield ExtensionCompiled(self.context, extension) + + def get_extension( + self, name: str, prefix: Optional[str] = None, arg_value: Optional[str] = None + ) -> Optional["ExtensionCompiled"]: + for ext in self.extensions(): + if ext.name() != name: + continue + if prefix is not None and ext.module().name() != prefix: + continue + if arg_value is not None and ext.argument() != arg_value: + continue + return ext + return None + def __str__(self) -> str: return self.name() diff --git a/tests/test_schema.py b/tests/test_schema.py index a310aad..4e40d3b 100644 --- a/tests/test_schema.py +++ b/tests/test_schema.py @@ -129,6 +129,19 @@ def test_mod_revisions(self): self.assertEqual(revisions[0].date(), "1999-04-01") self.assertEqual(revisions[1].date(), "1990-04-01") + def test_mod_extensions(self): + assert self.module is not None # pyright doesn't understand assertIsNotNone() + exts = list(self.module.extensions()) + self.assertEqual(len(exts), 1) + ext = self.module.get_extension("compile-validation", prefix="omg-extensions") + self.assertEqual(ext.argument(), "module-level") + sub_exts = list(ext.extensions()) + self.assertEqual(len(sub_exts), 1) + ext = sub_exts[0] + self.assertEqual(ext.name(), "compile-validation") + self.assertEqual(ext.module().name(), "omg-extensions") + self.assertEqual(ext.argument(), "module-sub-level") + # ------------------------------------------------------------------------------------- class RevisionTest(unittest.TestCase): diff --git a/tests/yang/yolo/yolo-system.yang b/tests/yang/yolo/yolo-system.yang index 36c7641..b6ad919 100644 --- a/tests/yang/yolo/yolo-system.yang +++ b/tests/yang/yolo/yolo-system.yang @@ -155,6 +155,10 @@ module yolo-system { } } + ext:compile-validation "module-level" { + ext:compile-validation "module-sub-level"; + } + container conf { description "Configuration.";