jsdom
jsdom copied to clipboard
Default type to XPathResult.ANY_TYPE in XPathExpression.evaluate
I got a DOMException when using the HTMX library inside JSDOM, as it does not provide an argument for the type parameter in XPathExpression.evaluate. This PR allows the type parameter to be optional and defaults the value to XPathResult.ANY_TYPE (0).
The whatwg living DOM spec states that the type argument should default to 0 (any): https://dom.spec.whatwg.org/#interface-xpathexpression.
Whilst the IDL in the level 3 XPath spec doesn't state explicitly that the type parameter is optional, it does use the phrase "If a specific type is specified" in the parameter description, which implies optionality: (https://www.w3.org/TR/DOM-Level-3-XPath/xpath.html#XPathExpression). Therefore, I believe this patch is spec-compliant on both counts.
Fixes #3422
Can you add a test for this, or find an existing one, per the instructions in CONTRIBUTING.md?
@deej-io @domenic any chance this can be merged? Facing this issue. Is there a workaround?
Sorry, I've not had a chance to take another look at this yet. Will see if I can find some time today to get a test case sorted.
Just ran into this issue, using JSDOM to test an HTMX application.
Until merged, I have the following workaround:
const fixXPathEvaluator = (browser) => {
const { XPathExpression, XPathResult } = browser.window;
const evaluate = XPathExpression.prototype.evaluate;
XPathExpression.prototype.evaluate = function (context, type, res) {
return evaluate.call(this, context, type || XPathResult.ANY_TYPE, res);
};
// YOU PROBABLY NEED TO ADD THIS TOO
// browser.window.Document.prototype.evaluate = XPathExpression.prototype.evaluate
};
From browsing the jsdom code, it appears that each jsdom instance has it's own XPathEvaluator class, so you can't fix it in a global setup, but need to call this for every instance of JSDOM you create. In my case (where I use it as a headless browser for a running web server)
const browser = await JSDOM.fromURL(url, { runScripts: "dangerously", resources: "usable" });
fixXPathEvaluator(browser);
I didn't replace Document.prototype.evaluate as I don't have any issues with that, but I guess it could be necessary.