I am using selenium to test my web application and I can successfully find tags using By.xpath
. However now and then I need to find child nodes within that node.
Example:
<div id="a">
<div>
<span />
<input />
</div>
</div>
I can do:
WebElement divA = driver.findElement( By.xpath( "//div[@id='a']" ) )
But now I need to find the input, so I could do:
driver.findElement( By.xpath( "//div[@id='a']//input" ) )
However, at that point in code I only have divA
, not its xpath anymore... I would like to do something like this:
WebElement input = driver.findElement( divA, By.xpath( "//input" ) );
But such a function does not exist. Can I do this anyhow?
BTW: Sometimes I need to find a <div>
that has a certain decendent node. How can I ask in xpath for "the <div>
that contains a <span>
with the text 'hello world'
"?
According to JavaDocs, you can do this:
The XPath spec is a suprisingly good read on this.
The toString() method of Selenium's By-Class produces something like "By.xpath: //XpathFoo"
So you could take a substring starting at the colon with something like this:
With this, you could find your element inside your other element with this:
Advantage: You have to search only once on the actual SUT, so it could give you a bonus in performance.
Disadvantage: Ugly... if you want to search for the parent element with css selectory and use xpath for it's childs, you have to check for types before you concatenate... In this case, Slanec's solution (using findElement on a WebElement) is much better.
I also found myself in a similar position a couple of weeks ago. You can also do this by creating a custom ElementLocatorFactory (or simply passing in divA into the DefaultElementLocatorFactory) to see if it's a child of the first div - you would then call the appropriate PageFactory initElements method.
In this case if you did the following:
For Finding All the ChildNodes you can use the below Snippet
Note that this will give all the Child Nodes at same level -> Like if you have structure like this :
It will give me tag names of 3 anchor tags here only . If you want all the child Elements recursively , you can replace the above code with MyCurrentWebElement.findElements(By.xpath(".//*"));
Hope That Helps !!
If you have to wait there is a method
presenceOfNestedElementLocatedBy
that takes the "parent" element and a locator, e.g. aBy.xpath
: