XPath: implement lang() and id() core functions (#34594)

XPath's `lang()` and `id()` functions were still unimplemented.

Also:
* Add WPT tests for `id()`.
* Fix uniqueness check in `NodesetHelpers::document_order_unique`.
* Tweak the AST a bit to make it clearer to express "no predicates".
* Fix a parsing bug where "/" was attempted before "//", leaving the
"//" branch as always unused.

---
- [x] `./mach build -d` does not report any errors
- [x] `./mach test-tidy` does not report any errors
- [x] These changes fix #34593 
- [x] There are tests for these changes

---------

Signed-off-by: Ville Lindholm <ville@lindholm.dev>
This commit is contained in:
Ville Lindholm 2025-06-02 22:00:13 +03:00 committed by GitHub
parent 1dfc14d2fb
commit 8cfb6e33fe
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
11 changed files with 276 additions and 61 deletions

View file

@ -8,7 +8,6 @@ use std::{fmt, string};
use crate::dom::bindings::codegen::Bindings::NodeBinding::Node_Binding::NodeMethods;
use crate::dom::bindings::root::DomRoot;
use crate::dom::bindings::utils::AsVoidPtr;
use crate::dom::node::Node;
/// The primary types of values that an XPath expression returns as a result.
@ -216,7 +215,7 @@ impl NodesetHelpers for Vec<DomRoot<Node>> {
}
fn document_order(&self) -> Vec<DomRoot<Node>> {
let mut nodes: Vec<DomRoot<Node>> = self.clone();
if nodes.len() == 1 {
if nodes.len() <= 1 {
return nodes;
}
@ -233,10 +232,13 @@ impl NodesetHelpers for Vec<DomRoot<Node>> {
nodes
}
fn document_order_unique(&self) -> Vec<DomRoot<Node>> {
let mut nodes: Vec<DomRoot<Node>> = self.document_order();
let mut seen = HashSet::new();
let unique_nodes: Vec<DomRoot<Node>> = self
.iter()
.filter(|node| seen.insert(node.to_opaque()))
.cloned()
.collect();
nodes.dedup_by_key(|n| n.as_void_ptr());
nodes
unique_nodes.document_order()
}
}