From ecf559cd6df4d90afe0fb5ec12cc0d11b092d8c6 Mon Sep 17 00:00:00 2001 From: Kyle Date: Mon, 20 Jul 2026 21:48:43 -0400 Subject: [PATCH] Refactor folder_library preview to delegate to song_preview Remove audio member resolution from folder_library and delegate hover-preview audio to the canonical song_preview plugin endpoint. This separates concerns: folder_library now only builds the preview URL with the filename, while song_preview handles manifest resolution (preview: key, stem fallback) and Range support. Changes: - Remove _audio_member() resolver and audio_member field from pack metadata - Update _previewUrl() to point to /api/plugins/song_preview/audio?file= - Add _previewMissing cache to avoid re-requesting packs with no preview - Add HEAD probe to check preview availability before playing - Add test coverage for _previewUrl with special character encoding Signed-off-by: Kyle --- plugins/folder_library/CLAUDE.md | 7 +- plugins/folder_library/routes.py | 35 +-------- plugins/folder_library/screen.js | 44 +++++++----- .../folder_library/tests/preview_url.test.js | 71 +++++++++++++++++++ 4 files changed, 100 insertions(+), 57 deletions(-) create mode 100644 plugins/folder_library/tests/preview_url.test.js diff --git a/plugins/folder_library/CLAUDE.md b/plugins/folder_library/CLAUDE.md index 4fbb0e3..c77ffc8 100644 --- a/plugins/folder_library/CLAUDE.md +++ b/plugins/folder_library/CLAUDE.md @@ -153,15 +153,14 @@ Each song object (built by `_meta()`): "added": 1748132400.0, "arrangements": ["Lead", "Rhythm", "Bass"], "stems": ["Drums", "Bass", "Vocals"], - "lyrics": true, - "audio_member": "preview.ogg" + "lyrics": true } ``` - `filename` is the full relative path from the DLC root — pass it directly to `window.playSong()`. - `added` is a Unix timestamp (float, seconds) from `stat().st_mtime` — convert with `new Date(added * 1000)`. Always recomputed fresh (it changes when a file moves), even on a metadata-cache hit. - `arrangements` / `stems` are flat lists of **strings**, even though `extract_meta()` returns them as objects. -- `audio_member` is the best in-pack audio file for **hover-preview**, resolved by `_audio_member()` (`preview.ogg` → `stems/full.ogg` → `stems/audio.mp3` → any stem; `null` if the pack has no audio). Fetch it as `/api/sloppak//file/` (both path-encoded per segment). Resolving it server-side means the frontend previews with **one** request instead of probing (and 404ing) a hardcoded path. Cached with the rest of the meta. +- Hover-preview audio is **not** resolved here — it delegates to the `song_preview` plugin (see Preview on Hover), so the tree carries no audio member. ### extract_meta returns arrangements/stems as objects, not strings @@ -335,7 +334,7 @@ Drag-and-drop uses **pointer events** (mousedown/mousemove/mouseup), not the HTM Hovering a song for `_HOVER_PREVIEW_DELAY_MS` (800 ms) plays a short audio preview in place — no navigation to the player. Toggled by a play-icon toolbar button (`_injectToolbar`); **on by default** (`_previewHover`, persisted per surface under `previewHover` — only an explicit stored `'false'` disables it). -- **Audio** — a dedicated `_previewAudio` `