I’m using AppleScript to control Safari. Now I need to execute a Javascript in Safari using AppleScript’s do javascript
to evaluate an Xpath and use the return values in the AppleScript
This works
$x('//div/div/a').map(link => link.href)
But when I try something like this
document.evaluate(('//div/div/a').map(link => link.href), document, null, 0, null)
I get
TypeError: ('//div/div/a').map is not a function. (In '('//div/div/a').map(link => link.href)', '('//div/div/a').map' is undefined)
According to Google this error message means that I try to use map
on non-array object
. I think I understand what this means – (‘//div/div/a’) has not been evaluated before the .map(link => link.href)
is executed but I can’t figure out how to express this statement so that map
can be applied on an array.
If I add parenthesis like this
(document.evaluate(('//div/div/a')
).map(link => link.href), document, null, 0, null)
document.evaluate
don’t get enough arguments. I also tried
(document.evaluate(('//div/div/a'), document, null, 0, null))
).map(link => link.href)
thinking that document.evaluate
would return an array but that got me the same error message as above map is not a function
.
I’m not sure document.evaluate
even gives a meaningful result:
document.evaluate(('//div/div/a'), document, null, XPathResult.ANY_TYPE, null)
XPathResult {resultType: 4, invalidIteratorState: false, iterateNext: function, snapshotItem: function, ANY_TYPE: 0, …} = $3
Isn’t this basically an empty result? That is, not an array?
How can I use ‘//div/div/a’).map(link => link.href in document.evaluate or similar function so I get an array-like datastructure as the result?
Update: I found this https://codereview.stackexchange.com/questions/167571/evaluating-an-xpath-with-document-evaluate-to-get-an-array-of-nodes and it works on a superficial level – but then I am back at my original problem – for some reason I can’t get the href-attribute using an xpath – to which the only solution seems to be to use .map(link => link.href)
2
Answers
On XPathResult use
iterateNext()
methodI navigated to https://www.facebook.com/zuck/followers in Firefox, opened the JS console, and ran this code which is identical to the one in the page you linked to in your update, above, but with the XPath changed:
The result was an array of
href
attributes containing the URLs of the profile pages of Zuckerberg’s followers.Does that work for you in your browser? If not, does it work for you with a different browser?