diff --git a/pysd/py_backend/builder.py b/pysd/py_backend/builder.py index 89ce584e..90d43020 100644 --- a/pysd/py_backend/builder.py +++ b/pysd/py_backend/builder.py @@ -301,7 +301,6 @@ def _build_main_module(elements, subscript_dict, file_name): """ % { "outfile": os.path.basename(file_name).split(".")[0], }) - print(text) text += funcs text = black.format_file_contents(text, fast=True, mode=black.FileMode()) @@ -1916,12 +1915,15 @@ def add_ext_lookup(identifier, file_name, tab, x_row_or_col, cell, return "%s(x)" % external["py_name"], [external] -def add_macro(macro_name, filename, arg_names, arg_vals): +def add_macro(identifier, macro_name, filename, arg_names, arg_vals): """ - Constructs a stateful object instantiating a 'Macro' + Constructs a stateful object instantiating a 'Macro'. Parameters ---------- + identifier: str + The python-safe name of the element that calls the macro. + macro_name: str Python safe name for macro. @@ -1934,16 +1936,16 @@ def add_macro(macro_name, filename, arg_names, arg_vals): Returns ------- reference: str - reference to the Initial object `__call__` method, - which will return the first calculated value of `initial_input` + Reference to the Initial object `__call__` method, + which will return the first calculated value of `initial_input`. + new_structure: list - list of element construction dictionaries for the builder to assemble + List of element construction dictionaries for the builder to assemble. """ Imports.add("functions", "Macro") - py_name = "_macro_" + macro_name + "_" + "_".join( - [utils.make_python_identifier(f)[0] for f in arg_vals]) + py_name = "_macro_" + macro_name + "_" + identifier func_args = "{ %s }" % ", ".join( ["'%s': lambda: %s" % (key, val) for key, val in zip(arg_names, @@ -1951,7 +1953,7 @@ def add_macro(macro_name, filename, arg_names, arg_vals): stateful = { "py_name": py_name, - "parent_name": macro_name, + "parent_name": identifier, "real_name": "Macro Instantiation of " + macro_name, "doc": "Instantiates the Macro", "py_expr": "Macro('%s', %s, '%s'," diff --git a/pysd/py_backend/utils.py b/pysd/py_backend/utils.py index 5947bf15..45b87881 100644 --- a/pysd/py_backend/utils.py +++ b/pysd/py_backend/utils.py @@ -890,8 +890,37 @@ def open_module(root_dir, model_name, module, submodule=None): def load_modules(module_name, module_content, work_dir, submodules): - # TODO: document + """ + Used to load model modules from the main model file, when + split_views=True in the read_vensim function. This function is used + to iterate over the different layers of the nested dictionary that + describes which model variables belong to each module/submodule. + + Parameters + ---------- + module_name: str + Name of the module to load. + + module_content: dict or list + Content of the module. If it's a dictionary, it means that the + module has submodules, whereas if it is a list it means that that + particular module/submodule is a final one. + + work_dir: str + Path to the module file. + submodules: list + This list gets updated at every recursive iteration, and each element + corresponds to the string representation of each module/submodule that + is read. + + Returns + ------- + str: + String representations of the modules/submodules to execute in the main + model file. + + """ if isinstance(module_content, list): with open(os.path.join(work_dir, module_name + ".py"), "r") as file: submodules.append(file.read()) diff --git a/pysd/py_backend/vensim/vensim2py.py b/pysd/py_backend/vensim/vensim2py.py index d658c6e7..f4eb1a5f 100644 --- a/pysd/py_backend/vensim/vensim2py.py +++ b/pysd/py_backend/vensim/vensim2py.py @@ -1435,7 +1435,7 @@ def visit_macro_call(self, n, vc): macro = [x for x in macro_list if x["py_name"] == py_name][ 0 ] # should match once - name, structure = builder.add_macro( + name, structure = builder.add_macro(element["py_name"], macro["py_name"], macro["file_name"], macro["params"], arglist ) self.new_structure += structure