检查元素是否存在

9
有没有一种方法可以在Selenium Web Driver中检查元素是否存在?我尝试使用这段代码:
if @driver.find_element(:link, "Save").displayed? == true

但是它会在异常中断,这不是我期望的,因为我仍然希望脚本继续运行。

5个回答

12

我不是 Ruby 专家,可能会犯一些语法错误,但是你可以得到一个大体的理解:

if @driver.find_elements(:link, "Save").size() > 0

这段代码不会抛出 NoSuchElementException 异常。

但是,如果您的 implicitlyWait 大于零且页面上没有元素,则此方法会“挂起”一段时间。第二个问题是,如果页面上存在元素但未显示,则会返回 true

为了解决这个问题,请尝试创建一个方法:

def is_element_present(how, what)
    @driver.manage.timeouts.implicit_wait = 0
    result = @driver.find_elements(how, what).size() > 0
    if result
        result = @driver.find_element(how, what).displayed?
    end
    @driver.manage.timeouts.implicit_wait = 30
    return result
end

为什么需要使用implicit_wait?如果不使用它,难道不会更好吗?这样可以确保在整个页面加载完成后元素已经存在。或者是我对此理解有误?请帮帮我! - Aks..

8

@driver.find_element 会抛出一个叫做 NoSuchElementError 的异常。

因此,您可以编写自己的方法,使用 try catch 块,并在没有异常时返回 true,在有异常时返回 false。


异常名称是NoSuchElementException还是NoSuchElementError?我的Rubymine 2018.2安装程序没有找到NoSuchElementException。 - Nafeez Quraishi
看起来异常名称已更改。根据最新文档:https://www.rubydoc.info/gems/selenium-webdriver/0.0.28/Selenium/WebDriver/Find。它是NoSuchElementError。谢谢@nAQ。 - Abhishek_Mishra

3
如果期望元素无论如何都应该在页面上出现:请使用具有element.displayed?selenium等待对象,而不是使用begin/rescue
wait = Selenium::WebDriver::Wait.new(:timeout => 15)
element = $driver.find_element(id: 'foo')
wait.until { element.displayed? } ## Or `.enabled?` etc.

这在一些页面中很有用,其中某些部分需要比其他部分更长时间才能正确渲染。


0

我正在使用本月早些时候发布的selenium-webdriver版本3.14.0。我试图使用以下代码对@web_driver_instance.find_element(:xpath, "//div[contains(text(), 'text_under_search')]").displayed?进行检查:

element_exists = @wait.until { @web_driver_instance.find_element(:xpath, "//div[contains(text(), 'text_under_search')]").displayed? }

 unless element_exists
   #do something if the element does not exist
 end

上面的尝试失败了,出现了NoSuchElementError异常,所以我尝试使用下面的方法:

begin
   @wait.until { @web_driver_instance.find_element(:xpath, "//div[contains(text(), 'text_under_search')]").displayed? }

rescue NoSuchElementError
  #do something if the element does not exist
end

这对我也没有用,再次失败并出现了NoSuchElementError异常。

由于我检查的文本存在于页面上可能是唯一的,因此尝试了以下方法,这对我起作用了

unless /text_under_search_without_quotes/.match?(@web_driver_instance.page_source)
   #do something if the text does not exist
end

0
寻找元素
解决方案 #1
expect(is_visible?(page.your_element)).to be(false) 
[or]
expect(is_visible?(@driver.find_element(:css => 'locator_value'))).to be(false)
[or]
expect(is_visible?(@driver.first(:css => 'locator_value'))).to be(true)

=> 通用的 Ruby 方法

  def is_visible?(element)
    begin
      element.displayed?
      return true
    rescue => e
      p e.message
      return false
    end
  end

解决方案 #2

expect(is_visible?(".locator_value")).to be(false)  # default css locator
[or]
expect(is_visible?("locator_value", 'xpath')).to be(true)
[or]
expect(is_visible?("locator_value", 'css')).to be(false)
[or]
expect(is_visible?("locator_value", 'id')).to be(false)

=> 通用 Ruby 方法

  def is_visible?(value, locator = 'css')
    begin
      @driver.first(eval(":#{locator}") => value).displayed?
      return true
    rescue => e
      p e.message
      return false
    end
  end

寻找元素(元素列表)
解决方案#1
=> 在页面类中声明变量
proceed_until(@driver.find_elements(:css => 'locator_value').size == 0)
[or]
proceed_until(@driver.all(:css => 'locator_value').size == 0)

=> 通用的 Ruby 方法

  def proceed_until(action)
    init = 0
    until action
      sleep 1
      init += 1
      raise ArgumentError.new("Assertion not matching") if init == 9
    end
  end

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接