【问题标题】:C# Selenium Select all column elements if two conditions are met (Multiple Conditions)C# Selenium 如果满足两个条件,则选择所有列元素(多个条件)
【发布时间】:2020-11-11 08:21:57
【问题描述】:

我正在尝试从 html 表 td 中检索所有元素,但是当我尝试通过 xpath 查找具有多个条件的元素时,它无法检索 0 个元素,使用单个条件获取所有值没有问题。到目前为止,我的问题可能是 html 元素的顺序。

这是使用 xpath 按单个条件进行的搜索,效果很好: "//input[@class='managebtn'][@value='repost']"

这是我想要达到的目标,但没有达到预期的效果:

"//td[contains(text(),'manage')]/div[@class='regular']/form[@class='manage']/input[@class='managebtn'][@value='repost']"

下面的 html 表格是我正在尝试阅读的表格”

 <tbody aria-live="polite" aria-relevant="all">
  <tr class="posting-row odd ui-state-default" role="row">
     <td class="status expired">
        <small class="gc" style="background:">
        Expired               </small>
     </td>
     <td class="buttons expired"></td>
  </tr>
  <tr class="posting-row even ui-widget-content" role="row">
     <td class="status deleted">
        <small class="gc" style="background:">
        Deleted               </small>
     </td>
     <td class="buttons deleted">
        <div class="regular">
           <form action="https://" method="GET" class="manage display">
              <input type="hidden" name="action" value="display">
              <input type="submit" name="go" value="display" class="managebtn">
           </form>
           <form action="https://" method="GET" class="manage ">
              <input type="hidden" name="action" value="repost">
              <input type="submit" name="go" value="repost" class="managebtn">
           </form>
        </div>
     </td>
   
  </tr>
  <tr class="posting-row odd ui-state-default" role="row">
     <td class="status deleted">
        <small class="gc" style="background:">
        Deleted               </small>
     </td>
     <td class="buttons deleted">
        <div class="regular">
           <form action="https://" method="GET" class="manage display">
              <input type="hidden" name="action" value="display">
              <input type="submit" name="go" value="display" class="managebtn">
           </form>
           <form action="https://" method="GET" class="manage ">
              <input type="hidden" name="action" value="repost">
              <input type="submit" name="go" value="repost" class="managebtn">
           </form>
        </div>
     </td>
  </tr>
  <tr class="posting-row even ui-widget-content" role="row">
     <td class="status deleted">
        <small class="gc" style="background:">
        Deleted               </small>
     </td>
     <td class="buttons deleted">
        <div class="regular">
           <form action="https://" method="GET" class="manage display">
              <input type="hidden" name="action" value="display">
              <input type="submit" name="go" value="display" class="managebtn">
           </form>
           <form action="https://" method="GET" class="manage ">
              <input type="hidden" name="action" value="repost">
              <input type="submit" name="go" value="repost" class="managebtn">
           </form>
        </div>
     </td>
    
  </tr>

我只想在第一列的值Expired时从第二列(value='repost')检索所有值。
看起来因为这个表在列中有多个元素,所以我可能忽略了一些东西。

因为列有这样的:

      <th data-column="0" class="tablesorter-header tablesorter-headerUnSorted ui-widget-header ui-corner-all ui-state-default" tabindex="0" scope="col" role="columnheader" aria-disabled="false" unselectable="on" style="user-select: none;" aria-sort="none" aria-label="status: No sort applied, activate to apply an ascending sort">
   <div class="tablesorter-wrapper" style="position:relative;height:100%;width:100%">
      <div class="tablesorter-header-inner">
         status <i class="tablesorter-icon ui-icon ui-icon-carat-2-n-s"></i>
      </div>
   </div>
</th>
<th class="sorter-false tablesorter-header tablesorter-headerUnSorted ui-widget-header ui-corner-all ui-state-default" data-column="1" scope="col" role="columnheader" aria-disabled="true" unselectable="on" style="user-select: none;" aria-sort="none" aria-label="manage: No sort applied, sorting is disabled">
   <div class="tablesorter-wrapper" style="position:relative;height:100%;width:100%">
      <div class="tablesorter-header-inner">
         manage  <i class="tablesorter-icon ui-icon"></i>
      </div>
   </div>
</th>

我不知道是否有可能有这样一行代码来获取我需要的值:

driver.findElement(By.xpath("//th[@class='sorter-false tablesorter-header tablesorter-headerUnSorted ui-widget-header ui-corner-all ui-state-default' and @text()='manage']"));

这就是表格的样子:

【问题讨论】:

  • 您仅在第一列的值为 Expired 时才询问 column (value='repost') 但您提供的 HTML 是针对 td 1234562 中的元素="status deleted。在构建答案时我不得不做出很多假设。
  • 这就是为什么我说我的 xpath 和 find 方法可能是错误的,因为第一列和第二列中有多个元素,如问题 (html) 中所述。请参阅下面的我的 cmets 以参考我收到的错误和警告建议的解决方案。

标签: c# selenium selenium-webdriver xpath webdriverwait


【解决方案1】:

要在 statusExpired 的项目中识别具有 value 属性为 repost 的元素,您必须诱导 WebDriverWaitVisibilityOfAllElementsLocatedBy(),您可以使用以下基于Locator Strategy

new WebDriverWait(driver, TimeSpan.FromSeconds(20)).Until(ExpectedConditions.VisibilityOfAllElementsLocatedBy(By.XPath("//tr[contains(@class, 'posting-row')][./td[@class='status expired']]//td[@class='buttons expired']//input[@class='managebtn' and @value='repost']")));

使用 SeleniumExtras.WaitHelpers 你可以使用:

new WebDriverWait(driver, TimeSpan.FromSeconds(10)).Until(SeleniumExtras.WaitHelpers.ExpectedConditions.VisibilityOfAllElementsLocatedBy(By.XPath("//tr[contains(@class, 'posting-row')][./td[@class='status expired']]//td[@class='buttons expired']//input[@class='managebtn' and @value='repost']")));

【讨论】:

  • 感谢您的耐心 DebanjanB,我实现了表单,无论我指定的时间(以秒为单位),我都会超时,这意味着 xpath 可能是错误的。根据警告消息,ExpectedConditions 也已过时。我将在下一条消息中向您展示我的实现。
  • 警告:已弃用的类 OpenQA.Selenium.Support.UI.ExpectedConditions 'ExpectedConditions' 已过时。这部分代码已经迁移到 DotNetSeleniumExtras GitHub (github.com/dotnetseleniumtools/dotnetseleniumextras) 实现: var wait = new WebDriverWait(webDriver, TimeSpan.FromSeconds(timeoutInSeconds)).Until(ExpectedConditions.VisibilityOfAllElementsLocatedBy(By.XPath("与您发布的相同“)));返回等待;
  • @John 检查答案更新并让我知道状态。
  • 这是@DebanjanB 的反馈,我只需要转到 NuGet,下载 DotNetSeleniumExtras.WaitHelpers 并实施您的解决方案,例如:...SeleniumExtras.WaitHelpers.ExpectedConditions.VisibilityOfAllElementsLocatedBy... 并且一切正常像一个魅力。再次感谢您的宝贵时间,我花了几个小时在这上面没有任何运气,而您刚刚拯救了我的夜晚!
  • @John 很高兴能为您提供帮助。 Upvote 答案如果这个/任何答案对您/对您有帮助,以造福未来的读者。
猜你喜欢
  • 2017-01-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-01-07
相关资源
最近更新 更多