50 lines
2.0 KiB
Python
50 lines
2.0 KiB
Python
"""Measure JSON validation, input normalization and strict XML construction separately.
|
|
Run from the repository root with its Python environment; artifacts are ignored.
|
|
"""
|
|
import json
|
|
from pathlib import Path
|
|
from statistics import median
|
|
from time import perf_counter_ns
|
|
|
|
from app.main import ReactFlowProjectPayload, build_reactflow_system_xml
|
|
from app.project_parameters import prepare_project
|
|
|
|
|
|
def measure(fn, repeat=200):
|
|
for _ in range(10):
|
|
fn()
|
|
samples = []
|
|
for _ in range(repeat):
|
|
start = perf_counter_ns()
|
|
fn()
|
|
samples.append((perf_counter_ns() - start) / 1e6)
|
|
samples.sort()
|
|
return {"medianMs": median(samples), "p95Ms": samples[int(.95 * len(samples))], "samples": repeat}
|
|
|
|
|
|
def main():
|
|
source = Path("tests/data/test-mql-8-corrected.json")
|
|
raw = json.loads(source.read_text(encoding="utf-8"))
|
|
current = ReactFlowProjectPayload.model_validate(raw)
|
|
old = current.model_copy(deep=True)
|
|
for node in old.nodes:
|
|
node.data.modelVersion = "0.0.1"
|
|
normalized, _ = prepare_project(current)
|
|
metrics = {
|
|
"source": str(source), "nodes": len(current.nodes),
|
|
"parameters": sum(len(n.data.parameters) for n in current.nodes),
|
|
"pydanticInput": measure(lambda: ReactFlowProjectPayload.model_validate(raw)),
|
|
"prepareCurrent": measure(lambda: prepare_project(current)),
|
|
"prepareAllOld": measure(lambda: prepare_project(old)),
|
|
"strictXmlAfterPreparation": measure(lambda: build_reactflow_system_xml(normalized)),
|
|
"notes": "prepare includes a defensive copy, parameter/expression/unit conversion, version comparison and simulation time normalization; not version checking alone.",
|
|
}
|
|
destination = Path("test/project-contract-20260912/backend-input-timing.json")
|
|
destination.parent.mkdir(parents=True, exist_ok=True)
|
|
destination.write_text(json.dumps(metrics, indent=2), encoding="utf-8")
|
|
print(json.dumps(metrics, indent=2))
|
|
|
|
|
|
if __name__ == "__main__":
|
|
main()
|