Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Implement custom element reactions #17614

Merged
merged 4 commits into from Jul 18, 2017
Merged
Changes from 1 commit
Commits
File filter...
Filter file types
Jump to…
Jump to file
Failed to load files.

Always

Just for now

Prev

Invoke backup element queue via a microtask

  • Loading branch information
cbrewster committed Jul 18, 2017
commit 9b587a4f2d1d8abc70fa6d6220ac31e6dac32c72
@@ -29,6 +29,8 @@ use js::conversions::ToJSValConvertible;
use js::jsapi::{Construct1, IsCallable, IsConstructor, HandleValueArray, HandleObject, MutableHandleValue};
use js::jsapi::{Heap, JS_GetProperty, JSAutoCompartment, JSContext};
use js::jsval::{JSVal, NullValue, ObjectValue, UndefinedValue};
use microtask::Microtask;
use script_thread::ScriptThread;
use std::cell::Cell;
use std::collections::{HashMap, VecDeque};
use std::ops::Deref;
@@ -532,13 +534,7 @@ impl CustomElementReactionStack {
self.processing_backup_element_queue.set(BackupElementQueueFlag::Processing);

// Step 4
// TODO: Invoke Microtask

// Step 4.1
self.backup_queue.invoke_reactions();

// Step 4.2
self.processing_backup_element_queue.set(BackupElementQueueFlag::NotProcessing);
ScriptThread::enqueue_microtask(Microtask::CustomElementReaction);
}

/// https://html.spec.whatwg.org/multipage/#enqueue-a-custom-element-callback-reaction
@@ -630,6 +626,7 @@ impl ElementQueue {
while let Some(element) = self.next_element() {
element.invoke_reactions()

This comment has been minimized.

@jdm

jdm Jul 12, 2017

Member

Can these reactions end up appending an element to this queue?

This comment has been minimized.

@cbrewster

cbrewster Jul 13, 2017

Author Member

I do not believe so, there are two queues an element can be added to:

  1. The current element queue.
  2. The backup element queue.

For the first case, the current element queue is popped from the custom element reaction stack thus it is no longer the current element queue which means no element will be added to it.

The second case is the backup element queue has the processing_backup_element_queue flag which prevents elements being enqueued until the flag is set to NotProcessing.

This comment has been minimized.

@cbrewster

cbrewster Jul 13, 2017

Author Member

Oh actually in the second case, an element can be appended to the backup element queue is being invoked. The flag check occurs after the element is appended to the queue. This is what causes the crash in the test expectations.

I want to change it so the queue is not borrowed for the duration of the loop. Instead if element are popped and processed, new element can be appended to the queue. But I always run into unrooted must root errors. any ideas?

while let Some(element) = self.queue.borrow_mut().pop_front().map(|e| Root::from_ref(&*e)) {
    element.invoke_reactions()
}

This comment has been minimized.

@cbrewster

cbrewster Jul 17, 2017

Author Member

Avoiding the closure appears to appease the lint

self.queue.borrow_mut().pop_front().as_ref().map(JS::deref).map(Root::from_ref)
}
self.queue.borrow_mut().clear();

This comment has been minimized.

@jdm

jdm Jul 17, 2017

Member

This shouldn't be necessary since we now pop, right?

}

fn next_element(&self) -> Option<Root<Element>> {
@@ -15,6 +15,7 @@ use dom::htmlimageelement::ImageElementMicrotask;
use dom::htmlmediaelement::MediaElementMicrotask;
use dom::mutationobserver::MutationObserver;
use msg::constellation_msg::PipelineId;
use script_thread::ScriptThread;
use std::cell::Cell;
use std::mem;
use std::rc::Rc;
@@ -33,6 +34,7 @@ pub enum Microtask {
Promise(EnqueuedPromiseCallback),
MediaElement(MediaElementMicrotask),
ImageElement(ImageElementMicrotask),
CustomElementReaction,
NotifyMutationObservers,
}

@@ -87,6 +89,9 @@ impl MicrotaskQueue {
Microtask::ImageElement(ref task) => {
task.handler();
},
Microtask::CustomElementReaction => {
ScriptThread::invoke_backup_element_queue();
},
Microtask::NotifyMutationObservers => {
MutationObserver::notify_mutation_observers();
}
@@ -755,6 +755,15 @@ impl ScriptThread {
})
}

pub fn invoke_backup_element_queue() {
SCRIPT_THREAD_ROOT.with(|root| {
if let Some(script_thread) = root.get() {
let script_thread = unsafe { &*script_thread };
script_thread.custom_element_reaction_stack.invoke_backup_element_queue();
}
})
}

/// Creates a new script thread.
pub fn new(state: InitialScriptState,
port: Receiver<MainThreadScriptMsg>,
@@ -129,3 +129,48 @@
[Custom Elements: adoptedCallback]
expected: FAIL

[Inserting a custom element into the owner document must not enqueue and invoke adoptedCallback]
expected: FAIL

[Inserting a custom element into the document of the template elements must enqueue and invoke adoptedCallback]
expected: FAIL

[Moving a custom element from the owner document into the document of the template elements must enqueue and invoke adoptedCallback]
expected: FAIL

[Inserting a custom element into a new document must enqueue and invoke adoptedCallback]
expected: FAIL

[Moving a custom element from the owner document into a new document must enqueue and invoke adoptedCallback]
expected: FAIL

[Inserting a custom element into a cloned document must enqueue and invoke adoptedCallback]
expected: FAIL

[Moving a custom element from the owner document into a cloned document must enqueue and invoke adoptedCallback]
expected: FAIL

[Inserting a custom element into a document created by createHTMLDocument must enqueue and invoke adoptedCallback]
expected: FAIL

[Moving a custom element from the owner document into a document created by createHTMLDocument must enqueue and invoke adoptedCallback]
expected: FAIL

[Inserting a custom element into an HTML document created by createDocument must enqueue and invoke adoptedCallback]
expected: FAIL

[Moving a custom element from the owner document into an HTML document created by createDocument must enqueue and invoke adoptedCallback]
expected: FAIL

[Inserting a custom element into the document of an iframe must enqueue and invoke adoptedCallback]
expected: FAIL

[Moving a custom element from the owner document into the document of an iframe must enqueue and invoke adoptedCallback]
expected: FAIL

[Inserting a custom element into an HTML document fetched by XHR must enqueue and invoke adoptedCallback]
expected: FAIL

[Moving a custom element from the owner document into an HTML document fetched by XHR must enqueue and invoke adoptedCallback]
expected: FAIL

@@ -99,3 +99,27 @@
[Custom Elements: connectedCallback]
expected: FAIL

[Inserting a custom element into the document must enqueue and invoke connectedCallback]
expected: FAIL

[Inserting a custom element into the document of the template elements must enqueue and invoke connectedCallback]
expected: FAIL

[Inserting a custom element into a new document must enqueue and invoke connectedCallback]
expected: FAIL

[Inserting a custom element into a cloned document must enqueue and invoke connectedCallback]
expected: FAIL

[Inserting a custom element into a document created by createHTMLDocument must enqueue and invoke connectedCallback]
expected: FAIL

[Inserting a custom element into an HTML document created by createDocument must enqueue and invoke connectedCallback]
expected: FAIL

[Inserting a custom element into the document of an iframe must enqueue and invoke connectedCallback]
expected: FAIL

[Inserting a custom element into an HTML document fetched by XHR must enqueue and invoke connectedCallback]
expected: FAIL

@@ -75,3 +75,51 @@
[Custom Elements: disconnectedCallback]
expected: FAIL

[Removing a custom element from the document must enqueue and invoke disconnectedCallback]
expected: FAIL

[Removing an ancestor of custom element from the document must enqueue and invoke disconnectedCallback]
expected: FAIL

[Removing a custom element from the document of the template elements must enqueue and invoke disconnectedCallback]
expected: FAIL

[Removing an ancestor of custom element from the document of the template elements must enqueue and invoke disconnectedCallback]
expected: FAIL

[Removing a custom element from a new document must enqueue and invoke disconnectedCallback]
expected: FAIL

[Removing an ancestor of custom element from a new document must enqueue and invoke disconnectedCallback]
expected: FAIL

[Removing a custom element from a cloned document must enqueue and invoke disconnectedCallback]
expected: FAIL

[Removing an ancestor of custom element from a cloned document must enqueue and invoke disconnectedCallback]
expected: FAIL

[Removing a custom element from a document created by createHTMLDocument must enqueue and invoke disconnectedCallback]
expected: FAIL

[Removing an ancestor of custom element from a document created by createHTMLDocument must enqueue and invoke disconnectedCallback]
expected: FAIL

[Removing a custom element from an HTML document created by createDocument must enqueue and invoke disconnectedCallback]
expected: FAIL

[Removing an ancestor of custom element from an HTML document created by createDocument must enqueue and invoke disconnectedCallback]
expected: FAIL

[Removing a custom element from the document of an iframe must enqueue and invoke disconnectedCallback]
expected: FAIL

[Removing an ancestor of custom element from the document of an iframe must enqueue and invoke disconnectedCallback]
expected: FAIL

[Removing a custom element from an HTML document fetched by XHR must enqueue and invoke disconnectedCallback]
expected: FAIL

[Removing an ancestor of custom element from an HTML document fetched by XHR must enqueue and invoke disconnectedCallback]
expected: FAIL

@@ -0,0 +1,23 @@
[ChildNode.html]
type: testharness
[before on ChildNode must enqueue a connected reaction]
expected: FAIL

[before on ChildNode must enqueue a disconnected reaction, an adopted reaction, and a connected reaction when the custom element was in another document]
expected: FAIL

[after on ChildNode must enqueue a connected reaction]
expected: FAIL

[after on ChildNode must enqueue a disconnected reaction, an adopted reaction, and a connected reaction when the custom element was in another document]
expected: FAIL

[replaceWith on ChildNode must enqueue a connected reaction]
expected: FAIL

[replaceWith on ChildNode must enqueue a disconnected reaction, an adopted reaction, and a connected reaction when the custom element was in another document]
expected: FAIL

[replaceWith on ChildNode must enqueue a disconnected reaction]
expected: FAIL

@@ -21,3 +21,15 @@
[importNode on Document must construct a new custom element when importing a custom element from a template]
expected: FAIL

[adoptNode on Document must enqueue an adopted reaction when importing a custom element]
expected: FAIL

[title on Document must enqueue disconnectedCallback when removing a custom element]
expected: FAIL

[write on Document must enqueue connectedCallback after constructing a custom element]
expected: FAIL

[writeln on Document must enqueue connectedCallback after constructing a custom element]
expected: FAIL

@@ -69,3 +69,15 @@
[insertAdjacentHTML on Element must enqueue a attributeChanged reaction for a newly constructed custom element]
expected: FAIL

[insertAdjacentElement on Element must enqueue a connected reaction]
expected: FAIL

[insertAdjacentElement on Element must enqueue a disconnected reaction, an adopted reaction, and a connected reaction when the custom element was in another document]
expected: FAIL

[innerHTML on Element must enqueue a disconnected reaction]
expected: FAIL

[outerHTML on Element must enqueue a disconnected reaction]
expected: FAIL

@@ -6,3 +6,12 @@
[add on HTMLOptionsCollection must enqueue connectedCallback when inserting a custom element]
expected: FAIL

[length on HTMLOptionsCollection must enqueue disconnectedCallback when removing a custom element]
expected: FAIL

[The indexed setter on HTMLOptionsCollection must enqueue disconnectedCallback when removing a custom element]
expected: FAIL

[remove on HTMLOptionsCollection must enqueue disconnectedCallback when removing a custom element]
expected: FAIL

@@ -9,3 +9,9 @@
[add on HTMLSelectElement must enqueue connectedCallback when inserting a custom element]
expected: FAIL

[length on HTMLSelectElement must enqueue disconnectedCallback when removing a custom element]
expected: FAIL

[remove on HTMLSelectElement must enqueue disconnectedCallback when removing a custom element]
expected: FAIL

@@ -0,0 +1,5 @@
[HTMLTitleElement.html]
type: testharness
[text on HTMLTitleElement must enqueue disconnectedCallback when removing a custom element]
expected: FAIL

@@ -15,3 +15,24 @@
[cloneNode on Node must enqueue an attributeChanged reaction when cloning an element only for observed attributes]
expected: FAIL

[insertBefore on ChildNode must enqueue a connected reaction]
expected: FAIL

[insertBefore on ChildNode must enqueue a disconnected reaction, an adopted reaction, and a connected reaction when the custom element was in another document]
expected: FAIL

[appendChild on ChildNode must enqueue a connected reaction]
expected: FAIL

[appendChild on ChildNode must enqueue a disconnected reaction, an adopted reaction, and a connected reaction when the custom element was in another document]
expected: FAIL

[replaceChild on ChildNode must enqueue a connected reaction]
expected: FAIL

[replaceChild on ChildNode must enqueue a disconnected reaction, an adopted reaction, and a connected reaction when the custom element was in another document]
expected: FAIL

[removeChild on ChildNode must enqueue a disconnected reaction]
expected: FAIL

@@ -0,0 +1,14 @@
[ParentNode.html]
type: testharness
[prepend on ParentNode must enqueue a connected reaction]
expected: FAIL

[prepend on ParentNode must enqueue a disconnected reaction, an adopted reaction, and a connected reaction when the custom element was in another document]
expected: FAIL

[append on ParentNode must enqueue a connected reaction]
expected: FAIL

[append on ParentNode must enqueue a disconnected reaction, an adopted reaction, and a connected reaction when the custom element was in another document]
expected: FAIL

@@ -15,3 +15,18 @@
[createContextualFragment on Range must construct a custom element]
expected: FAIL

[deleteContents on Range must enqueue a disconnected reaction]
expected: FAIL

[insertNode on Range must enqueue a connected reaction]
expected: FAIL

[insertNode on Range must enqueue a disconnected reaction, an adopted reaction, and a connected reaction when the custom element was in another document]
expected: FAIL

[surroundContents on Range must enqueue a connected reaction]
expected: FAIL

[surroundContents on Range must enqueue a disconnected reaction, an adopted reaction, and a connected reaction when the custom element was in another document]
expected: FAIL

ProTip! Use n and p to navigate between commits in a pull request.
You can’t perform that action at this time.