pimpbunny fix

This commit is contained in:
Simon
2026-05-18 17:27:34 +00:00
committed by ForgeCode
parent ee47bbe74d
commit aea2cda627

View File

@@ -147,28 +147,33 @@ impl PimpbunnyProxy {
.collect() .collect()
} }
/// Returns true if the URL appears to serve video content (not an "access denied" response). /// GET the decoded URL without following redirects and return the Location header
async fn url_is_accessible(url: &str, requester: &mut Requester) -> bool { /// if the server responds with a 302, or None if it responds with anything else
// Range: bytes=0-1 keeps the response body tiny while still probing auth. /// (including 403 "access denied").
match requester ///
.get_raw_with_headers( /// The PHPSESSID cookie — acquired when we fetched the detail page — must be
url, /// forwarded; the server won't issue the 302 without it.
vec![("Range".to_string(), "bytes=0-1".to_string())], async fn follow_302(url: &str, requester: &Requester) -> Option<String> {
) let client = wreq::Client::builder()
.await .redirect(wreq::redirect::Policy::none())
{ .build()
Ok(resp) => { .ok()?;
let s = resp.status().as_u16(); let mut req = client.get(url);
// 200 / 206 = success; 301/302/307 = redirect (follows, so we see final status) if let Some(cookie) = requester.cookie_header_for_url(url) {
// Treat anything that isn't a client-error 4xx as accessible. req = req.header("Cookie", cookie);
s < 400 || s == 416 // 416 = Range Not Satisfiable means the server accepted auth
} }
Err(_) => false, let resp = req.send().await.ok()?;
if resp.status().as_u16() != 302 {
return None;
} }
resp.headers()
.get("location")
.and_then(|v| v.to_str().ok())
.map(|s| s.to_string())
} }
/// Try to decode the video URL using the KVS algorithm extracted from kt_player.js. /// Try to decode the video URL using the KVS algorithm extracted from kt_player.js.
/// Returns the decoded URL if the server accepts it, None otherwise. /// Returns the CDN redirect target (Location from the 302) on success, None otherwise.
async fn try_decode(detail_url: &str, requester: &mut Requester) -> Option<String> { async fn try_decode(detail_url: &str, requester: &mut Requester) -> Option<String> {
let html = requester.get(detail_url, None).await.ok()?; let html = requester.get(detail_url, None).await.ok()?;
@@ -183,8 +188,8 @@ impl PimpbunnyProxy {
let Some(decoded) = Self::decode_encoded_url(encoded_url, &license_code) else { let Some(decoded) = Self::decode_encoded_url(encoded_url, &license_code) else {
continue; continue;
}; };
if Self::url_is_accessible(&decoded, requester).await { if let Some(location) = Self::follow_302(&decoded, requester).await {
return Some(decoded); return Some(location);
} }
} }