7

I'm using selenium to get some text on my webpage using xpath.

The page tag structure is as follows -

<span id="data" class="firefinder-match">
    Seat Height, Laden
  <sup>
     <a class="speckeyfootnote" rel="p7" href="#">7</a>
  </sup>
</span>

If I use the following code -

driver.findElement(By.xpath("//span[@id='data']")).getText();

I get the result = Seat Height, Laden 7

But I want to avoid reading the text within the <sup> tags and get the result Seat Height, Laden

Please let me know which xpath expression I can use to get my desired result.

5
  • 3
    Um. In plain XPath (that would be able to return Strings and not only WebElements), you could do //span[@id='data']/text()[1]. One possible solution I can think of uses JS, the second gets the whole text and then deletes everything from child elements. Both solutions are rather ugly and I would like to see a nicer one. Anyway, if there's no answer in some reasonable short time, I'll post it. Commented May 30, 2012 at 8:44
  • 1
    Any reason why xpath is your only option? Webdriver takes longest to locate an element by the xpath Commented May 30, 2012 at 14:57
  • well I use xpath only because I'm comfortable with it. If there is any other way to solve my problem, I will be grateful. Commented May 31, 2012 at 4:24
  • 1. As the span has id, it is the best to use id instead of xpath. 2. cssSelector is faster than xpath, that's why I suggest to use cssSelector instead of xpath. Commented Sep 6, 2012 at 7:11
  • According to the post below, you can't select text nodes by css either: stackoverflow.com/questions/5688712/…. So selecting by css won't help Commented Apr 23, 2014 at 14:07

1 Answer 1

8

I don't know about any way to do this in Selenium, so there's my JS solution. The idea is to get all children of the element (including the text nodes) and then select only the text nodes. You might need to add some .trim() (or JS equivalent) calls to get rid of unneeded spaces.

The whole code:

WebElement elem = driver.findElement(By.id("data"));
String text;
if (driver instanceof JavascriptExecutor) {
    text = ((JavascriptExecutor)driver).executeScript(
            "var nodes = arguments[0].childNodes;" +
            "var text = '';" +
            "for (var i = 0; i < nodes.length; i++) {" +
            "    if (nodes[i].nodeType == Node.TEXT_NODE) {" +
            "        text += nodes[i].textContent;" +
            "    }" +
            "}" +
            "return text;"
            , elem);
}

And just the JS for better readability.

var nodes = arguments[0].childNodes;
var text = '';
for (var i = 0; i < nodes.length; i++) {
    if (nodes[i].nodeType == Node.TEXT_NODE) {
        text += nodes[i].textContent;
    }
}
return text;
Sign up to request clarification or add additional context in comments.

2 Comments

Hey nice solution to get the result through the JS. But I want to ask if there is anything like a ! operator in xpath by which we can neglect certain tags.
Yes, there is. However, it won't work in this particular case since you are still selecting the outer element and that contains all the child elements by default. The text node is also a child element of it and a usual parser could get it. WebDriver is not a usual parser and does not have this functionality. Yet. If you want to know any particular XPath, feel free to ask.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.