Fix orphan "-(p)" suffix in filenames for media without resolution metadata - #812
Fix orphan "-(p)" suffix in filenames for media without resolution metadata#812independent-arg wants to merge 11 commits into
Conversation
Added regex-based formatting for template values with support for float precision.
…prefixes for existing users.
Updated default filename templates to use yt-dlp conditional operators and auto-reference syntax to prevent orphan characters.
|
With this proposed solution, we can definitively solve these orphan character issues once and for all, at least covering all possible use cases. We'll also need to update the following all locale files to keep them in sync with these changes: Back then, {} self-references for its OWN fields (playlist_title, playlist_index, etc.) weren't supported, even though yt-dlp does support them for its own. If someone built a custom template mixing a playlist field with that syntax, it would just break silently. So, the addition of BRACE_RE is important. Please let me know if there are any other files related to the templates that need to be changed to this new syntax. |
|
@jely2002 when you have time, it would be interesting to know your thoughts on this, thanks :) |
#797
This PR fixes the long-standing bug where filenames for audio‑only content (e.g., SoundCloud) would incorrectly end with
-(p)or-(k).Example:
Música sin Copyright de Fondo-(p).mp4→ nowMúsica sin Copyright de Fondo.mp4The root cause was the default video template:
%(title).200s-(%(height)sp%(fps).0d).%(ext)sWhen
heightandfpsare absent, they become empty strings, leaving a straypliteral.My first instinct was to nest %(fps) inside the conditional replacement for %(height&...)s. Before suggesting it to you, I tested it against actual yt-dlp, and it breaks the parser:
Solution
Replace the templates with conditional blocks using
yt-dlp's&operator and auto‑reference{}:Video:
%(title).200s%(height&-{:.0f}p|)s%(fps&-{:.0f}fps|)s.%(ext)sAudio:
%(title).200s%(abr&-{:.0f}k|)s.%(ext)sThis only renders the resolution/bitrate part when the field exists, removing orphan characters.
Note: Check out the visual change: it goes from -(1080p30) to -1080p-30fps. There’s honestly no way to keep the exact style with parentheses and combine two fields into a single conditional block, it’s a hard limitation of yt-dlp’s template engine, not something we can bypass in Rust. If you really want about keeping the brackets instead of dashes, I also tried
-[{:.0f}p][{:.0f}fps]and it works just as fine, it’s purely aesthetic, so your call.Changes
config_models.rs- updated default templates.config.rs- added auto‑migration for users with old default templates (custom templates are not overwritten).template_context.rs- extended the preview engine to handle{}and format specifiers like{:.0f}.PreferencesFilename.vue- updated built‑in presets to use the new syntax.src/tauri/types/config.ts- updated templates.Testing
...-(p).mp4❌....mp4✅...-(1080p24).mp4...-1080p-24fps.mp4✅I also found the same latent bug pattern in the audio template (
%(abr)dk→-(k)whenabris absent), even though it doesn't currently trigger in practice,abris virtually always present for real audio streams, which matches what I reported ("audio mode works flawlessly"). Fixed proactively with the same approach for consistency.height/fpsas literal0instead of omitting the field, yt-dlp's
&operator treats0as present,producing
-0p-0fps. Still strictly better than the original bug, but notperfect, there's no
>0comparison available inside-otemplates.yt-dlpbinary (not just reasoning about thesyntax) with edge cases: very long titles, missing title, special
characters, and
--restrict-filenames, all resolve cleanly.