From 838e8a9639cb992d0bad6320b88db38065b40fab Mon Sep 17 00:00:00 2001 From: bot-backend Date: Wed, 17 Jun 2026 20:00:43 +0300 Subject: [PATCH] fix(scripts): guard zero-division in vectorize summarise aggregate (#299) --- backend/scripts/spike_plan_vectorize.py | 40 +++++++++++++++++-------- 1 file changed, 27 insertions(+), 13 deletions(-) diff --git a/backend/scripts/spike_plan_vectorize.py b/backend/scripts/spike_plan_vectorize.py index a33987b0..2ffd2a77 100644 --- a/backend/scripts/spike_plan_vectorize.py +++ b/backend/scripts/spike_plan_vectorize.py @@ -93,9 +93,7 @@ def _require_binary(name: str) -> str: path = shutil.which(name) if path is None: logger.error("required binary %r not found on PATH", name) - raise SystemExit( - f"{name!r} not found — install it (e.g. `brew install {name}`) and retry" - ) + raise SystemExit(f"{name!r} not found — install it (e.g. `brew install {name}`) and retry") return path @@ -145,9 +143,13 @@ def svg_to_png(rsvg_bin: str, svg_path: Path, png_path: Path, *, width: int) -> try: subprocess.run( [ - rsvg_bin, "-w", str(width), + rsvg_bin, + "-w", + str(width), "--background-color=white", - "-o", str(png_path), str(svg_path), + "-o", + str(png_path), + str(svg_path), ], check=True, capture_output=True, @@ -216,8 +218,10 @@ def summarise(results: list[VectorizeResult]) -> None: print(f"max ratio : {max(ratios):.2f}x") total_raster = sum(r.raster_bytes for r in results) total_svg = sum(r.svg_bytes for r in results) - print(f"aggregate : {total_raster}B raster -> {total_svg}B svg " - f"({total_raster / total_svg:.2f}x overall)") + agg_ratio = total_raster / total_svg if total_svg else float("inf") + print( + f"aggregate : {total_raster}B raster -> {total_svg}B svg " f"({agg_ratio:.2f}x overall)" + ) def build_parser() -> argparse.ArgumentParser: @@ -225,27 +229,37 @@ def build_parser() -> argparse.ArgumentParser: description="Spike: contour-vectorize floor-plan rasters (PNG/JPG → SVG) via Potrace.", ) parser.add_argument( - "--in-dir", type=Path, required=True, + "--in-dir", + type=Path, + required=True, help="folder containing input rasters (PNG/JPG/...)", ) parser.add_argument( - "--out-dir", type=Path, required=True, + "--out-dir", + type=Path, + required=True, help="folder for output .pbm/.svg (and .rendered.png with --render-back)", ) parser.add_argument( - "--threshold", type=int, default=128, + "--threshold", + type=int, + default=128, help="grayscale ink/paper cutoff 0-255 (default 128)", ) parser.add_argument( - "--invert", action="store_true", + "--invert", + action="store_true", help="treat light strokes on a dark field as ink", ) parser.add_argument( - "--render-back", action="store_true", + "--render-back", + action="store_true", help="rasterise each SVG back to PNG via rsvg-convert for visual QA", ) parser.add_argument( - "--render-width", type=int, default=900, + "--render-width", + type=int, + default=900, help="width in px for --render-back output (default 900)", ) return parser