Source code for pycropml.transpiler.antlr_py.dssat.dssatExtraction


# coding: utf-8
""" A simple Strategy class
 In the constructor (Parameters description, Input and Output name, category)
 In SetPublisherData method (author, institution)
 In Domain property (Composite name)
 In URL property (URL)
 In Description property (Description)

 """
from pycropml.transpiler.antlr_py.extract_metadata import MetaExtraction
from pycropml.transpiler.antlr_py.extract_metadata_from_comment import ExtractComments, extract_compo
from pycropml.transpiler.antlr_py.extraction import ExtractComments


[docs] class DssatExtraction(MetaExtraction): def __init__(self): MetaExtraction.__init__(self) self.inputs = [] self.outputs = [] self.model = None self.mc = None
[docs] def getProcess(self, tree): self.getTypeNode(tree, "function_definition") print([m.name for m in self.getTree]) res = [] for n in self.getTree: if n.comments: if n.comments[-1]=="!%%ModelUnit_Start%%": res.append(n) return res
[docs] def getSubroutine(self, tree, name=None): self.getTypeNode(tree, "function_definition") functionNode = self.getTree if name:functions = self.getAttNode(functionNode,**{"name":name}) else: return functionNode return functions[0] if functions else []
[docs] def getModule(self, tree, name): self.getTypeNode(tree, "module") moduleNode = self.getTree module = self.getAttNode(moduleNode,**{"name":name}) return module[0] if module else []
[docs] def getDecl(self, tree, modulenames, varnames): """Get declarations of variables provided from modules imports Args: tree (Node): ASG of the code from the merging of all source files modulenames (list): List of the modules names imported in a specific subroutine or function varnames (list): list of variables not declared in a specific subroutine or function Returns: dict: dictionary where the key is the name of the variable and its value is its declaration Node """ res = {} for modulename in modulenames: m = self.getModule(tree, modulename) for varname in varnames: decl = self.getDeclaration(m,varname) if decl: res[varname] = decl continue return res
[docs] def getStruct(self, tree, name): self.getTypeNode(tree, "struct") structNode = self.getTree structs = self.getAttNode(structNode,**{"name":name}) return structs[0] if structs else []
[docs] def getDeclaration(self, tree, name): self.getTypeNode(tree, "declaration") declNodes = self.getTree declNode = [] for d in declNodes: declNode.extend(d.decl) decls = self.getAttNode(declNode,**{"name":name}) return decls[0] if decls else []
[docs] def modelunit(self, file, tree): self.model = self.getFromComment(file, "!", "////", "////") funcs = self.externFunction(tree) self.model.function = funcs
[docs] def externFunction(self, algo): self.getTypeNode(algo, "call_stmt") custom_call = self.getTree methNames = set({c.name for c in custom_call}) if custom_call else set() return methNames
[docs] def notRequiredFunc(self, tree): self.getTypeNode(tree, "function_definition") res = [] for n in self.getTree: if n.comments: if n.comments[-1]=='!%%NotRequired%%': res.append(n) names = [n.name for n in res] return set(names)
[docs] def modelcomposition(self, file, models, tree): comments = ExtractComments(file, "!", "////", "////") newcom = list(comments.values()) com = '\n'.join(newcom) self.mc = extract_compo(com) inputlink = [] outputlink = [] subroutines = self.getSubroutine(tree) algo = [f for f in subroutines if f.name.startswith("model")] self.getTypeNode(algo[0].block,"custom_call") call = self.getTree self.mc.model = [c.function.split("model_")[-1] for c in call] inps, outs = [], [] md = [n for m in self.mc.model for n in models if m == n.name.split("model_")[-1]] inps = [n.name for m in md for n in m.inputs ] outs = [n.name for m in md for n in m.outputs ] m_in = set(inps) - set(outs) z = {} internallink= [] for m in md: vi = list(set([n.name for n in m.inputs ]).intersection(m_in)) vo = [n.name for n in m.outputs] for v in vi: inputlink.append({"target": m.name + "." + v, "source":v}) for v in vo: z.update({v:m.name}) for k, v in z.items(): outputlink.append({"source": v + "." + k, "target":k}) for i in range(0, len(md)-1): mi = md[i] for j in range(i+1, len(md)): mj = md[j] vi = list(set([n.name for n in mi.outputs ]).intersection(set([n.name for n in mj.inputs ]))) if vi: for k in vi: internallink.append({"source": mi.name + "." + k, "target":mj.name + "." + k}) self.mc.inputlink = inputlink self.mc.outputlink = outputlink self.mc.internallink = internallink """ call = self.getAttNode(self.getTree, **{"function":"Estimate"}) self.mc.model = [c.namespace[1:] for c in call] inps, outs = [], [] md = [n for m in self.mc.model for n in models if m == n.name] inps = [n.name for m in md for n in m.inputs ] outs = [n.name for m in md for n in m.outputs ] m_in = set(inps) - set(outs) z = {} internallink= [] for m in md: vi = list(set([n.name for n in m.inputs ]).intersection(m_in)) vo = [n.name for n in m.outputs] for v in vi: inputlink.append({"target": m.name + "." + v, "source":v}) for v in vo: z.update({v:m.name}) for k, v in z.items(): outputlink.append({"source": v + "." + k, "target":k}) for i in range(0, len(md)-1): mi = md[i] for j in range(i+1, len(md)): mj = md[j] vi = list(set([n.name for n in mi.outputs ]).intersection(set([n.name for n in mj.inputs ]))) if vi: for k in vi: internallink.append({"source": mi.name + "." + k, "target":mj.name + "." + k}) self.mc.inputlink = inputlink self.mc.outputlink = outputlink self.mc.internallink = internallink"""