infra-praesi/source/lib.py

200 lines
3.6 KiB
Python
Raw Permalink Normal View History

2024-07-12 11:19:40 +02:00
import os as _os
def convey(x, fs):
y = x
for f in fs:
y = f(y)
return y
def string_coin(template, arguments, options = None):
options = (
{
"open": "{{",
"close": "}}",
}
|
(options or {})
)
result = template
for (key, value, ) in arguments.items():
if (value is None):
pass
else:
result = result.replace(
(
"%s%s%s"
% (
options["open"],
key,
options["close"],
)
),
value
)
return result
def file_read(path):
handle = open(path, "r")
content = handle.read()
handle.close()
return content
def file_write(path, content):
_os.makedirs(_os.path.dirname(path), exist_ok = True)
handle = open(path, "w" if _os.path.exists(path) else "a")
handle.write(content)
handle.close()
return None
def dot_entry(head, attributes, options = None):
options = (
{
"indentation": 0,
}
|
(options or {})
)
return string_coin(
"{{indentation}}{{head}} [{{attributes}}];\n",
{
"indentation": ("\t" * options["indentation"]),
"head": head,
"attributes": convey(
attributes,
[
lambda x: x.items(),
lambda x: map(
lambda pair: string_coin(
"{{key}}=\"{{value}}\"",
{
"key": pair[0],
"value": pair[1]
}
),
x
),
", ".join,
]
),
}
)
def dot_node(node, options = None):
options = (
{
"indentation": 0,
}
|
(options or {})
)
return dot_entry(
string_coin("{{name}}", {"name": node["name"]}),
node["attributes"],
options
)
def dot_edge(edge, options = None):
options = (
{
"indentation": 0,
}
|
(options or {})
)
return dot_entry(
string_coin("{{name_from}} -> {{name_to}}", {"name_from": edge["name_from"], "name_to": edge["name_to"]}),
edge["attributes"],
options
)
def dot_subgraph(subgraph, options = None):
options = (
{
"indentation": 0,
}
|
(options or {})
)
return string_coin(
(
"{{indentation}}subgraph cluster_{{name}}\n"
+
"{{indentation}}{\n"
+
"{{attributes}}\n"
+
"{{nodes}}\n"
+
"{{edges}}\n"
+
"{{indentation}}}\n"
),
{
"indentation": ("\t" * options["indentation"]),
"name": subgraph["name"],
"attributes": convey(
subgraph["attributes"],
[
lambda x: x.items(),
lambda x: map(
lambda pair: string_coin(
"{{indentation}}{{key}}=\"{{value}}\";\n",
{
"indentation": ("\t" * (options["indentation"] + 1)),
"key": pair[0],
"value": pair[1]
}
),
x
),
"".join,
]
),
"nodes": "".join(map(lambda node: dot_node(node, {"indentation": (options["indentation"] + 1)}), subgraph["nodes"])),
"edges": "".join(map(lambda edge: dot_edge(edge, {"indentation": (options["indentation"] + 1)}), subgraph["edges"])),
}
)
def dot_graph(graph):
return string_coin(
(
"digraph {{name}}\n"
+
"{\n"
+
"{{settings_graph}}\n"
+
"{{settings_node}}\n"
+
"{{settings_edge}}\n"
+
"{{subgraphs}}\n"
+
"{{nodes}}\n"
+
"{{edges}}\n"
+
"}\n"
),
{
"name": graph["name"],
"settings_graph": dot_entry("graph", graph["settings"]["graph"], {"indentation": 1}),
"settings_node": dot_entry("node", graph["settings"]["node"], {"indentation": 1}),
"settings_edge": dot_entry("edge", graph["settings"]["edge"], {"indentation": 1}),
"nodes": "".join(map(lambda node: dot_node(node, {"indentation": 1}), graph["nodes"])),
"edges": "".join(map(lambda edge: dot_edge(edge, {"indentation": 1}), graph["edges"])),
"subgraphs": "".join(map(lambda subgraph: dot_subgraph(subgraph, {"indentation": 1}), graph["subgraphs"])),
}
)