How to find sibling element text using xpath
<label>
<span>some span</span>
</label>
<label>
Second Label
</label>
//label[normalize-space(text()) = 'some span']/following-sibling::label/text()
In Python we would do something like this :
driver.find_element(By.XPATH, "//label[//text()[normalize-space() = 'some span']]/following-sibling::label").text
basically Python Selenium bindings provide a text method for web element. getText() for Java.
Now if you want to heavily dependent on XPATH then you can try below XPATH :
//span[contains(text(),'some span')]/../following-sibling::label
or probably
//span[contains(text(),'some span')]/../following-sibling::label[contains(text(),'Second Label')]
I would use:
//label[span[text()='some span']]/following-sibling::label/text()
or if you only want to find that if it is actually the first following-element:(i.e: you don't want to find that label if there is a input in between)
//label[span[text()='some span']]/following-sibling::*[1][self::label]/text()
or if you only want to find that the first following label(if there even more following label-elements):
//label[span[text()='some span']]/following-sibling::label[1]/text()
Related
Quick one, i am trying to avoid using xpath and using css selectors due to performance issues xpath can have so i would like to know the right approach of locating for example "A" in the list
<div class="input-search-suggests" xpath="1">
<div class="input-search-suggests-item">A</div>
<div class="input-search-suggests-item">B</div>
<div class="input-search-suggests-item">C</div>
</div>
Currently i am locating A using xpath / span but it would be indeed sufficient locating all elements and then grabbing A from the list that have same class which is "input-search-suggests-item"
#FindBy(xpath = "//span[contains(text(),'A')]")
CSS_SELECTOR does not have support for direct text what xpath has.
What this means is, for the below xpath
xpath = "//span[contains(text(),'A')]"
based on text A you can not write a css selector.
Instead to locate A using css selector, you can do :
div.input-search-suggests > div.input-search-suggests-item
In Selenium something like this :
#FindBy(cssSelector= "div.input-search-suggests > div.input-search-suggests-item")
Even though it will have 3 matching nodes, but findElement will take the first web element.
Also you may wanna look at nth-child(n)
div.input-search-suggests > nth-child(1)
to make use of index to locate A, B, C
Here is the Reference Link
The page contains a multi-select dropdown (similar to the one below)
The html code looks like the below:
<div class="button-and-dropdown-div>
<button class="Multi-Select-Button">multi-select button</button>
<div class="dropdown-containing-options>
<label class="dropdown-item">
<input class="checkbox">
"
Name
"
</label>
<label class="dropdown-item">
<input class="checkbox">
"
Address
"
</label>
</div>
After testing in firefox developer tools, I was finally able to figure out the xPath needed in order to get the text for a certain label ...
The below XPath statement will return the the text "Phone"
$x("(//label[#class='dropdown-item'])[4]/text()[2]")
The label contains multiple text items (although it looks like there is just one text object when looking at the UI) in the label element. There are actually two text elements within each label element. The first is always empty, the second contains the actual text (as shown in the below image when observing the element through the Firefox developer tool's console window):
Question:
How do I modify the XPath shown above in order to use in Selenium's FindElement?
Driver.FindElement(By.XPath("?"));
I know how to use the contains tool, but apparently not with more complex XPath statements. I was pretty sure one of the below would work but they did not (develop tool complain of a syntax error):
$x("(//label[#class='dropdown-item' and text()[2][contains(., 'Name')]]")
$x("(//label[#class='dropdown-item' and contains(text()[2], 'Name')]")
I am using the 'contains' in order to avoid white-space conflicts.
Additional for learning purposes (good for XPath debugging):
just in case anyone comes across this who is new to XPath, I wanted to show what the data structure of these label objects looked like. You can explore the data structure of objects within your webpage by using the Firefox Console window within the developer tools (F12). As you can see, the label element contains three sub-items; text which is empty, then the inpput checkbox, then some more text which has the actual text in it (not ideal). In the picture below, you can see the part of the webpage that corresponds to the label data structure.
If you are looking to find the element that contains "Name" given the HTML above, you can use
//label[#class='dropdown-item'][contains(.,'Name')]
So finally got it to work. The Firefox developer environment was correct when it stated there was a syntax problem with the XPath strings.
The following XPath string finally returned the desired result:
$x("//label[#class='dropdown-item' and contains(text()[2], 'Name')]")
I am inspecting one button element from a web page using chrome driver and selenium. And the html code for the particular button is:
<div class="label text-left text-link link-blue text-
uppercase">Financial Statement Analysis <span class="count">(2)</span>
</div>
I have tried different element options like find element by name, xpath, link text etc. But none of them unable to locate the element.
What will be the element to locate the button. ?
try Xpath :
//span[contains(#class,'count') and text() = '(2)']
You can try with this css selector :
div.label.text-left.text-link.link-blue.text-.uppercase
To locate the element with text as Financial Statement Analysis (2) you can use the following solution:
Java Solution:
WebElement elem = driver.findElement(By.xpath("//div[#class='label text-left text-link link-blue text-uppercase'][contains(.,'Financial Statement Analysis')]"));
In my case, there are some legacy web sites, in which not all the inputs have
id attribute properly set. Such as this:
<div class="form-group">
<label>Amount</label>
<input id="unreasonablename" type="text" value=""></input>
</div>
But human testers can still test it by typing amount value in the input right behind "Amount". I'd like to make web driver do the same thing:
webDriver.inputAfter("Amount", 100); //I do not want to use "unreasonablename" to find the input.
But how can I find the input element after the text "Amount"? Thanks.
There is a relative question here: In Selenium Webdriver, how to get a text after an element?. But I'm not familiar with xpath and do not know if my case can be solved in the same way.
To find the <input> element just after the text Amount you can use the findElement() method along with the Locator Strategy as follows :
webDriver.findElement(By.xpath("//label[contains(.,'Amount')]//following::input[1]"));
you can try following_sibling as
webDriver.findElement(By.xpath("//*[text()='Amount']/following-sibling::Input"));
try this :
driver.findElement(By.xpath("//label[text()='Amount']/following-sibling::input")).sendKeys("amount to be sent");
you can write some generic method like below. It can be used for all the required fileds by passing the label name and input value as argument
void enterInputAfterLabel(String labelname,String value){
driver.findElement(By.xpath("//label[text()='"+labelname+"']]/input")).sendKeys(value);
}
What is the meaning of the following command in selenium?
I tried to create a automatic test cases.Then following:
//button[#type='submit'] syntax I saw in selenium tool.
This is an XPath expression. It means: find a button element anywhere in the document having type attribute value that equals to submit.
Example element matching the expression:
<button type="submit">Click Me</button>
This is an xpath for finding the element. when you inspect the element you will find button as Tag. and that Tag should have values type="submit"