from __future__ import annotations from pathlib import Path from typing import Any STRICT = {"surface_mm": 0.01, "bbox_mm": 0.01, "volume_relative": 1e-5, "area_relative": 1e-5} RP = {"surface_mm": 0.02, "bbox_mm": 0.02, "volume_relative": 0.005, "area_relative": 0.005} def _assess(report: dict[str, Any], limits: dict[str, float]) -> dict[str, Any]: surface = report["surface"]; metrics = report["metrics"] maximum = [surface["gold_to_rebuilt"]["max_mm"], surface["rebuilt_to_gold"]["max_mm"]] p99 = [surface["gold_to_rebuilt"]["p99_mm"], surface["rebuilt_to_gold"]["p99_mm"]] surface_ready = all(isinstance(value, (int, float)) for value in [*maximum, *p99]) checks = { "surface_max": surface_ready and max(maximum) <= limits["surface_mm"], "surface_p99": surface_ready and max(p99) <= limits["surface_mm"], "bbox": isinstance(metrics["bbox_max_delta_mm"], (int, float)) and metrics["bbox_max_delta_mm"] <= limits["bbox_mm"], "volume": metrics["volume_relative_error"] <= limits["volume_relative"], "area": metrics["surface_area_relative_error"] <= limits["area_relative"], "solid_count": metrics["gold_solid_count"] == metrics["rebuilt_solid_count"], } return {"passed": all(checks.values()), "limits": limits, "checks": checks} def compare_steps(gold_step: Path, rebuilt_step: Path, *, surface_tessellation_mm: float = 0.05) -> dict[str, Any]: from onshape_to_cdsl.compare import strict_compare raw = strict_compare( gold_step, rebuilt_step, surface_tolerance_mm=surface_tessellation_mm, fast_reject_relative_error=RP["volume_relative"], ) strict, rp = _assess(raw, STRICT), _assess(raw, RP) decision = "strict_pass" if strict["passed"] else "approximate_pass" if rp["passed"] else "rejected" return {"schema": "cadfs_to_cdsl.comparison.v1", "gold_step": str(gold_step), "rebuilt_step": str(rebuilt_step), "raw": raw, "strict": strict, "rp": rp, "decision": decision}