mirror of
https://github.com/alexta69/metube.git
synced 2026-07-23 13:22:48 +00:00
feat: ALLOW_PRIVATE_ADDRESSES to opt out of the SSRF checks (closes #1036)
The SSRF guard rejects any address that isn't globally routable, which breaks proxy/VPN setups that resolve hosts into private or special-use ranges. The reported case is Fake-IP clients (sing-box, Clash, Mihomo) that map YouTube to the RFC 2544 benchmarking range 198.18.0.0/15 to tunnel the traffic; MeTube rejected it with "Refusing to fetch internal address" even though yt-dlp itself handles it fine. Add a boolean ALLOW_PRIVATE_ADDRESSES (default false) that, when set, skips both layers: validate_url returns after scheme validation without the internal-host checks, and the connect-time socket guard is not installed. Threaded to the download subprocess via Download so the guard sees it too. Scheme validation (http/https only) still applies. Documented in the README as a trust-your-network opt-out that disables SSRF protection. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
@@ -115,7 +115,7 @@ def extract_flat_playlist(
|
||||
if not nested_url:
|
||||
continue
|
||||
# nested_url comes from remote playlist content; guard it too.
|
||||
if validate_url(nested_url) is not None:
|
||||
if validate_url(nested_url, allow_private=getattr(config, "ALLOW_PRIVATE_ADDRESSES", False)) is not None:
|
||||
continue
|
||||
nested_info, nested_entries = extract_flat_playlist(
|
||||
config,
|
||||
@@ -548,7 +548,8 @@ class SubscriptionManager:
|
||||
return {"status": "error", "msg": "Missing URL"}
|
||||
# SSRF guard: block non-http(s) schemes and internal/metadata hosts
|
||||
# before yt-dlp fetches the feed. May do a DNS lookup, so run off-loop.
|
||||
url_error = await asyncio.get_running_loop().run_in_executor(None, validate_url, url)
|
||||
url_error = await asyncio.get_running_loop().run_in_executor(
|
||||
None, partial(validate_url, url, allow_private=getattr(self.config, "ALLOW_PRIVATE_ADDRESSES", False)))
|
||||
if url_error is not None:
|
||||
log.warning('Rejected subscription URL "%s": %s', url, url_error)
|
||||
return {"status": "error", "msg": url_error}
|
||||
|
||||
Reference in New Issue
Block a user