mirror of
https://dev.iopsys.eu/bbf/bbfdm.git
synced 2025-12-10 07:44:39 +01:00
360 lines
9.2 KiB
Python
Executable file
360 lines
9.2 KiB
Python
Executable file
#!/usr/bin/python
|
|
|
|
# This program is free software: you can redistribute it and/or modify
|
|
# it under the terms of the GNU General Public License as published by
|
|
# the Free Software Foundation, either version 2 of the License, or
|
|
# (at your option) any later version.
|
|
#
|
|
# Copyright (C) 2019 iopsys Software Solutions AB
|
|
# Author: Amin Ben Ramdhane <amin.benramdhane@pivasoftware.com>
|
|
|
|
# Copyright (C) 2019 PIVA SOFTWARE <www.pivasoftware.com> - All Rights Reserved
|
|
# Author: Mohamed Kallel <mohamed.kallel@pivasoftware.com>
|
|
|
|
import os, sys, time, re, json
|
|
import xml.etree.ElementTree as xml
|
|
from collections import OrderedDict
|
|
from shutil import copyfile
|
|
|
|
def removefile( filename ):
|
|
try:
|
|
os.remove(filename)
|
|
except OSError:
|
|
pass
|
|
|
|
def securemkdir( folder ):
|
|
try:
|
|
os.mkdir(folder)
|
|
except:
|
|
pass
|
|
|
|
def getname( objname ):
|
|
global model_root_name
|
|
OBJSname = objname
|
|
if (objname.count('.') > 1 and (objname.count('.') != 2 or objname.count('{i}') != 1) ):
|
|
OBJSname = objname.replace(dmroot.get('name'), "", 1)
|
|
OBJSname = OBJSname.replace("{i}", "")
|
|
OBJSname = OBJSname.replace(".", "")
|
|
if (objname.count('.') == 1):
|
|
model_root_name = OBJSname
|
|
OBJSname = "Root" + OBJSname
|
|
return OBJSname
|
|
if (objname.count('.') == 2 and objname.count('{i}') == 1):
|
|
model_root_name = OBJSname
|
|
OBJSname = "Services" + OBJSname
|
|
return OBJSname
|
|
return OBJSname;
|
|
|
|
def getparamtype( dmparam ):
|
|
ptype = None
|
|
for s in dmparam:
|
|
if s.tag == "syntax":
|
|
for c in s:
|
|
if c.tag == "list":
|
|
ptype = "string"
|
|
break
|
|
if c.tag == "dataType":
|
|
reftype = c.get("ref")
|
|
if "StatsCounter" in reftype:
|
|
ptype = "unsignedInt"
|
|
break
|
|
ptype = "string"
|
|
break
|
|
ptype = c.tag
|
|
break
|
|
break
|
|
if ptype == None:
|
|
ptype = "__NA__"
|
|
return ptype
|
|
|
|
def getparamrange( dmparam ):
|
|
min = None
|
|
max = None
|
|
for s in dmparam:
|
|
if s.tag == "syntax":
|
|
for c in s:
|
|
for o in c:
|
|
if o.tag == "range":
|
|
min = o.get("minInclusive")
|
|
max = o.get("maxInclusive")
|
|
break
|
|
if min == None:
|
|
min = ""
|
|
if max == None:
|
|
max = ""
|
|
return min, max
|
|
|
|
def getparamunit( dmparam ):
|
|
unit = None
|
|
for s in dmparam:
|
|
if s.tag == "syntax":
|
|
for c in s:
|
|
for o in c:
|
|
if o.tag == "units":
|
|
unit = o.get("value")
|
|
break
|
|
if unit == None:
|
|
unit = ""
|
|
return unit
|
|
|
|
def getparamvalues( dmparam ):
|
|
hasvalues = 0
|
|
values = ""
|
|
for s in dmparam:
|
|
if s.tag == "syntax":
|
|
for c in s:
|
|
if c.tag == "string":
|
|
for a in c:
|
|
if a.tag == "enumeration":
|
|
hasvalues = 1
|
|
for x in c.findall('enumeration'):
|
|
if values:
|
|
values = "%s, \"%s\"" % (values, x.get('value'))
|
|
else:
|
|
values = "\"%s\"" % x.get('value')
|
|
break
|
|
|
|
break
|
|
return hasvalues, values
|
|
|
|
def objhaschild (parentname, level):
|
|
hasobj = 0
|
|
for c in model:
|
|
objname = c.get('name')
|
|
if c.tag == "object" and parentname in objname and (objname.count('.') - objname.count('{i}')) == level:
|
|
hasobj = 1
|
|
break;
|
|
return hasobj
|
|
|
|
def objhasparam (dmobject):
|
|
hasparam = 0
|
|
for c in dmobject:
|
|
if c.tag == "parameter":
|
|
hasparam = 1
|
|
break;
|
|
return hasparam
|
|
|
|
def printopenobject (obj):
|
|
fp = open('./.json_tmp', 'a')
|
|
print >> fp, "\"%s\" : {" % obj.get('name')
|
|
fp.close()
|
|
|
|
def printopenfile ():
|
|
fp = open('./.json_tmp', 'a')
|
|
print >> fp, "{"
|
|
fp.close()
|
|
|
|
def printclosefile ():
|
|
fp = open('./.json_tmp', 'a')
|
|
print >> fp, "}"
|
|
fp.close()
|
|
|
|
def removelastline ():
|
|
file = open("./.json_tmp")
|
|
lines = file.readlines()
|
|
lines = lines[:-1]
|
|
file.close()
|
|
w = open("./.json_tmp",'w')
|
|
w.writelines(lines)
|
|
w.close()
|
|
printclosefile ()
|
|
|
|
def replace_data_in_file( data_in, data_out ):
|
|
file_r = open("./.json_tmp", "rt")
|
|
file_w = open("./.json_tmp_1", "wt")
|
|
text = ''.join(file_r).replace(data_in, data_out)
|
|
file_w.write(text)
|
|
file_r.close()
|
|
file_w.close()
|
|
copyfile("./.json_tmp_1", "./.json_tmp")
|
|
removefile("./.json_tmp_1")
|
|
|
|
def updatejsontmpfile ():
|
|
replace_data_in_file ("}\n", "},\n")
|
|
replace_data_in_file ("},\n},", "}\n},")
|
|
replace_data_in_file ("}\n},\n},", "}\n}\n},")
|
|
replace_data_in_file ("}\n},\n}\n},", "}\n}\n}\n},")
|
|
replace_data_in_file ("}\n},\n}\n}\n},", "}\n}\n}\n}\n},")
|
|
replace_data_in_file ("}\n}\n}\n},\n}\n},", "}\n}\n}\n}\n}\n},")
|
|
replace_data_in_file ("}\n}\n}\n}\n}\n}\n},", "}\n}\n}\n}\n}\n}\n},")
|
|
|
|
def removetmpfiles():
|
|
removefile("./.json_tmp")
|
|
removefile("./.json_tmp_1")
|
|
|
|
def printOBJ( dmobject, hasobj, hasparam ):
|
|
if (dmobject.get('name')).endswith(".{i}."):
|
|
fbrowse = "true"
|
|
else:
|
|
fbrowse = "false"
|
|
|
|
fp = open('./.json_tmp', 'a')
|
|
print >> fp, "\"type\" : \"object\","
|
|
if (dmobject.get('access') == "readOnly"):
|
|
print >> fp, "\"access\" : \"false\","
|
|
else:
|
|
print >> fp, "\"access\" : \"true\","
|
|
if hasparam or hasobj:
|
|
print >> fp, "\"array\" : \"%s\"," % fbrowse
|
|
else:
|
|
print >> fp, "\"array\" : \"%s\"" % fbrowse
|
|
fp.close()
|
|
|
|
def printPARAM( dmparam ):
|
|
ptype = getparamtype(dmparam)
|
|
min, max = getparamrange(dmparam)
|
|
unit = getparamunit(dmparam)
|
|
hasvalues, values = getparamvalues(dmparam)
|
|
if (dmparam.get('access') == "readOnly"):
|
|
access = "false"
|
|
else:
|
|
access = "true"
|
|
|
|
fp = open('./.json_tmp', 'a')
|
|
print >> fp, "\"%s\" : {" % dmparam.get('name')
|
|
print >> fp, "\"type\" : \"%s\"," % ptype
|
|
if min != "" and max != "":
|
|
print >> fp, "\"range\" : {"
|
|
print >> fp, "\"min\" : \"%s\"," % min
|
|
print >> fp, "\"max\" : \"%s\"" % max
|
|
print >> fp, "},"
|
|
elif min != "" and max == "":
|
|
print >> fp, "\"range\" : {"
|
|
print >> fp, "\"min\" : \"%s\"" % min
|
|
print >> fp, "},"
|
|
elif min == "" and max != "":
|
|
print >> fp, "\"range\" : {"
|
|
print >> fp, "\"max\" : \"%s\"" % max
|
|
print >> fp, "},"
|
|
if unit != "":
|
|
print >> fp, "\"unit\" : \"%s\"," % unit
|
|
print >> fp, "\"read\" : \"true\","
|
|
if hasvalues:
|
|
print >> fp, "\"write\" : \"%s\"," % access
|
|
print >> fp, "\"values\": [%s]" % values
|
|
else:
|
|
print >> fp, "\"write\" : \"%s\"" % access
|
|
print >> fp, "}"
|
|
fp.close()
|
|
|
|
def printusage():
|
|
print "Usage: " + sys.argv[0] + " <xml data model> [Object path]...[Object path]"
|
|
print "Examples:"
|
|
print " - " + sys.argv[0] + " tr-181-2-12-0-cwmp-full.xml Device.WiFi."
|
|
print " ==> Generate the json file of the sub tree Device.WiFi. in wifi.json"
|
|
print " - " + sys.argv[0] + " tr-181-2-12-0-cwmp-full.xml Device.IP.Diagnostics."
|
|
print " ==> Generate the json file of the sub tree Device.IP.Diagnostics. in ipdiagnostics.json"
|
|
print " - " + sys.argv[0] + " tr-181-2-12-0-cwmp-full.xml Device.WiFi. Device.Time."
|
|
print " ==> Generate the json file of the sub tree Device.IP. and Device.WiFi. in time.json and wifi.json"
|
|
print " - " + sys.argv[0] + " tr-181-2-12-0-cwmp-full.xml Device."
|
|
print " ==> Generate the json file of all data model in rootdevice.json"
|
|
print "Example of xml data model file: https://www.broadband-forum.org/cwmp/tr-181-2-12-0-cwmp-full.xml"
|
|
|
|
def getobjectpointer( objname ):
|
|
obj = None
|
|
for c in model:
|
|
if c.tag == "object" and (c.get('name') == objname or c.get('name') == (objname + "{i}.")):
|
|
obj = c
|
|
break
|
|
return obj
|
|
|
|
def object_parse_childs( dmobject, level):
|
|
hasobj = objhaschild(dmobject.get('name'), level)
|
|
hasparam = objhasparam(dmobject)
|
|
|
|
printOBJ(dmobject, hasobj, hasparam)
|
|
|
|
if hasparam:
|
|
for c in dmobject:
|
|
paramname = c.get('name')
|
|
if c.tag == "parameter":
|
|
printPARAM(c)
|
|
|
|
if hasobj:
|
|
for c in model:
|
|
objname = c.get('name')
|
|
if c.tag == "object" and dmobject.get('name') in objname and (objname.count('.') - objname.count('{i}')) == level:
|
|
printopenobject(c)
|
|
object_parse_childs(c, level+1)
|
|
printclosefile ()
|
|
|
|
return;
|
|
|
|
def generatejsonfromobj(pobj, pdir):
|
|
securemkdir(pdir)
|
|
removetmpfiles()
|
|
dmlevel = (pobj.get('name')).count(".") - (pobj.get('name')).count("{i}.") + 1
|
|
printopenfile ()
|
|
printopenobject(pobj)
|
|
object_parse_childs(pobj, dmlevel)
|
|
dmfp = open(pdir + "/" + (getname(pobj.get('name'))).lower() + ".json", "a")
|
|
printclosefile ()
|
|
printclosefile ()
|
|
updatejsontmpfile ()
|
|
removelastline ()
|
|
|
|
with open("./.json_tmp", "r") as f:
|
|
obj = json.load(f, object_pairs_hook=OrderedDict)
|
|
dump = json.dumps(obj, indent=4)
|
|
tabs = re.sub('\n +', lambda match: '\n' + '\t' * (len(match.group().strip('\n')) / 4), dump)
|
|
|
|
try:
|
|
print >> dmfp, "%s" % tabs
|
|
dmfp.close()
|
|
except:
|
|
pass
|
|
|
|
removetmpfiles()
|
|
|
|
### main ###
|
|
if len(sys.argv) < 3:
|
|
printusage()
|
|
exit(1)
|
|
|
|
if (sys.argv[1]).lower() == "-h" or (sys.argv[1]).lower() == "--help":
|
|
printusage()
|
|
exit(1)
|
|
|
|
model_root_name = "Root"
|
|
tree = xml.parse(sys.argv[1])
|
|
|
|
xmlroot = tree.getroot()
|
|
model = xmlroot
|
|
|
|
for child in model:
|
|
if child.tag == "model":
|
|
model = child
|
|
|
|
if model.tag != "model":
|
|
print "Wrong XML Data model format!"
|
|
exit(1)
|
|
|
|
dmroot = None
|
|
for c in model:
|
|
if c.tag == "object" and c.get("name").count(".") == 1:
|
|
dmroot = c
|
|
break;
|
|
|
|
if dmroot == None:
|
|
print "Wrong XML Data model format!"
|
|
exit(1)
|
|
|
|
gendir = "source_" + time.strftime("%Y-%m-%d_%H-%M-%S")
|
|
isemptytreeargs = 1
|
|
|
|
if (len(sys.argv) > 2):
|
|
for i in range(2, len(sys.argv)):
|
|
if sys.argv[i] == "":
|
|
continue
|
|
isemptytreeargs = 0
|
|
objstart = getobjectpointer(sys.argv[i])
|
|
if objstart == None:
|
|
print "Wrong Object Name! %s" % sys.argv[i]
|
|
continue
|
|
generatejsonfromobj(objstart, gendir)
|
|
|
|
if (os.path.isdir(gendir)):
|
|
print "Json file generated under \"./%s\"" % gendir
|
|
else:
|
|
print "No json file generated!"
|
|
|