@@ -113,6 +113,28 @@ def __init__(
113113 if tree .identifier != self ._identifier :
114114 new_node .clone_pointers (tree .identifier , self ._identifier )
115115
116+ @classmethod
117+ def from_json (cls , raw : Union [str , bytes , bytearray ]):
118+ """
119+ Load tree from exported JSON.
120+ """
121+ tree = cls ()
122+ json_parsed = json .loads (raw )
123+
124+ def _append_node (subtree , parent_id = None ):
125+ for tag , node_info in subtree .items ():
126+ node_id = node_info ["id" ]
127+ node_data = node_info .get ("data" )
128+ tree .create_node (
129+ tag = tag , identifier = node_id , parent = parent_id , data = node_data
130+ )
131+
132+ for child in node_info .get ("children" , []):
133+ _append_node (child , parent_id = node_id )
134+
135+ _append_node (json_parsed )
136+ return tree
137+
116138 def _clone (
117139 self ,
118140 identifier : Optional [str ] = None ,
@@ -1110,7 +1132,8 @@ def to_dict(self, nid=None, key=None, sort=True, reverse=False, with_data=False)
11101132
11111133 nid = self .root if (nid is None ) else nid
11121134 ntag = self [nid ].tag
1113- tree_dict = {ntag : {"children" : []}}
1135+ tree_dict = {ntag : {"id" : nid , "children" : []}}
1136+
11141137 if with_data :
11151138 tree_dict [ntag ]["data" ] = self [nid ].data
11161139
@@ -1128,9 +1151,12 @@ def to_dict(self, nid=None, key=None, sort=True, reverse=False, with_data=False)
11281151 )
11291152 if len (tree_dict [ntag ]["children" ]) == 0 :
11301153 tree_dict = (
1131- self [nid ].tag if not with_data else {ntag : {"data" : self [nid ].data }}
1154+ {ntag : {"id" : nid }}
1155+ if not with_data
1156+ else {ntag : {"id" : nid , "data" : self [nid ].data }}
11321157 )
1133- return tree_dict
1158+
1159+ return tree_dict
11341160
11351161 def to_json (
11361162 self , with_data : bool = False , sort : bool = True , reverse : bool = False
0 commit comments