Frontend in web/ (Vite via bun, pure CSS, no component libraries), built to internal/dashboard/dist and embedded into the binary; the Dockerfile builds it in a bun stage. Old static dashboard.html removed.
Static non-root alpine image; tunneld must own host ports 443/80 directly since visitor TLS is SNI-routed and never proxy-terminated.