diff options
author | TIN TUN AUNG <62133983+rayguo17@users.noreply.github.com> | 2025-01-14 08:21:29 +0800 |
---|---|---|
committer | GitHub <noreply@github.com> | 2025-01-14 00:21:29 +0000 |
commit | 55ac1887dc57f5b7924059ed57612338a2c7bf51 (patch) | |
tree | f4c9a466340a7aa37ea63db4db17d0d43665daeb /components/net/filemanager_thread.rs | |
parent | faf30176f18e276125cbdac4a5750834258460c5 (diff) | |
download | servo-55ac1887dc57f5b7924059ed57612338a2c7bf51.tar.gz servo-55ac1887dc57f5b7924059ed57612338a2c7bf51.zip |
Add Content Range Header and add one for blob end range (#34797)
Signed-off-by: rayguo17 <rayguo17@gmail.com>
Diffstat (limited to 'components/net/filemanager_thread.rs')
-rw-r--r-- | components/net/filemanager_thread.rs | 49 |
1 files changed, 43 insertions, 6 deletions
diff --git a/components/net/filemanager_thread.rs b/components/net/filemanager_thread.rs index b501d845c9b..e72290b2694 100644 --- a/components/net/filemanager_thread.rs +++ b/components/net/filemanager_thread.rs @@ -11,7 +11,7 @@ use std::sync::atomic::{self, AtomicBool, AtomicUsize, Ordering}; use std::sync::{Arc, Mutex, RwLock, Weak}; use embedder_traits::{EmbedderMsg, EmbedderProxy, FilterPattern}; -use headers::{ContentLength, ContentType, HeaderMap, HeaderMapExt, Range}; +use headers::{ContentLength, ContentRange, ContentType, HeaderMap, HeaderMapExt, Range}; use http::header::{self, HeaderValue}; use ipc_channel::ipc::{self, IpcSender}; use log::warn; @@ -290,24 +290,39 @@ impl FileManager { response: &mut Response, ) -> Result<(), BlobURLStoreError> { let file_impl = self.store.get_impl(id, file_token, origin_in)?; + /* + Only Fetch Blob Range Request would have unresolved range, and only in that case we care about range header. + */ + let mut is_range_requested = false; match file_impl { FileImpl::Memory(buf) => { let bounds = match bounds { - BlobBounds::Unresolved(range) => get_range_request_bounds(range, buf.size), + BlobBounds::Unresolved(range) => { + if range.is_some() { + is_range_requested = true; + } + get_range_request_bounds(range, buf.size) + }, BlobBounds::Resolved(bounds) => bounds, }; let range = bounds .get_final(Some(buf.size)) .map_err(|_| BlobURLStoreError::InvalidRange)?; - let range = range.to_abs_range(buf.size as usize); + let range = range.to_abs_blob_range(buf.size as usize); let len = range.len() as u64; + let content_range = if is_range_requested { + ContentRange::bytes(range.start as u64..range.end as u64, buf.size).ok() + } else { + None + }; set_headers( &mut response.headers, len, buf.type_string.parse().unwrap_or(mime::TEXT_PLAIN), /* filename */ None, + content_range, ); let mut bytes = vec![]; @@ -327,9 +342,14 @@ impl FileManager { let file = File::open(&metadata.path) .map_err(|e| BlobURLStoreError::External(e.to_string()))?; - + let mut is_range_requested = false; let bounds = match bounds { - BlobBounds::Unresolved(range) => get_range_request_bounds(range, metadata.size), + BlobBounds::Unresolved(range) => { + if range.is_some() { + is_range_requested = true; + } + get_range_request_bounds(range, metadata.size) + }, BlobBounds::Resolved(bounds) => bounds, }; let range = bounds @@ -349,6 +369,13 @@ impl FileManager { .and_then(|osstr| osstr.to_str()) .map(|s| s.to_string()); + let content_range = if is_range_requested { + let abs_range = range.to_abs_blob_range(metadata.size as usize); + ContentRange::bytes(abs_range.start as u64..abs_range.end as u64, metadata.size) + .ok() + } else { + None + }; set_headers( &mut response.headers, metadata.size, @@ -356,6 +383,7 @@ impl FileManager { .first() .unwrap_or(mime::TEXT_PLAIN), filename, + content_range, ); self.fetch_file_in_chunks( @@ -939,8 +967,17 @@ fn read_file_in_chunks( } } -fn set_headers(headers: &mut HeaderMap, content_length: u64, mime: Mime, filename: Option<String>) { +fn set_headers( + headers: &mut HeaderMap, + content_length: u64, + mime: Mime, + filename: Option<String>, + content_range: Option<ContentRange>, +) { headers.typed_insert(ContentLength(content_length)); + if let Some(content_range) = content_range { + headers.typed_insert(content_range); + } headers.typed_insert(ContentType::from(mime.clone())); let name = match filename { Some(name) => name, |