From 2a86f9d165f2c6482fcbe093f3029f09ae2b1232 Mon Sep 17 00:00:00 2001 From: Paul Rouget Date: Tue, 8 Dec 2015 04:39:37 +0100 Subject: [PATCH] Browser API: implement iframe.reload() --- components/compositing/constellation.rs | 24 ++++++++----- components/msg/constellation_msg.rs | 2 +- components/script/dom/htmliframeelement.rs | 11 ++++-- components/script/script_task.rs | 2 +- tests/wpt/mozilla/meta/MANIFEST.json | 6 ++++ .../tests/mozilla/mozbrowser/reload.html | 35 +++++++++++++++++++ 6 files changed, 67 insertions(+), 13 deletions(-) create mode 100644 tests/wpt/mozilla/tests/mozilla/mozbrowser/reload.html diff --git a/components/compositing/constellation.rs b/components/compositing/constellation.rs index 7013d9250de..7d0b909308b 100644 --- a/components/compositing/constellation.rs +++ b/components/compositing/constellation.rs @@ -790,6 +790,17 @@ impl Constellation { // containing_page_pipeline_id's frame tree's children. This message is never the result of a // page navigation. fn handle_script_loaded_url_in_iframe_msg(&mut self, load_info: IframeLoadInfo) { + let old_pipeline_id = load_info.old_subpage_id.map(|old_subpage_id| { + self.find_subpage(load_info.containing_pipeline_id, old_subpage_id).id + }); + + // If no url is specified, reload. + let new_url = match (old_pipeline_id, load_info.url) { + (_, Some(ref url)) => url.clone(), + (Some(old_pipeline_id), None) => self.pipeline(old_pipeline_id).url.clone(), + (None, None) => url!("about:blank"), + }; + // Compare the pipeline's url to the new url. If the origin is the same, // then reuse the script task in creating the new pipeline let script_chan = { @@ -797,27 +808,24 @@ impl Constellation { let source_url = source_pipeline.url.clone(); - let same_script = (source_url.host() == load_info.url.host() && - source_url.port() == load_info.url.port()) && + let same_script = (source_url.host() == new_url.host() && + source_url.port() == new_url.port()) && load_info.sandbox == IFrameSandboxState::IFrameUnsandboxed; // FIXME(tkuehn): Need to follow the standardized spec for checking same-origin // Reuse the script task if the URL is same-origin if same_script { debug!("Constellation: loading same-origin iframe, \ - parent url {:?}, iframe url {:?}", source_url, load_info.url); + parent url {:?}, iframe url {:?}", source_url, new_url); Some(source_pipeline.script_chan.clone()) } else { debug!("Constellation: loading cross-origin iframe, \ - parent url {:?}, iframe url {:?}", source_url, load_info.url); + parent url {:?}, iframe url {:?}", source_url, new_url); None } }; // Create the new pipeline, attached to the parent and push to pending frames - let old_pipeline_id = load_info.old_subpage_id.map(|old_subpage_id| { - self.find_subpage(load_info.containing_pipeline_id, old_subpage_id).id - }); let window_size = old_pipeline_id.and_then(|old_pipeline_id| { self.pipeline(old_pipeline_id).size }); @@ -825,7 +833,7 @@ impl Constellation { Some((load_info.containing_pipeline_id, load_info.new_subpage_id)), window_size, script_chan, - LoadData::new(load_info.url)); + LoadData::new(new_url)); self.subpage_map.insert((load_info.containing_pipeline_id, load_info.new_subpage_id), load_info.new_pipeline_id); diff --git a/components/msg/constellation_msg.rs b/components/msg/constellation_msg.rs index 139a77bc4fb..df25736074e 100644 --- a/components/msg/constellation_msg.rs +++ b/components/msg/constellation_msg.rs @@ -217,7 +217,7 @@ bitflags! { #[derive(Deserialize, Serialize)] pub struct IframeLoadInfo { /// Url to load - pub url: Url, + pub url: Option, /// Pipeline ID of the parent of this iframe pub containing_pipeline_id: PipelineId, /// The new subpage ID for this load diff --git a/components/script/dom/htmliframeelement.rs b/components/script/dom/htmliframeelement.rs index 3798ab4f539..e7816399619 100644 --- a/components/script/dom/htmliframeelement.rs +++ b/components/script/dom/htmliframeelement.rs @@ -90,7 +90,7 @@ impl HTMLIFrameElement { (subpage_id, old_subpage_id) } - pub fn navigate_child_browsing_context(&self, url: Url) { + pub fn navigate_or_reload_child_browsing_context(&self, url: Option) { let sandboxed = if self.is_sandboxed() { IFrameSandboxed } else { @@ -127,7 +127,7 @@ impl HTMLIFrameElement { None => url!("about:blank"), }; - self.navigate_child_browsing_context(url); + self.navigate_or_reload_child_browsing_context(Some(url)); } #[allow(unsafe_code)] @@ -399,7 +399,12 @@ impl HTMLIFrameElementMethods for HTMLIFrameElement { // https://developer.mozilla.org/en-US/docs/Web/API/HTMLIFrameElement/reload fn Reload(&self, _hardReload: bool) -> Fallible<()> { - Err(Error::NotSupported) + if mozbrowser_enabled() { + if self.upcast::().is_in_doc() { + self.navigate_or_reload_child_browsing_context(None); + } + } + Ok(()) } // https://developer.mozilla.org/en-US/docs/Web/API/HTMLIFrameElement/stop diff --git a/components/script/script_task.rs b/components/script/script_task.rs index f0ea6bd1354..77cc03a53ac 100644 --- a/components/script/script_task.rs +++ b/components/script/script_task.rs @@ -1943,7 +1943,7 @@ impl ScriptTask { doc.find_iframe(subpage_id) }); if let Some(iframe) = iframe.r() { - iframe.navigate_child_browsing_context(load_data.url); + iframe.navigate_or_reload_child_browsing_context(Some(load_data.url)); } } None => { diff --git a/tests/wpt/mozilla/meta/MANIFEST.json b/tests/wpt/mozilla/meta/MANIFEST.json index cdb4e4b59ae..5ccf1aa3c3e 100644 --- a/tests/wpt/mozilla/meta/MANIFEST.json +++ b/tests/wpt/mozilla/meta/MANIFEST.json @@ -5643,6 +5643,12 @@ "url": "/_mozilla/mozilla/mozbrowser/mozbrowsericonchange_event.html" } ], + "mozilla/mozbrowser/reload.html": [ + { + "path": "mozilla/mozbrowser/reload.html", + "url": "/_mozilla/mozilla/mozbrowser/reload.html" + } + ], "mozilla/navigator.html": [ { "path": "mozilla/navigator.html", diff --git a/tests/wpt/mozilla/tests/mozilla/mozbrowser/reload.html b/tests/wpt/mozilla/tests/mozilla/mozbrowser/reload.html new file mode 100644 index 00000000000..7dea32d3730 --- /dev/null +++ b/tests/wpt/mozilla/tests/mozilla/mozbrowser/reload.html @@ -0,0 +1,35 @@ + + + + + + +