Ask the provider again for a favorite yt-dlp can't resolve

Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01MPZFnNdHbPGDTqQUNiE4ZN
This commit is contained in:
Simon
2026-11-02 22:29:00 +00:00
parent 2fcc17877d
commit 93463bce3a
2 changed files with 107 additions and 4 deletions

View File

@@ -0,0 +1,69 @@
#!/usr/bin/env python3
"""A favorite whose site yt-dlp can't extract still gets its formats.
Providers like rule34video hand the listing their formats; a favorite keeps
none, and /api/resolve comes back empty for them. ensureFormats must then ask
the providers again and take the item that is this video.
backend/main.py &
.venv/bin/python tests/smoke_favorite_formats.py
"""
import json
import sys
from playwright.sync_api import sync_playwright
BASE = "http://127.0.0.1:5000/"
SERVER = "https://a.fixture.test"
FAV = {"key": "rule34video:4511669", "id": "rule34video:4511669",
"url": "https://rule34video.com/video/4511669/sindel-cassie-sonya/",
"title": "Sindel, Cassie, Sonya", "thumb": "", "channel": "Rule34video",
"uploader": "Nyl", "duration": 510, "isLive": False,
"favoriteDate": "2026-11-02T22:00:05.356Z"}
STATUS = {"id": "a", "name": "a", "online": True, "channels": [
{"id": "rule34video", "name": "Rule34video", "description": "x", "options": []}]}
FMT = [{"url": "https://rule34video.com/get_file/1/x/4511669_720p.mp4/", "height": 720, "ext": "mp4"}]
asked = []
def videos(route):
body = json.loads(route.request.post_data or "{}")
asked.append(body)
items = [{"id": "rule34video:1", "url": "https://rule34video.com/video/1/other/", "formats": []},
{"id": FAV["id"], "url": FAV["url"], "formats": FMT}]
route.fulfill(status=200, content_type="application/json", body=json.dumps({"items": items}))
def main():
failed = 0
with sync_playwright() as p:
b = p.chromium.launch(args=["--no-sandbox", "--disable-gpu"])
page = b.new_page()
page.route(f"{SERVER}/api/status", lambda r: r.fulfill(
status=200, content_type="application/json", body=json.dumps(STATUS)))
page.route("**/api/resolve", lambda r: r.fulfill(
status=200, content_type="application/json",
body='{"formats":[],"http_headers":{},"isLive":false,"url":null}'))
page.route("**/api/videos", videos)
page.goto(BASE, wait_until="domcontentloaded")
page.evaluate("""([s, f]) => {
localStorage.setItem('config', JSON.stringify({servers: [{[s]: {}}]}));
localStorage.setItem('favorites', JSON.stringify([f]));
}""", [SERVER, FAV])
page.goto(BASE, wait_until="load")
meta = page.evaluate("""async (f) => {
const v = Object.assign({}, f);
const m = await App.videos.ensureFormats(v);
return { m, attached: !!v.meta };
}""", FAV)
ok = bool(meta["m"]) and meta["m"]["formats"] == FMT and meta["attached"]
print(f" [{'PASS' if ok else 'FAIL'}] favorite gets the provider's formats {meta}")
failed += 0 if ok else 1
ok = bool(asked) and asked[0]["channel"] == "rule34video" and asked[0]["server"] == SERVER
print(f" [{'PASS' if ok else 'FAIL'}] asked the right channel and server {asked[:1]}")
failed += 0 if ok else 1
b.close()
return 1 if failed else 0
if __name__ == "__main__":
sys.exit(main())