mirror of
https://github.com/servo/servo.git
synced 2025-06-06 16:45:39 +00:00
Set descendant's attribute's owner document in Node::adopt (#35076)
* Set descendant's attribute's owner document in Node::adopt Signed-off-by: Simon Wülker <simon.wuelker@arcor.de> * Add test that adopting an element into a new doc updates the attribute' owner docs Signed-off-by: Simon Wülker <simon.wuelker@arcor.de> --------- Signed-off-by: Simon Wülker <simon.wuelker@arcor.de>
This commit is contained in:
parent
dabe162d44
commit
c070372d1e
4 changed files with 38 additions and 7 deletions
|
@ -160,6 +160,7 @@ use crate::task::TaskOnce;
|
|||
// and when the element enters or leaves a browsing context container.
|
||||
// https://html.spec.whatwg.org/multipage/#selector-focus
|
||||
|
||||
/// <https://dom.spec.whatwg.org/#element>
|
||||
#[dom_struct]
|
||||
pub(crate) struct Element {
|
||||
node: Node,
|
||||
|
|
|
@ -1886,30 +1886,46 @@ impl Node {
|
|||
pub(crate) fn adopt(node: &Node, document: &Document) {
|
||||
document.add_script_and_layout_blocker();
|
||||
|
||||
// Step 1.
|
||||
// Step 1. Let oldDocument be node’s node document.
|
||||
let old_doc = node.owner_doc();
|
||||
old_doc.add_script_and_layout_blocker();
|
||||
// Step 2.
|
||||
|
||||
// Step 2. If node’s parent is non-null, then remove node.
|
||||
node.remove_self();
|
||||
// Step 3.
|
||||
|
||||
// Step 3. If document is not oldDocument:
|
||||
if &*old_doc != document {
|
||||
// Step 3.1.
|
||||
// Step 3.1. For each inclusiveDescendant in node’s shadow-including inclusive descendants:
|
||||
for descendant in node.traverse_preorder(ShadowIncluding::Yes) {
|
||||
// Step 3.1.1 Set inclusiveDescendant’s node document to document.
|
||||
descendant.set_owner_doc(document);
|
||||
|
||||
// Step 3.1.2 If inclusiveDescendant is an element, then set the node document of each
|
||||
// attribute in inclusiveDescendant’s attribute list to document.
|
||||
if let Some(element) = descendant.downcast::<Element>() {
|
||||
for attribute in element.attrs().iter() {
|
||||
attribute.upcast::<Node>().set_owner_doc(document);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Step 3.2 For each inclusiveDescendant in node’s shadow-including inclusive descendants
|
||||
// that is custom, enqueue a custom element callback reaction with inclusiveDescendant,
|
||||
// callback name "adoptedCallback", and « oldDocument, document ».
|
||||
for descendant in node
|
||||
.traverse_preorder(ShadowIncluding::Yes)
|
||||
.filter_map(|d| d.as_custom_element())
|
||||
{
|
||||
// Step 3.2.
|
||||
ScriptThread::enqueue_callback_reaction(
|
||||
&descendant,
|
||||
CallbackReaction::Adopted(old_doc.clone(), DomRoot::from_ref(document)),
|
||||
None,
|
||||
);
|
||||
}
|
||||
|
||||
// Step 3.3 For each inclusiveDescendant in node’s shadow-including inclusive descendants,
|
||||
// in shadow-including tree order, run the adopting steps with inclusiveDescendant and oldDocument.
|
||||
for descendant in node.traverse_preorder(ShadowIncluding::Yes) {
|
||||
// Step 3.3.
|
||||
vtable_for(&descendant).adopting_steps(&old_doc);
|
||||
}
|
||||
}
|
||||
|
|
2
tests/wpt/meta/MANIFEST.json
vendored
2
tests/wpt/meta/MANIFEST.json
vendored
|
@ -606523,7 +606523,7 @@
|
|||
]
|
||||
],
|
||||
"Node-mutation-adoptNode.html": [
|
||||
"9c9594c07b22a4ac94b3703f8ab1711b41a759e4",
|
||||
"812a2e4d3af326c1e73115c6fc50726bc4fc4b23",
|
||||
[
|
||||
null,
|
||||
{}
|
||||
|
|
|
@ -20,4 +20,18 @@ test(() => {
|
|||
assert_equals(div.firstChild.ownerDocument, document);
|
||||
}, "simple append of foreign div with text");
|
||||
|
||||
test(function() {
|
||||
var div = document.createElement("div");
|
||||
div.id = "foobar";
|
||||
|
||||
assert_equals(div.ownerDocument, document);
|
||||
assert_equals(div.attributes[0].ownerDocument, document);
|
||||
|
||||
var other_doc = document.implementation.createHTMLDocument();
|
||||
other_doc.body.appendChild(div);
|
||||
|
||||
assert_equals(div.ownerDocument, other_doc);
|
||||
assert_equals(div.attributes[0].ownerDocument, other_doc);
|
||||
}, "Adopting an element into a different document update's the element's owner doc as well as the owner docs of it's attributes")
|
||||
|
||||
</script>
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue