Commit Graph

8 Commits

Author SHA1 Message Date
wenil 3418e01689 holder: cap total cells at 1000 to prevent runaway renders
User-triggered 120x120 = 14400 cells, which produces huge STL/long
renders. Total cells is the right metric (CSG cost scales with count,
not max axis), so cap by N = rows*cols (or rows*(rows+1)/2 for tria
style). 1000 covers any realistic pack (e.g. 20x50) while blocking
accidental misuse.

Backend:
- holder.py: MAX_CELLS env-tunable (default 1000); expected_cell_count
  and _check_cell_limit raise ValueError on exceed; both
  compute_cells() and render_stl() call it up-front.
- app.py: /api/holder/render now returns 400 on ValueError (not 500)
  so the frontend can distinguish bad input from server failure.
  /api/holder/params now publishes max_cells alongside the schema.

Frontend:
- holder-app.js: reads max_cells from the params endpoint; status
  shows "N cells / over limit (1000)" in red and disables the
  Render and "Design busbars" buttons when exceeded.
- holder.css: .topbar-status.over-limit style (red, bold).
2026-05-25 11:49:28 +03:00
wenil 0aa38809b4 holder: switch to OpenSCAD Manifold backend (10-50x faster renders)
OpenSCAD 2021.01 (Debian 13 default) is single-threaded CGAL. The Manifold
backend, available in OpenSCAD 2024+, parallelises CSG operations and
gives massive speedups on multi-cell holders.

Bench on this LXC (6 cores), realistic params:
  6x12  (72 cells):  CGAL  3.14s -> Manifold 0.08s   (37x)
  10x20 (200 cells): -                       1.41s
  15x25 (375 cells): -                       1.97s

Installation steps performed on the server (manual, not in this repo):
  wget https://files.openscad.org/snapshots/OpenSCAD-2026.04.26-x86_64.AppImage
  ./AppImage --appimage-extract  (no FUSE required)
  ln -s squashfs-root/AppRun /usr/local/bin/openscad-nightly

Code changes:
- holder.py: new OPENSCAD_BACKEND env var (default "Manifold");
  appends "--backend Manifold" to the openscad call when set.
- deploy/busbar-designer.service: points OPENSCAD_BIN at the
  extracted nightly and sets OPENSCAD_BACKEND=Manifold.

Real-time progress percentage was investigated but not implemented:
OpenSCAD has no headless --progress flag, so live % from the CLI is
not feasible. With Manifold making renders sub-second to a few seconds,
the existing indeterminate progress bar + elapsed timer is sufficient.
2026-05-25 11:35:20 +03:00
wenil af3ed092dc holder: explicit Render button + progress UI + longer render timeout
- Replace debounced auto-render-on-param-change with an explicit Render
  button. Param changes mark the button "dirty" (accent ring); user clicks
  Render to drive a render. A Cancel button (AbortController) appears
  while a render is in flight.
- Add indeterminate progress bar with elapsed-time counter in the status
  panel. Real OpenSCAD --progress streaming can come later.
- Bump OPENSCAD_TIMEOUT default 60s -> 300s and gunicorn --timeout
  120s -> 300s. The 60s cap was misclassified by the frontend as
  "OpenSCAD not installed" because the error string contained the word
  "openscad" -- which the JS matched too greedily.
- Frontend error classifier now distinguishes "binary not found",
  "timed out", and "geometry empty" cases and only shows the
  install-OpenSCAD hint for the real not-found case.
2026-05-25 11:22:04 +03:00
wenil 1fadef0b3f systemd: redirect HOME / XDG dirs into project so ProtectHome stays on
ezdxf, matplotlib, and other Python libs try to write into $HOME/.config
and $HOME/.cache. With ProtectHome=true the real /home/busbar is invisible
to the service and pathlib.Path.exists() throws PermissionError.

Fix: set HOME, XDG_CONFIG_HOME, XDG_CACHE_HOME to /opt/busbar-designer/data/*
which is already in ReadWritePaths. Hardening (ProtectHome) stays intact.

install.sh also pre-creates the .config / .cache subdirs.
2026-05-25 09:38:39 +03:00
wenil a16952f7c5 install.sh: rebuild venv if pip missing (Debian 13 / Python 3.13 quirk)
On Debian 13 with Python 3.13, `python3 -m venv` sometimes finishes without
pip if the user pasted commands that got interrupted (Ctrl-Z, broken pipe).
Now we (1) detect missing pip and tear down + recreate the venv, (2) fall
back to `ensurepip` if even a fresh venv lacks pip. Also dropped --quiet
so install progress is visible.
2026-05-25 09:23:20 +03:00
wenil cd2840fbb3 Remove proxmox-lxc.sh; recommend manual LXC creation via Proxmox UI
The whiptail helper added cognitive overhead without saving much time vs.
the standard Proxmox web UI. Removed it from deploy/ and rewrote README +
deploy/README to point at the manual flow:

  1. Create LXC via Proxmox UI (Debian 12, 4c/8GB/32GB, nesting=1)
  2. Inside: curl deploy/install.sh — provisions everything

install.sh and update.sh stay (those are useful).
2026-05-24 19:51:30 +03:00
wenil 6bc922cabf Add hex holder designer page (/holder)
Server-side OpenSCAD renders STL from bundled hex_cell.scad with parameter
overrides via -D. Frontend is a Three.js viewer with auto-form generated
from /api/holder/params. 'Design busbars →' button posts the computed
cell coordinates to /api/projects and redirects to the busbar editor with
the holder cells pre-loaded.

  - holder.py:                openscad subprocess wrapper + compute_cells()
                              (Python mirror of get_hex_center_points_*)
  - scad/hex_cell.scad:       verbatim copy of Addy/Hex-Cell-Holder source
  - app.py:                   /holder route + /api/holder/{params,render,cells}
  - static/holder.html etc:   parameter form + Three.js STL viewer
  - Dockerfile / install.sh:  apt install openscad
  - static/index.html:        nav link Holder ↔ Busbars in topbar
2026-05-24 19:27:50 +03:00
wenil d8cb0dc06d Initial commit: Busbar Designer
Web tool for designing nickel/copper busbars over cylindrical-cell battery
packs (21700, 18650) in hex holders. Flask + build123d backend exports
STEP/DXF/SVG; vanilla JS frontend with live preview, multi-project SQLite
persistence, snapshot history.

Deploy scripts in deploy/ (proxmox-lxc.sh, install.sh, update.sh).
2026-05-24 18:59:50 +03:00