WebDriver(Java) - 使用driver.findElements()时排除表下的元素

时间:2014-08-05 06:40:35

标签: java xpath webdriver

使用WebDriver,我正在编写一个代码来查找页面给定区域上的特定类型的所有元素(也可以是整个页面本身)。

让我们说我的页面就像这样

<div id='mydiv'>
    <a href='#' id='mylink_1'>Link 01</a>
    <a href='#' id='mylink_2'>Link 02</a>
    <span>Enter your name</span>
    <input type='text' id='txtName' value=''/>
    <div id='mytable'>
        <table id='mytableelement'>
            <tr>
                <td><a href='#' id='table_link_1'>Table Link 1</a></td>
                <td><input type='text' id='table_text_1' value=''/></td>
            </tr>
            <tr>
                <td><a href='#' id='table_link_2'>Table Link 2</a></td>
                <td><input type='text' id='table_text_2' value=''/></td>
            </tr>
            <tr>
                <td><a href='#' id='table_link_3'>Table Link 3</a></td>
                <td><input type='text' id='table_text_3' value=''/></td>
            </tr>
        </table>
    </div>
</div>

现在,我的要求是,获取div下的所有链接&#39; mydiv&#39;。

所以,我已经写了这样的代码

WebElement myDiv = driver.findElement(By.id("mydiv"));
List<WebElement> links = myDiv.findElements(By.tagName("a"));

这将返回&lt; mydiv&#39;下的所有链接,这很好。不过,我想排除标记下的链接,即带有ID&#39; table_link_1&#39;,&#39; table_link_2&#39;,&#39;的链接。 table_link_3&#39;

为了达到这个目的,我做了以下

ArrayList<WebElement> finalLinks =  new ArrayList<WebElement>();
WebElement myDiv = driver.findElement(By.id("mydiv"));
List<WebElement> links = myDiv.findElements(By.tagName("a"));
for(WebElelemnt link:links){
  try{
      WebElement containingtable = link.findElement(By.xpath("ancestor::table[1]"));
      System.out.println("Element occurs inside a table. So, skip it");
  }
  catch(Exception e){
      finalLinks.add(link);
  }
}

这似乎也有效,但唯一的问题是,如果表包含1000行,那么它循环1000个链接,只跳过它们。这显然会影响性能。

有没有更快的方法来跳过表格下的链接?

注意:此处的表格仅为示例。我可能想跳过一个特定的div或一组嵌套的div。

有没有通用的方法呢?

谢谢你, 斯利拉姆

2 个答案:

答案 0 :(得分:1)

我知道的唯一方法是使用xpath表达式。

尝试

WebElement myDiv = driver.findElement(By.id("mydiv"));
List<WebElement> links = myDiv.findElements(By.xpath("./a")); 

这应该只返回你想要的链接(div的直接子节点)。

例如,xpath表达式“./tbody/tr”只匹配“当前”表的表行,嵌套表的行将被忽略。

答案 1 :(得分:0)

我不确定selenium是否支持:not()伪选择器。 你可能想尝试这样的事情:

List<WebElement> anchors = driver.findElements(
    By.css("#myDiv :not(.skip1) a, #myDiv > a")
);

您可以使用:not(.skip1)之类的内容,而不是使用:not(table)。 我对:not()还不熟悉。也许上面的选择器匹配像

这样的东西
<div id="myDiv>
   <div class="skip1">
       <div class="evilDivMaybeBypassingTheNotPart"><a href="...">...</a></div>
   </div>
</div> 

意外。

这里有一个小提琴:http://jsfiddle.net/fabian_barney/ad4vuaf9/
HTML代码的另一个小提琴:http://jsfiddle.net/fabian_barney/n5Lcg9ar/2/