A timed-out install() call left the original thread running and let a
later call spawn a second one, racing both over the same mpv render
context and segfaulting. install() is now single-flight per process.
Also gate release publishing on all three platform builds succeeding,
not just the first one to finish.
libloading's Display for this error is hardcoded to "LoadLibraryExW
failed" and never includes the actual OS error, even though it's
captured internally via source(). Walks the error chain so a future
failure (if any) gives an actual diagnosable reason instead of a dead end.
Was 0x200 (actually LOAD_LIBRARY_SEARCH_APPLICATION_DIR's value, already
implied by DEFAULT_DIRS), not 0x100. The previous fix never actually told
Windows to search lib/ for mpv-2.dll's dependencies -- it was a no-op.
LoadLibraryW on Windows doesn't search a DLL's own directory for its
dependencies unless told to -- only the exe dir, System32, and PATH.
mpv-2.dll's ~110 dependency DLLs (ffmpeg, libplacebo, etc.) live next to
it in lib/, so every load failed despite all the files being present.
Confirmed via the new logging: "LoadLibraryExW failed" right before the
player surface install times out, which is what silently kicked users
back to the previous screen on every playback attempt.
Release builds use windows_subsystem="windows" (no console) and there
was no logger backend registered at all -- every log::warn!/error! call
in the player code was silently dropped. Adds tauri-plugin-log writing
to the app's log dir, and logs every step of native player surface
setup, load attempts, and mpv end-file events so a real failure reason
is visible instead of just "it went back to the previous screen".
Polling eof-reached right after loadfile can read stale, and never
distinguished a real end-of-file from the stream simply failing to
open -- both looked like "silently kick back to the previous screen".
Drains mpv's actual event queue (MPV_EVENT_END_FILE) instead, and
surfaces the real error plus recent warn-level log lines when the
stream genuinely fails to open.
apt has no cache between runs; on a slow mirror day this turned into a
20+ minute step. Point apt's archive cache at $HOME (avoids permission
issues with the root-owned default path) and persist it via
actions/cache so a slow mirror only costs once.
if-let on a temporary lock guard without a trailing semicolon extends
the guard's drop scope past the enclosing block, so the State it
borrowed from gets dropped first -- E0597 on macOS/Windows.
The KhooLy/mpv fork's libmpv.so.2 links libass, libavfilter, and
libplacebo (needed for the gpu-next render path) -- none of which were
in the apt install list, so the post-fetch ldd check failed.
fluxa-core is public now -- the workflow was pointing at a repo name
(KhooLy/FluxaCore) that never existed, gated behind a PAT secret that
was never set, which is why every release build job failed at checkout.
- OAuth: generate and validate a state param across the Trakt/MAL/Simkl
deep-link flow to close a login-CSRF gap (code was exchanged with no
check that it came from a flow this app actually started).
- Add net_guard: resolves the host of any addon-supplied URL and refuses
to fetch loopback/private/link-local/CGNAT addresses, applied to
http_fetch_text, artwork prefetch, and offline downloads. Drop the
now-unused localhost/ws CSP allowances.
- Encrypt storage_read/storage_write at rest (AES-256-GCM, key in a
0600-permissioned file) instead of plaintext JSON, with transparent
fallback for existing unencrypted files so upgrading doesn't lose data.
- Replace get_nuvio_config (handed the Supabase anon key straight to JS)
with a nuvio_request proxy command -- Rust attaches the key and makes
the call itself, so it never exists in webview-reachable memory.
- Render backend now sources prebuilt libmpv from KhooLy/mpv (gpu-next),
fetched via src-tauri/fetch-libmpv.sh; video-sync switched to
display-resample with vsync-paced render loops on all platforms.
- CI (build.yml) updated to fetch the fork instead of building/bundling
mpv per-platform.
- Fix: next-episode auto-skip countdown kept ticking while paused.
- Fix: addon HTTP fetches had no timeout, so a hung (not just refused)
connection could block the home feed load forever, leaving a blank
screen with no error.
- Fix: Nuvio offline banner overlapped the player's top bar instead of
pushing it down.
- Add F11 as a fullscreen toggle in the player, alongside F.
- Restyle Skip Intro/Outro button: flat surface instead of native
button chrome bleeding through, icon, hover/focus state, progress bar.