Selenium and XPath - locating a link by containing text
Asked Answered
B

5

21

I'm trying to use XPath to find an element containing a piece of text, but I can't get it to work....

WebElement searchItemByText = driver.findElement(By.xpath("//*[@id='popover-search']/div/div/ul/li[1]/a/span[contains(text()='Some text')]"));

If I remove the last bit with the "contains" thing, it locates my span element, but I need to select it based on the text contents. It's not going to be a perfect match of 'Some text' either, because it might contain truncated strings as well.

What is the issue?

Bearce answered 15/4, 2014 at 8:28 Comment(1)
You should show the HTML of the a element (and it's surrounding elements) so we can compare it's structure to what your XPath follows.Espresso
E
56

I think the problem is here:

[contains(text()='Some text')]

To break this down,

  1. The [] are a conditional that operates on each individual node in that node set -- each span node in your case. It matches if any of the individual nodes it operates on match the conditions inside the brackets.
  2. text() is a selector that matches all of the text nodes that are children of the context node -- it returns a node set.
  3. contains is a function that operates on a string. If it is passed a node set, the node set is converted into a string by returning the string-value of the node in the node-set that is first in document order.

You should try to change this to

[text()[contains(.,'Some text')]]

  1. The outer [] are a conditional that operates on each individual node in that node set text() is a selector that matches all of the text nodes that are children of the context node -- it returns a node set.

  2. The inner [] are a conditional that operates on each node in that node set.

  3. contains is a function that operates on a string. Here it is passed an individual text node (.).

Equimolecular answered 15/4, 2014 at 8:41 Comment(4)
slight change in topic, can this work for class too? [contains(class()='Some class')]Mcconaghy
We need more answers like this, not just "try this" answers.Meridethmeridian
Thx Peter, could be just me but 10 years ago it was a lot more stimulating to write better answers on this site imoEquimolecular
tried [text()[contains(.,'Some text')]] and it is not working...Atomics
D
14

Use this

//*[@id='popover-search']/div/div/ul/li[1]/a/span[contains(text(),'Some text')]

OR

//*[@id='popover-search']/div/div/ul/li[1]/a/span[contains(.,'Some text')]
Disciple answered 15/4, 2014 at 8:38 Comment(1)
Thanks! Went with the first one :)Bearce
U
2
@FindBy(xpath = "//button[@class='btn btn-primary' and contains(text(), 'Submit')]") private WebElementFacade submitButton;

public void clickOnSubmitButton() {
    submitButton.click();
}   
Undersized answered 4/1, 2017 at 13:39 Comment(0)
A
0

This is working for me;

By.xpath("//span[contains(text(), 'Your Text')]")
Atomics answered 15/12, 2023 at 2:9 Comment(0)
U
-5

Use:

@FindBy(xpath = "//span[@class='y2' and contains(text(), 'Your Text')] ") 
private WebElementFacade emailLinkToVerifyAccount;
Undersized answered 14/7, 2016 at 12:27 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.