mirror of
https://github.com/servo/servo.git
synced 2025-08-03 12:40:06 +01:00
Create resource timing entry for sync network fetch
This commit is contained in:
parent
ea71b35220
commit
e5217eed0e
7 changed files with 131 additions and 90 deletions
|
@ -597,38 +597,6 @@ pub enum CookieSource {
|
||||||
NonHTTP,
|
NonHTTP,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Convenience function for synchronously loading a whole resource.
|
|
||||||
pub fn load_whole_resource(
|
|
||||||
request: RequestBuilder,
|
|
||||||
core_resource_thread: &CoreResourceThread,
|
|
||||||
) -> Result<(Metadata, Vec<u8>), NetworkError> {
|
|
||||||
let (action_sender, action_receiver) = ipc::channel().unwrap();
|
|
||||||
core_resource_thread
|
|
||||||
.send(CoreResourceMsg::Fetch(
|
|
||||||
request,
|
|
||||||
FetchChannels::ResponseMsg(action_sender, None),
|
|
||||||
))
|
|
||||||
.unwrap();
|
|
||||||
|
|
||||||
let mut buf = vec![];
|
|
||||||
let mut metadata = None;
|
|
||||||
loop {
|
|
||||||
match action_receiver.recv().unwrap() {
|
|
||||||
FetchResponseMsg::ProcessRequestBody | FetchResponseMsg::ProcessRequestEOF => (),
|
|
||||||
FetchResponseMsg::ProcessResponse(Ok(m)) => {
|
|
||||||
metadata = Some(match m {
|
|
||||||
FetchMetadata::Unfiltered(m) => m,
|
|
||||||
FetchMetadata::Filtered { unsafe_, .. } => unsafe_,
|
|
||||||
})
|
|
||||||
},
|
|
||||||
FetchResponseMsg::ProcessResponseChunk(data) => buf.extend_from_slice(&data),
|
|
||||||
FetchResponseMsg::ProcessResponseEOF(Ok(_)) => return Ok((metadata.unwrap(), buf)),
|
|
||||||
FetchResponseMsg::ProcessResponse(Err(e)) |
|
|
||||||
FetchResponseMsg::ProcessResponseEOF(Err(e)) => return Err(e),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Network errors that have to be exported out of the loaders
|
/// Network errors that have to be exported out of the loaders
|
||||||
#[derive(Clone, Debug, Deserialize, Eq, MallocSizeOf, PartialEq, Serialize)]
|
#[derive(Clone, Debug, Deserialize, Eq, MallocSizeOf, PartialEq, Serialize)]
|
||||||
pub enum NetworkError {
|
pub enum NetworkError {
|
||||||
|
|
|
@ -22,6 +22,7 @@ use crate::dom::globalscope::GlobalScope;
|
||||||
use crate::dom::messageevent::MessageEvent;
|
use crate::dom::messageevent::MessageEvent;
|
||||||
use crate::dom::worker::{TrustedWorkerAddress, Worker};
|
use crate::dom::worker::{TrustedWorkerAddress, Worker};
|
||||||
use crate::dom::workerglobalscope::WorkerGlobalScope;
|
use crate::dom::workerglobalscope::WorkerGlobalScope;
|
||||||
|
use crate::fetch::load_whole_resource;
|
||||||
use crate::script_runtime::ScriptThreadEventCategory::WorkerEvent;
|
use crate::script_runtime::ScriptThreadEventCategory::WorkerEvent;
|
||||||
use crate::script_runtime::{new_child_runtime, CommonScriptMsg, Runtime, ScriptChan, ScriptPort};
|
use crate::script_runtime::{new_child_runtime, CommonScriptMsg, Runtime, ScriptChan, ScriptPort};
|
||||||
use crate::task_queue::{QueuedTask, QueuedTaskConversion, TaskQueue};
|
use crate::task_queue::{QueuedTask, QueuedTaskConversion, TaskQueue};
|
||||||
|
@ -37,7 +38,7 @@ use js::jsval::UndefinedValue;
|
||||||
use js::rust::HandleValue;
|
use js::rust::HandleValue;
|
||||||
use msg::constellation_msg::{PipelineId, TopLevelBrowsingContextId};
|
use msg::constellation_msg::{PipelineId, TopLevelBrowsingContextId};
|
||||||
use net_traits::request::{CredentialsMode, Destination, Referrer, RequestBuilder};
|
use net_traits::request::{CredentialsMode, Destination, Referrer, RequestBuilder};
|
||||||
use net_traits::{load_whole_resource, IpcSend};
|
use net_traits::IpcSend;
|
||||||
use script_traits::{TimerEvent, TimerSource, WorkerGlobalScopeInit, WorkerScriptLoadOrigin};
|
use script_traits::{TimerEvent, TimerSource, WorkerGlobalScopeInit, WorkerScriptLoadOrigin};
|
||||||
use servo_rand::random;
|
use servo_rand::random;
|
||||||
use servo_url::ServoUrl;
|
use servo_url::ServoUrl;
|
||||||
|
@ -316,25 +317,6 @@ impl DedicatedWorkerGlobalScope {
|
||||||
.referrer_policy(referrer_policy)
|
.referrer_policy(referrer_policy)
|
||||||
.origin(origin);
|
.origin(origin);
|
||||||
|
|
||||||
let (metadata, bytes) =
|
|
||||||
match load_whole_resource(request, &init.resource_threads.sender()) {
|
|
||||||
Err(_) => {
|
|
||||||
println!("error loading script {}", serialized_worker_url);
|
|
||||||
parent_sender
|
|
||||||
.send(CommonScriptMsg::Task(
|
|
||||||
WorkerEvent,
|
|
||||||
Box::new(SimpleWorkerErrorHandler::new(worker)),
|
|
||||||
pipeline_id,
|
|
||||||
TaskSourceName::DOMManipulation,
|
|
||||||
))
|
|
||||||
.unwrap();
|
|
||||||
return;
|
|
||||||
},
|
|
||||||
Ok((metadata, bytes)) => (metadata, bytes),
|
|
||||||
};
|
|
||||||
let url = metadata.final_url;
|
|
||||||
let source = String::from_utf8_lossy(&bytes);
|
|
||||||
|
|
||||||
let runtime = unsafe { new_child_runtime(parent) };
|
let runtime = unsafe { new_child_runtime(parent) };
|
||||||
|
|
||||||
let (devtools_mpsc_chan, devtools_mpsc_port) = unbounded();
|
let (devtools_mpsc_chan, devtools_mpsc_port) = unbounded();
|
||||||
|
@ -356,7 +338,7 @@ impl DedicatedWorkerGlobalScope {
|
||||||
|
|
||||||
let global = DedicatedWorkerGlobalScope::new(
|
let global = DedicatedWorkerGlobalScope::new(
|
||||||
init,
|
init,
|
||||||
url,
|
worker_url,
|
||||||
devtools_mpsc_port,
|
devtools_mpsc_port,
|
||||||
runtime,
|
runtime,
|
||||||
parent_sender.clone(),
|
parent_sender.clone(),
|
||||||
|
@ -369,6 +351,29 @@ impl DedicatedWorkerGlobalScope {
|
||||||
// FIXME(njn): workers currently don't have a unique ID suitable for using in reporter
|
// FIXME(njn): workers currently don't have a unique ID suitable for using in reporter
|
||||||
// registration (#6631), so we instead use a random number and cross our fingers.
|
// registration (#6631), so we instead use a random number and cross our fingers.
|
||||||
let scope = global.upcast::<WorkerGlobalScope>();
|
let scope = global.upcast::<WorkerGlobalScope>();
|
||||||
|
let global_scope = global.upcast::<GlobalScope>();
|
||||||
|
|
||||||
|
let (metadata, bytes) = match load_whole_resource(
|
||||||
|
request,
|
||||||
|
&global_scope.resource_threads().sender(),
|
||||||
|
&global_scope,
|
||||||
|
) {
|
||||||
|
Err(_) => {
|
||||||
|
println!("error loading script {}", serialized_worker_url);
|
||||||
|
parent_sender
|
||||||
|
.send(CommonScriptMsg::Task(
|
||||||
|
WorkerEvent,
|
||||||
|
Box::new(SimpleWorkerErrorHandler::new(worker)),
|
||||||
|
pipeline_id,
|
||||||
|
TaskSourceName::DOMManipulation,
|
||||||
|
))
|
||||||
|
.unwrap();
|
||||||
|
return;
|
||||||
|
},
|
||||||
|
Ok((metadata, bytes)) => (metadata, bytes),
|
||||||
|
};
|
||||||
|
scope.set_url(metadata.final_url);
|
||||||
|
let source = String::from_utf8_lossy(&bytes);
|
||||||
|
|
||||||
unsafe {
|
unsafe {
|
||||||
// Handle interrupt requests
|
// Handle interrupt requests
|
||||||
|
|
|
@ -19,6 +19,7 @@ use crate::dom::extendablemessageevent::ExtendableMessageEvent;
|
||||||
use crate::dom::globalscope::GlobalScope;
|
use crate::dom::globalscope::GlobalScope;
|
||||||
use crate::dom::worker::TrustedWorkerAddress;
|
use crate::dom::worker::TrustedWorkerAddress;
|
||||||
use crate::dom::workerglobalscope::WorkerGlobalScope;
|
use crate::dom::workerglobalscope::WorkerGlobalScope;
|
||||||
|
use crate::fetch::load_whole_resource;
|
||||||
use crate::script_runtime::{new_rt_and_cx, CommonScriptMsg, Runtime, ScriptChan};
|
use crate::script_runtime::{new_rt_and_cx, CommonScriptMsg, Runtime, ScriptChan};
|
||||||
use crate::task_queue::{QueuedTask, QueuedTaskConversion, TaskQueue};
|
use crate::task_queue::{QueuedTask, QueuedTaskConversion, TaskQueue};
|
||||||
use crate::task_source::TaskSourceName;
|
use crate::task_source::TaskSourceName;
|
||||||
|
@ -31,7 +32,7 @@ use js::jsapi::{JSAutoCompartment, JSContext, JS_AddInterruptCallback};
|
||||||
use js::jsval::UndefinedValue;
|
use js::jsval::UndefinedValue;
|
||||||
use msg::constellation_msg::PipelineId;
|
use msg::constellation_msg::PipelineId;
|
||||||
use net_traits::request::{CredentialsMode, Destination, Referrer, RequestBuilder};
|
use net_traits::request::{CredentialsMode, Destination, Referrer, RequestBuilder};
|
||||||
use net_traits::{load_whole_resource, CustomResponseMediator, IpcSend};
|
use net_traits::{CustomResponseMediator, IpcSend};
|
||||||
use script_traits::{
|
use script_traits::{
|
||||||
ScopeThings, ServiceWorkerMsg, TimerEvent, WorkerGlobalScopeInit, WorkerScriptLoadOrigin,
|
ScopeThings, ServiceWorkerMsg, TimerEvent, WorkerGlobalScopeInit, WorkerScriptLoadOrigin,
|
||||||
};
|
};
|
||||||
|
@ -292,8 +293,11 @@ impl ServiceWorkerGlobalScope {
|
||||||
.referrer_policy(referrer_policy)
|
.referrer_policy(referrer_policy)
|
||||||
.origin(origin);
|
.origin(origin);
|
||||||
|
|
||||||
let (url, source) =
|
let (url, source) = match load_whole_resource(
|
||||||
match load_whole_resource(request, &init.resource_threads.sender()) {
|
request,
|
||||||
|
&init.resource_threads.sender(),
|
||||||
|
&GlobalScope::current().expect("No current global object"),
|
||||||
|
) {
|
||||||
Err(_) => {
|
Err(_) => {
|
||||||
println!("error loading script {}", serialized_worker_url);
|
println!("error loading script {}", serialized_worker_url);
|
||||||
return;
|
return;
|
||||||
|
|
|
@ -2,6 +2,7 @@
|
||||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||||
* file, You can obtain one at https://mozilla.org/MPL/2.0/. */
|
* file, You can obtain one at https://mozilla.org/MPL/2.0/. */
|
||||||
|
|
||||||
|
use crate::dom::bindings::cell::DomRefCell;
|
||||||
use crate::dom::bindings::codegen::Bindings::FunctionBinding::Function;
|
use crate::dom::bindings::codegen::Bindings::FunctionBinding::Function;
|
||||||
use crate::dom::bindings::codegen::Bindings::RequestBinding::RequestInit;
|
use crate::dom::bindings::codegen::Bindings::RequestBinding::RequestInit;
|
||||||
use crate::dom::bindings::codegen::Bindings::WorkerGlobalScopeBinding::WorkerGlobalScopeMethods;
|
use crate::dom::bindings::codegen::Bindings::WorkerGlobalScopeBinding::WorkerGlobalScopeMethods;
|
||||||
|
@ -42,10 +43,11 @@ use js::panic::maybe_resume_unwind;
|
||||||
use js::rust::{HandleValue, ParentRuntime};
|
use js::rust::{HandleValue, ParentRuntime};
|
||||||
use msg::constellation_msg::PipelineId;
|
use msg::constellation_msg::PipelineId;
|
||||||
use net_traits::request::{CredentialsMode, Destination, RequestBuilder as NetRequestInit};
|
use net_traits::request::{CredentialsMode, Destination, RequestBuilder as NetRequestInit};
|
||||||
use net_traits::{load_whole_resource, IpcSend};
|
use net_traits::IpcSend;
|
||||||
use script_traits::WorkerGlobalScopeInit;
|
use script_traits::WorkerGlobalScopeInit;
|
||||||
use script_traits::{TimerEvent, TimerEventId};
|
use script_traits::{TimerEvent, TimerEventId};
|
||||||
use servo_url::{MutableOrigin, ServoUrl};
|
use servo_url::{MutableOrigin, ServoUrl};
|
||||||
|
use std::cell::Ref;
|
||||||
use std::default::Default;
|
use std::default::Default;
|
||||||
use std::rc::Rc;
|
use std::rc::Rc;
|
||||||
use std::sync::atomic::{AtomicBool, Ordering};
|
use std::sync::atomic::{AtomicBool, Ordering};
|
||||||
|
@ -78,7 +80,7 @@ pub struct WorkerGlobalScope {
|
||||||
globalscope: GlobalScope,
|
globalscope: GlobalScope,
|
||||||
|
|
||||||
worker_id: WorkerId,
|
worker_id: WorkerId,
|
||||||
worker_url: ServoUrl,
|
worker_url: DomRefCell<ServoUrl>,
|
||||||
#[ignore_malloc_size_of = "Arc"]
|
#[ignore_malloc_size_of = "Arc"]
|
||||||
closing: Option<Arc<AtomicBool>>,
|
closing: Option<Arc<AtomicBool>>,
|
||||||
#[ignore_malloc_size_of = "Defined in js"]
|
#[ignore_malloc_size_of = "Defined in js"]
|
||||||
|
@ -123,7 +125,7 @@ impl WorkerGlobalScope {
|
||||||
Default::default(),
|
Default::default(),
|
||||||
),
|
),
|
||||||
worker_id: init.worker_id,
|
worker_id: init.worker_id,
|
||||||
worker_url,
|
worker_url: DomRefCell::new(worker_url),
|
||||||
closing,
|
closing,
|
||||||
runtime,
|
runtime,
|
||||||
location: Default::default(),
|
location: Default::default(),
|
||||||
|
@ -159,8 +161,12 @@ impl WorkerGlobalScope {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_url(&self) -> &ServoUrl {
|
pub fn get_url(&self) -> Ref<ServoUrl> {
|
||||||
&self.worker_url
|
self.worker_url.borrow()
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn set_url(&self, url: ServoUrl) {
|
||||||
|
*self.worker_url.borrow_mut() = url;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_worker_id(&self) -> WorkerId {
|
pub fn get_worker_id(&self) -> WorkerId {
|
||||||
|
@ -187,7 +193,7 @@ impl WorkerGlobalScopeMethods for WorkerGlobalScope {
|
||||||
// https://html.spec.whatwg.org/multipage/#dom-workerglobalscope-location
|
// https://html.spec.whatwg.org/multipage/#dom-workerglobalscope-location
|
||||||
fn Location(&self) -> DomRoot<WorkerLocation> {
|
fn Location(&self) -> DomRoot<WorkerLocation> {
|
||||||
self.location
|
self.location
|
||||||
.or_init(|| WorkerLocation::new(self, self.worker_url.clone()))
|
.or_init(|| WorkerLocation::new(self, self.worker_url.borrow().clone()))
|
||||||
}
|
}
|
||||||
|
|
||||||
// https://html.spec.whatwg.org/multipage/#handler-workerglobalscope-onerror
|
// https://html.spec.whatwg.org/multipage/#handler-workerglobalscope-onerror
|
||||||
|
@ -197,7 +203,7 @@ impl WorkerGlobalScopeMethods for WorkerGlobalScope {
|
||||||
fn ImportScripts(&self, url_strings: Vec<DOMString>) -> ErrorResult {
|
fn ImportScripts(&self, url_strings: Vec<DOMString>) -> ErrorResult {
|
||||||
let mut urls = Vec::with_capacity(url_strings.len());
|
let mut urls = Vec::with_capacity(url_strings.len());
|
||||||
for url in url_strings {
|
for url in url_strings {
|
||||||
let url = self.worker_url.join(&url);
|
let url = self.worker_url.borrow().join(&url);
|
||||||
match url {
|
match url {
|
||||||
Ok(url) => urls.push(url),
|
Ok(url) => urls.push(url),
|
||||||
Err(_) => return Err(Error::Syntax),
|
Err(_) => return Err(Error::Syntax),
|
||||||
|
@ -215,12 +221,13 @@ impl WorkerGlobalScopeMethods for WorkerGlobalScope {
|
||||||
.pipeline_id(Some(self.upcast::<GlobalScope>().pipeline_id()))
|
.pipeline_id(Some(self.upcast::<GlobalScope>().pipeline_id()))
|
||||||
.referrer_policy(None);
|
.referrer_policy(None);
|
||||||
|
|
||||||
let (url, source) =
|
let (url, source) = match fetch::load_whole_resource(
|
||||||
match load_whole_resource(request, &global_scope.resource_threads().sender()) {
|
request,
|
||||||
|
&global_scope.resource_threads().sender(),
|
||||||
|
&global_scope,
|
||||||
|
) {
|
||||||
Err(_) => return Err(Error::Network),
|
Err(_) => return Err(Error::Network),
|
||||||
Ok((metadata, bytes)) => {
|
Ok((metadata, bytes)) => (metadata.final_url, String::from_utf8(bytes).unwrap()),
|
||||||
(metadata.final_url, String::from_utf8(bytes).unwrap())
|
|
||||||
},
|
|
||||||
};
|
};
|
||||||
|
|
||||||
let result = self.runtime.evaluate_script(
|
let result = self.runtime.evaluate_script(
|
||||||
|
@ -381,7 +388,7 @@ impl WorkerGlobalScope {
|
||||||
match self.runtime.evaluate_script(
|
match self.runtime.evaluate_script(
|
||||||
self.reflector().get_jsobject(),
|
self.reflector().get_jsobject(),
|
||||||
&source,
|
&source,
|
||||||
self.worker_url.as_str(),
|
self.worker_url.borrow().as_str(),
|
||||||
1,
|
1,
|
||||||
rval.handle_mut(),
|
rval.handle_mut(),
|
||||||
) {
|
) {
|
||||||
|
|
|
@ -33,6 +33,7 @@ use crate::dom::workletglobalscope::WorkletGlobalScope;
|
||||||
use crate::dom::workletglobalscope::WorkletGlobalScopeInit;
|
use crate::dom::workletglobalscope::WorkletGlobalScopeInit;
|
||||||
use crate::dom::workletglobalscope::WorkletGlobalScopeType;
|
use crate::dom::workletglobalscope::WorkletGlobalScopeType;
|
||||||
use crate::dom::workletglobalscope::WorkletTask;
|
use crate::dom::workletglobalscope::WorkletTask;
|
||||||
|
use crate::fetch::load_whole_resource;
|
||||||
use crate::script_runtime::new_rt_and_cx;
|
use crate::script_runtime::new_rt_and_cx;
|
||||||
use crate::script_runtime::CommonScriptMsg;
|
use crate::script_runtime::CommonScriptMsg;
|
||||||
use crate::script_runtime::Runtime;
|
use crate::script_runtime::Runtime;
|
||||||
|
@ -47,7 +48,6 @@ use js::jsapi::JSTracer;
|
||||||
use js::jsapi::JS_GetGCParameter;
|
use js::jsapi::JS_GetGCParameter;
|
||||||
use js::jsapi::JS_GC;
|
use js::jsapi::JS_GC;
|
||||||
use msg::constellation_msg::PipelineId;
|
use msg::constellation_msg::PipelineId;
|
||||||
use net_traits::load_whole_resource;
|
|
||||||
use net_traits::request::Destination;
|
use net_traits::request::Destination;
|
||||||
use net_traits::request::RequestBuilder;
|
use net_traits::request::RequestBuilder;
|
||||||
use net_traits::request::RequestMode;
|
use net_traits::request::RequestMode;
|
||||||
|
@ -631,7 +631,11 @@ impl WorkletThread {
|
||||||
.credentials_mode(credentials.into())
|
.credentials_mode(credentials.into())
|
||||||
.origin(origin);
|
.origin(origin);
|
||||||
|
|
||||||
let script = load_whole_resource(request, &resource_fetcher)
|
let script = load_whole_resource(
|
||||||
|
request,
|
||||||
|
&resource_fetcher,
|
||||||
|
&global_scope.upcast::<GlobalScope>(),
|
||||||
|
)
|
||||||
.ok()
|
.ok()
|
||||||
.and_then(|(_, bytes)| String::from_utf8(bytes).ok());
|
.and_then(|(_, bytes)| String::from_utf8(bytes).ok());
|
||||||
|
|
||||||
|
|
|
@ -20,7 +20,9 @@ use crate::dom::promise::Promise;
|
||||||
use crate::dom::request::Request;
|
use crate::dom::request::Request;
|
||||||
use crate::dom::response::Response;
|
use crate::dom::response::Response;
|
||||||
use crate::dom::serviceworkerglobalscope::ServiceWorkerGlobalScope;
|
use crate::dom::serviceworkerglobalscope::ServiceWorkerGlobalScope;
|
||||||
use crate::network_listener::{self, NetworkListener, PreInvoke, ResourceTimingListener};
|
use crate::network_listener::{
|
||||||
|
self, submit_timing_data, NetworkListener, PreInvoke, ResourceTimingListener,
|
||||||
|
};
|
||||||
use crate::task_source::TaskSourceName;
|
use crate::task_source::TaskSourceName;
|
||||||
use ipc_channel::ipc;
|
use ipc_channel::ipc;
|
||||||
use ipc_channel::router::ROUTER;
|
use ipc_channel::router::ROUTER;
|
||||||
|
@ -28,6 +30,7 @@ use js::jsapi::JSAutoCompartment;
|
||||||
use net_traits::request::RequestBuilder;
|
use net_traits::request::RequestBuilder;
|
||||||
use net_traits::request::{Request as NetTraitsRequest, ServiceWorkersMode};
|
use net_traits::request::{Request as NetTraitsRequest, ServiceWorkersMode};
|
||||||
use net_traits::CoreResourceMsg::Fetch as NetTraitsFetch;
|
use net_traits::CoreResourceMsg::Fetch as NetTraitsFetch;
|
||||||
|
use net_traits::{CoreResourceMsg, CoreResourceThread, FetchResponseMsg};
|
||||||
use net_traits::{FetchChannels, FetchResponseListener, NetworkError};
|
use net_traits::{FetchChannels, FetchResponseListener, NetworkError};
|
||||||
use net_traits::{FetchMetadata, FilteredMetadata, Metadata};
|
use net_traits::{FetchMetadata, FilteredMetadata, Metadata};
|
||||||
use net_traits::{ResourceFetchTiming, ResourceTimingType};
|
use net_traits::{ResourceFetchTiming, ResourceTimingType};
|
||||||
|
@ -301,3 +304,43 @@ fn fill_headers_with_metadata(r: DomRoot<Response>, m: Metadata) {
|
||||||
r.set_raw_status(m.status);
|
r.set_raw_status(m.status);
|
||||||
r.set_final_url(m.final_url);
|
r.set_final_url(m.final_url);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Convenience function for synchronously loading a whole resource.
|
||||||
|
pub fn load_whole_resource(
|
||||||
|
request: RequestBuilder,
|
||||||
|
core_resource_thread: &CoreResourceThread,
|
||||||
|
global: &GlobalScope,
|
||||||
|
) -> Result<(Metadata, Vec<u8>), NetworkError> {
|
||||||
|
let (action_sender, action_receiver) = ipc::channel().unwrap();
|
||||||
|
let url = request.url.clone();
|
||||||
|
core_resource_thread
|
||||||
|
.send(CoreResourceMsg::Fetch(
|
||||||
|
request,
|
||||||
|
FetchChannels::ResponseMsg(action_sender, None),
|
||||||
|
))
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
|
let mut buf = vec![];
|
||||||
|
let mut metadata = None;
|
||||||
|
loop {
|
||||||
|
match action_receiver.recv().unwrap() {
|
||||||
|
FetchResponseMsg::ProcessRequestBody | FetchResponseMsg::ProcessRequestEOF => (),
|
||||||
|
FetchResponseMsg::ProcessResponse(Ok(m)) => {
|
||||||
|
metadata = Some(match m {
|
||||||
|
FetchMetadata::Unfiltered(m) => m,
|
||||||
|
FetchMetadata::Filtered { unsafe_, .. } => unsafe_,
|
||||||
|
})
|
||||||
|
},
|
||||||
|
FetchResponseMsg::ProcessResponseChunk(data) => buf.extend_from_slice(&data),
|
||||||
|
FetchResponseMsg::ProcessResponseEOF(Ok(_)) => {
|
||||||
|
let metadata = metadata.unwrap();
|
||||||
|
if let Some(timing) = &metadata.timing {
|
||||||
|
submit_timing_data(global, url, InitiatorType::Other, &timing);
|
||||||
|
}
|
||||||
|
return Ok((metadata, buf));
|
||||||
|
},
|
||||||
|
FetchResponseMsg::ProcessResponse(Err(e)) |
|
||||||
|
FetchResponseMsg::ProcessResponseEOF(Err(e)) => return Err(e),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -10,7 +10,9 @@ use crate::dom::performanceresourcetiming::{InitiatorType, PerformanceResourceTi
|
||||||
use crate::task::{TaskCanceller, TaskOnce};
|
use crate::task::{TaskCanceller, TaskOnce};
|
||||||
use crate::task_source::networking::NetworkingTaskSource;
|
use crate::task_source::networking::NetworkingTaskSource;
|
||||||
use crate::task_source::TaskSource;
|
use crate::task_source::TaskSource;
|
||||||
use net_traits::{Action, FetchResponseListener, FetchResponseMsg, ResourceTimingType};
|
use net_traits::{
|
||||||
|
Action, FetchResponseListener, FetchResponseMsg, ResourceFetchTiming, ResourceTimingType,
|
||||||
|
};
|
||||||
use servo_url::ServoUrl;
|
use servo_url::ServoUrl;
|
||||||
use std::sync::{Arc, Mutex};
|
use std::sync::{Arc, Mutex};
|
||||||
|
|
||||||
|
@ -42,14 +44,22 @@ pub fn submit_timing<T: ResourceTimingListener + FetchResponseListener>(listener
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
let global = listener.resource_timing_global();
|
submit_timing_data(
|
||||||
let performance_entry = PerformanceResourceTiming::new(
|
&listener.resource_timing_global(),
|
||||||
&global,
|
|
||||||
url,
|
url,
|
||||||
initiator_type,
|
initiator_type,
|
||||||
None,
|
listener.resource_timing(),
|
||||||
&listener.resource_timing(),
|
|
||||||
);
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn submit_timing_data(
|
||||||
|
global: &GlobalScope,
|
||||||
|
url: ServoUrl,
|
||||||
|
initiator_type: InitiatorType,
|
||||||
|
resource_timing: &ResourceFetchTiming,
|
||||||
|
) {
|
||||||
|
let performance_entry =
|
||||||
|
PerformanceResourceTiming::new(global, url, initiator_type, None, resource_timing);
|
||||||
global
|
global
|
||||||
.performance()
|
.performance()
|
||||||
.queue_entry(performance_entry.upcast::<PerformanceEntry>(), false);
|
.queue_entry(performance_entry.upcast::<PerformanceEntry>(), false);
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue