From 8d36c9c00e8dad6a1bf83eac54079e1e787550f1 Mon Sep 17 00:00:00 2001 From: euzu Date: Fri, 9 May 2025 18:18:59 +0200 Subject: [PATCH] Refactored stream handling --- src/api/api_utils.rs | 2 +- .../model/streams/provider_stream_factory.rs | 33 ++++++++++++------- src/model/config_download.rs | 2 +- src/utils/constants.rs | 3 +- 4 files changed, 25 insertions(+), 15 deletions(-) diff --git a/src/api/api_utils.rs b/src/api/api_utils.rs index 136059485..41b69518f 100644 --- a/src/api/api_utils.rs +++ b/src/api/api_utils.rs @@ -585,7 +585,7 @@ pub async fn force_provider_stream_response(app_state: &AppState, } drop(stream_details.provider_connection_guard.take()); if let (Some(stream), _stream_info) = - create_channel_unavailable_stream(&app_state.config, &vec![], StatusCode::BAD_GATEWAY) + create_channel_unavailable_stream(&app_state.config, &[], StatusCode::BAD_GATEWAY) { debug!("Streaming custom stream"); axum::response::Response::builder().status(StatusCode::OK).body(Body::from_stream(stream)).unwrap().into_response() diff --git a/src/api/model/streams/provider_stream_factory.rs b/src/api/model/streams/provider_stream_factory.rs index e154c56b3..d4170e8c1 100644 --- a/src/api/model/streams/provider_stream_factory.rs +++ b/src/api/model/streams/provider_stream_factory.rs @@ -6,11 +6,11 @@ use crate::api::model::streams::buffered_stream::BufferedStream; use crate::api::model::streams::client_stream::ClientStream; use crate::api::model::streams::provider_stream::{create_channel_unavailable_stream, get_header_filter_for_item_type}; use crate::api::model::streams::timed_client_stream::TimeoutClientStream; -use crate::model::Config; use crate::model::PlaylistItemType; +use crate::model::{Config, DEFAULT_USER_AGENT}; use crate::tools::atomic_once_flag::AtomicOnceFlag; -use crate::utils::debug_if_enabled; use crate::utils::request::{classify_content_type, get_request_headers, sanitize_sensitive_info, MimeCategory}; +use crate::utils::{debug_if_enabled, filter_request_header}; use futures::stream::{self}; use futures::{StreamExt, TryStreamExt}; use log::{debug, warn}; @@ -251,7 +251,7 @@ fn get_request_range_start_bytes(req_headers: &HashMap>) -> Opti fn get_host_and_optional_port(url: &Url) -> Option { let host = url.host_str()?; match url.port() { - Some(port) => Some(format!("{}:{}", host, port)), + Some(port) => Some(format!("{host}:{port}")), None => Some(host.to_string()), } } @@ -259,24 +259,33 @@ fn get_host_and_optional_port(url: &Url) -> Option { fn prepare_client(request_client: &Arc, stream_options: &ProviderStreamFactoryOptions) -> (reqwest::RequestBuilder, bool) { let url = stream_options.get_url(); - let host = get_host_and_optional_port(url); let range_start = stream_options.get_total_bytes_send(); let original_headers = stream_options.get_headers(); - let mut headers = original_headers.clone(); + debug!("original_headers {original_headers:?}"); - if let Some(host_header) = host { - if let Ok(header_value) = axum::http::header::HeaderValue::from_str(&host_header) { - headers.insert(axum::http::header::HOST, header_value); + + let mut headers = HeaderMap::default(); + for (key, value) in original_headers { + if filter_request_header(key.as_str()) { + headers.insert(key.clone(), value.clone()); } } - if !headers.contains_key(axum::http::header::TRANSFER_ENCODING) { - headers.insert(axum::http::header::TRANSFER_ENCODING, axum::http::header::HeaderValue::from_static("chunked")); - } + // if !headers.contains_key(axum::http::header::HOST) { + // if let Some(host_header) = get_host_and_optional_port(url) { + // if let Ok(header_value) = axum::http::header::HeaderValue::from_str(&host_header) { + // headers.insert(axum::http::header::HOST, header_value); + // } + // } + // } if !headers.contains_key(axum::http::header::USER_AGENT) { - headers.insert(axum::http::header::USER_AGENT, axum::http::header::HeaderValue::from_static("Mozilla/5.0 (Linux; Android 10)")); + headers.insert(axum::http::header::USER_AGENT, axum::http::header::HeaderValue::from_static(DEFAULT_USER_AGENT)); + } + + if !headers.contains_key(axum::http::header::CONNECTION) { + headers.insert(axum::http::header::CONNECTION, axum::http::header::HeaderValue::from_static("keep-alive")); } let partial = if let Some(range) = range_start { diff --git a/src/model/config_download.rs b/src/model/config_download.rs index ea450f130..486f22498 100644 --- a/src/model/config_download.rs +++ b/src/model/config_download.rs @@ -3,7 +3,7 @@ use regex::Regex; use std::borrow::BorrowMut; use std::collections::HashMap; -const DEFAULT_USER_AGENT: &str = "Mozilla/5.0 (AppleTV; U; CPU OS 14_2 like Mac OS X; en-us) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/14.0.1 Safari/605.1.15"; +pub const DEFAULT_USER_AGENT: &str = "VLC/3.0.16 LibVLC/3.0.16"; #[derive(Debug, Clone, serde::Serialize, serde::Deserialize, Default)] #[serde(deny_unknown_fields)] diff --git a/src/utils/constants.rs b/src/utils/constants.rs index fdcdb6a62..7f795f14f 100644 --- a/src/utils/constants.rs +++ b/src/utils/constants.rs @@ -30,7 +30,7 @@ pub const DASH_EXT_FRAGMENT: &str = ".mpd#"; pub const FILENAME_TRIM_PATTERNS: &[char] = &['.', '-', '_']; const SUPPORTED_RESPONSE_HEADERS: &[&str] = &[ - "accept", + //"accept", "accept-ranges", "content-type", "content-length", @@ -48,6 +48,7 @@ const SUPPORTED_RESPONSE_HEADERS: &[&str] = &[ "expires" ]; + pub fn filter_response_header(key: &str) -> bool { SUPPORTED_RESPONSE_HEADERS.contains(&key) }