mirror of
https://github.com/Screenly/Anthias.git
synced 2026-06-10 00:57:38 -04:00
* fix(server): restore multi-file (bulk) upload in the Add Asset modal Multi-file upload (added in #2778 for the React UI) was lost in the #2818 React→Alpine/HTMX rewrite: the file picker accepted a single file only. The assets_upload endpoint already takes one file per POST, so this is a client-only fix. - Add `multiple` to the #add-file input. - Drive the upload from uploadFiles() in home.ts: iterate the selected files and POST them sequentially (one XHR per file) against the existing single-file endpoint, with "X of N" progress. htmx's single-form submit would only ever send the first file, so the file tab is no longer htmx-managed; toasts are replayed from the server's HX-Trigger header by hand. - Single-file uploads still flow through the same path unchanged. Adds an integration test (test_add_multiple_uploads_at_once) that selects two files in one go and asserts both persist. Fixes #3045 Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * fix(server): don't clear upload state on closeModal mid-batch Hiding the modal during an in-flight 'sending' upload cleared uploadState, which disarmed uploadFiles()'s re-entry guard and let a reopened modal start a second batch racing the first over the shared progress/index fields. Only reset upload state when nothing is in flight. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * fix(server): surface upload rejections instead of swallowing them assets_upload refused invalid/empty uploads with messages.error + HTTP 200, which the HTMX/XHR path drops silently (the partial carries no toast header) — so the operator saw nothing and the batch uploader counted the rejection as a success. Pass the rejection through _asset_table_response(toast=('error', …)) so it rides the HX-Trigger header on every transport. Client side, uploadOne() now distinguishes 'ok' / 'rejected' (2xx + error toast) / 'error' (transport): a rejected file surfaces its server toast and the batch skips it and keeps going, while a true transport failure aborts. Addresses Copilot review feedback. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * docs(server): update uploadOne comment for the UploadResult return The doc comment still described the old boolean return; it now documents the ok / rejected / error tri-state. Comment-only. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * docs(server): attribute single-file limit to the endpoint, not htmx The comments said htmx "would only ever send the first file", but htmx includes every selected file in the multipart body — the real single-file constraint is assets_upload reading request.FILES.get. Reword both comments. Comment-only. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>