4
4
# SPDX-License-Identifier: MIT
5
5
6
6
import os
7
- from typing import IO , Any , Iterator , Optional , Union
7
+ from typing import IO , Any , Callable , Iterator , Optional , Tuple , Union
8
8
9
9
from _libyang import ffi , lib
10
10
from .data import (
19
19
from .util import DataType , IOType , LibyangError , c2str , data_load , str2c
20
20
21
21
22
+ # -------------------------------------------------------------------------------------
23
+ @ffi .def_extern (name = "lypy_module_imp_data_free_clb" )
24
+ def libyang_c_module_imp_data_free_clb (cdata , user_data ):
25
+ instance = ffi .from_handle (user_data )
26
+ instance .free_module_data (cdata )
27
+
28
+
29
+ # -------------------------------------------------------------------------------------
30
+ @ffi .def_extern (name = "lypy_module_imp_clb" )
31
+ def libyang_c_module_imp_clb (
32
+ mod_name ,
33
+ mod_rev ,
34
+ submod_name ,
35
+ submod_rev ,
36
+ user_data ,
37
+ fmt ,
38
+ module_data ,
39
+ free_module_data ,
40
+ ):
41
+ fmt [0 ] = lib .LYS_IN_UNKNOWN
42
+ module_data [0 ] = ffi .NULL
43
+ free_module_data [0 ] = lib .lypy_module_imp_data_free_clb
44
+ instance = ffi .from_handle (user_data )
45
+ in_fmt , content = instance .get_module_data (
46
+ c2str (mod_name ), c2str (mod_rev ), c2str (submod_name ), c2str (submod_rev )
47
+ )
48
+ if content is None :
49
+ return lib .LY_ENOT
50
+ fmt [0 ] = schema_in_format (in_fmt )
51
+ module_data [0 ] = content
52
+ return lib .LY_SUCCESS
53
+
54
+
22
55
# -------------------------------------------------------------------------------------
23
56
class Context :
24
- __slots__ = ("cdata" , "__dict__" )
57
+ __slots__ = (
58
+ "cdata" ,
59
+ "_module_data_clb" ,
60
+ "_cffi_handle" ,
61
+ "_cdata_modules" ,
62
+ "__dict__" ,
63
+ )
25
64
26
65
def __init__ (
27
66
self ,
@@ -34,6 +73,10 @@ def __init__(
34
73
yanglib_fmt : str = "json" ,
35
74
cdata = None , # C type: "struct ly_ctx *"
36
75
):
76
+ self ._module_data_clb = None
77
+ self ._cffi_handle = ffi .new_handle (self )
78
+ self ._cdata_modules = []
79
+
37
80
if cdata is not None :
38
81
self .cdata = ffi .cast ("struct ly_ctx *" , cdata )
39
82
return # already initialized
@@ -475,3 +518,41 @@ def __iter__(self) -> Iterator[Module]:
475
518
while mod :
476
519
yield Module (self , mod )
477
520
mod = lib .ly_ctx_get_module_iter (self .cdata , idx )
521
+
522
+ def free_module_data (self , cdata ) -> None :
523
+ self ._cdata_modules .remove (cdata )
524
+
525
+ def get_module_data (
526
+ self ,
527
+ mod_name : Optional [str ],
528
+ mod_rev : Optional [str ],
529
+ submod_name : Optional [str ],
530
+ submod_rev : Optional [str ],
531
+ ) -> Tuple [str , Optional [str ]]:
532
+ if self ._module_data_clb is None :
533
+ return None
534
+ fmt_str , module_data = self ._module_data_clb (
535
+ mod_name , mod_rev , submod_name , submod_rev
536
+ )
537
+ if module_data is None :
538
+ return fmt_str , None
539
+ module_data_c = str2c (module_data )
540
+ self ._cdata_modules .append (module_data_c )
541
+ return fmt_str , module_data_c
542
+
543
+ def set_module_data_clb (
544
+ self ,
545
+ clb : Optional [
546
+ Callable [
547
+ [Optional [str ], Optional [str ], Optional [str ], Optional [str ]],
548
+ Tuple [str , Optional [str ]],
549
+ ]
550
+ ] = None ,
551
+ ) -> None :
552
+ self ._module_data_clb = clb
553
+ if clb is None :
554
+ lib .ly_ctx_set_module_imp_clb (self .cdata , ffi .NULL , ffi .NULL )
555
+ else :
556
+ lib .ly_ctx_set_module_imp_clb (
557
+ self .cdata , lib .lypy_module_imp_clb , self ._cffi_handle
558
+ )
0 commit comments