`resolveVideoSource` chose between a local file and a remote URL for video playback. Backend-owned stream selection took that decision into Rust — `media_local_selection` for a downloaded file, `get_stream_selection` for a streamed one — and its last caller went with it. What remained was the function plus sixty lines of tests exercising nothing that ships. `fittedVideoSize` computed the rendered size of a video letterboxed into its container. Nothing has ever called it: it arrived with the fix that made the video fill its viewport and was superseded by `object-fit: contain` in the same change. There is some irony in a helper that models letterboxing sitting unused beside a container that was not letterboxing at all — the bug fixed in the previous commit was CSS, and this function would not have helped. A survey for exported symbols referenced only by their own tests finds 22 more. Most are legitimate — test mocks, deliberate reset hooks, public utility APIs — and the rest are unrelated to this work, so they are left for a cleanup that can be reviewed on its own terms rather than smuggled into a playback branch. Also records in the spec why DR-231's design changed. Reparenting Tauri's webview into a GtkOverlay aborts the process on the first click: Linux calls `attach_resize_handler` unconditionally (the Windows path guards it with `is_decorated()`), and its handler walks webview -> GtkBox -> GtkWindow with an unwrap that an overlay breaks. So the webview is not moved at all — mpv draws into the default vbox's own `draw` handler via `gdk_cairo_draw_from_gl()`, and GTK's container-before-children order puts the webview on top for free. No reparent, one less widget, and nothing a Tauri upgrade can invalidate by assuming its own layout.
Specs index
Feature specs for JellyTau. Start a new one from SPEC-TEMPLATE.md and run it past SPEC-REVIEW-CHECKLIST.md before accepting it.
What lives here
Only work that has not shipped. Once a spec is fully implemented its design is folded into the architecture docs — which are the maintained description of the build — and the spec file is deleted. Git history keeps the original, including its rejected alternatives and acceptance criteria; the architecture docs keep the reasoning that a future change still needs.
So: a file in this directory is a promise, not a description. If you want to know how something works, read docs/architecture/. If you want to know what is planned, read here.
Status vocabulary
| Status | Meaning |
|---|---|
| Proposed | Written, not accepted. Nothing built. |
| Accepted | Agreed as the design; implementation not started or not finished. |
| Partially implemented | Some parts shipped; the spec names what is left. |
| Design authority | No code of its own — it records a decision later specs act on. |
Next free requirement ids (always re-check requirements.md before allocating): UR-079, IR-033, DR-232. Three specs below suggested ids that have since been taken by other work; each carries a ⚠️ note at the top.
Partially implemented
| Spec | What landed | What is left |
|---|---|---|
| frontend-domain-model.md | Catalog surface: MediaKind, from_jellyfin isolated, ticks → ms |
primaryImageTag → imageId (~30 sites); player/session/reporting tick math; stream.type |
| libmpv2-migration.md | LICENSE |
The libmpv → libmpv2 crate swap |
| read-through-media-cache.md | DR-126…128, DR-133…138 — cache entries are download rows; local playback of downloads | DR-122/124/125 — the read-through capture. DR-121 shipped as backend-owned stream selection and left this spec |
| scoped-search-boundary-implementation.md | Stage 1: SearchScope owned by Rust (DR-063…067) |
Stage 2: result-side grouping (GROUP_ITEM_TYPES still in searchScope.ts) |
Not started
| Spec | Blocked on / note |
|---|---|
| desktop-native-video.md | mpv draws video on every desktop platform, then the webview <video> path and hls.js are deleted. Converts a measured 7% direct-play rate toward Android's 85%. Stacked on backend-owned stream selection. |
| build-provenance.md | build.rs is still bare. ⚠️ suggested id DR-093 is taken. |
| player-facade-enforcement.md | ~60 commands.player* sites still outside the facade; no lint rule. ⚠️ suggested id DR-095 is taken. |
| windows-native-audio-backend.md | Blocked on the libmpv2 swap. ⚠️ suggested id IR-030 is taken. |
| linux-native-video-spike.md | Spike run 2026-08-21: compositing works on Linux, X11 and Wayland. G1-G6 green bar the Tauri default_vbox() half of G1. The adaptive-bitrate question it was waiting on is answered: the server publishes one EXT-X-STREAM-INF, so there is no ladder for mpv to lose (DR-229). StreamSelection (DR-225) is the contract to consume. |
Design authority
| Spec | Role |
|---|---|
| playback-backend-unification.md | Why video cannot unify onto one native engine and audio can. The audio half has since shipped on Android; Windows has not. |
| scoped-search-boundary.md | The boundary design the check:boundary rule came from. Stage 1 built. |
| scoped-search.md | Superseded in part — its "frontend only, no Rust changes" decision is the leak the boundary spec reversed. UX still current. |
Where the shipped specs went
Sixteen specs were folded into the architecture docs and deleted (2026-08-21). Where to look for each:
| Shipped work | Now documented in |
|---|---|
| Account menu & global chrome | 02-svelte-frontend.md — App Shell and Chrome |
| Library mosaic | 02-svelte-frontend.md — Library Mosaic |
| Series current-episode navigation | 02-svelte-frontend.md — Series and Episode Navigation |
| Downloads as an offline library | 02-svelte-frontend.md — Downloaded Browse |
| Favourites browsing | 01-rust-backend.md — Favorites System |
| Streaming bitrate cap | 01-rust-backend.md — Streaming quality ladder |
| Locally-indexed search | 03-data-flow.md — Search Flow; 01-rust-backend.md — Background workers |
| Offline downloaded-only filter | 06-downloads-and-offline.md — Offline Catalog Visibility |
| Audio equalizer · Android audio settings parity | 05-platform-backends.md — Audio settings on ExoPlayer |
| Android native video spike | 05-platform-backends.md — Native Video Compositing |
| Video background audio | 05-platform-backends.md — Background Audio Handoff |
| Traceability gate repair | traceability-ci.md |
| Boundary tripwire hardening | scripts/check-frontend-boundary.sh (its header is the spec) |
| Playback docs corrections · req-coverage script removal | Nothing to document — both were corrections that have been applied |