在 Selenium 中的许多 findElement(s)/By 函数中,您啥时候会使用其中一个?

Posted

技术标签:

【中文标题】在 Selenium 中的许多 findElement(s)/By 函数中,您啥时候会使用其中一个?【英文标题】:Of the many findElement(s)/By functions in Selenium, when would you use one over the other?在 Selenium 中的许多 findElement(s)/By 函数中,您什么时候会使用其中一个? 【发布时间】:2018-06-11 18:24:05 【问题描述】:

Selenium 包括 findElement 函数,就像这样......

.find_element_by_

id
link_text
partial_link_text
name
class_name
tag_name
css_selector
xpath

很明显,由于 html 页面的创建方式,某些标签受到设计的限制,例如 id、link_text、name、tag_name,因为并非所有标签都可能包含 id、link_text 等......但是,css_selector 和xpath 几乎可以做这些可以做的所有事情,然后是一些,但似乎受限于它们可以与之交互的内容。例如,某些按钮可能无法通过 xpath 被点击,但可以被 css_selector 点击。

所以我想知道,什么时候想要使用一个而不是另一个(特别是 xpath 或 css_selector)?

其他函数(id、link_text 等)是否几乎没有用,因为(至少)我发现 xpath/css_selector 也可以做到这一点?

比 xpath/css_selector 使用 link_text 有什么好处吗?

【问题讨论】:

我使用给我 unique 元素定位器的函数!您可能想看看这个页面 - elementalselenium.com/tips/32-xpath-vs-css,为您提供性能统计数据。 这个讨论可能是相关的:What makes a good selenium locator?。 如果我需要通过文本查找某些内容,或者如果找到我想要的元素的唯一方法是找到另一个元素,我几乎只使用 xpaths,遍历 dom 树到某个共享元素,然后回到我想要的元素。根据我的经验,css 选择器最终会变得更干净、更易于阅读。您会发现有人争辩说 xpath 也较慢,但实际上您可能不会注意到差异。 @PhaniAnne 唯一定位器是什么意思? CSS_selector 和 Xpath 都有唯一的路径/值/你想怎么称呼它。 @Matt 是的,它们大多是独一无二的。如果我看到 id,我使用 findelementbyid;如果缺少,我使用 xpath/CSS 选择器。但是我确实对 findelementbyclass 有信任问题,因为类名可以在多个地方使用。一开始我不担心性能,会选择简单的路径。如果性能不好,那么我才会考虑优化。希望对您有所帮助! 【参考方案1】:

这个问题已经在许多论坛中以不同的形式提出和回答。如果我们优先考虑定位器,则将它们全部考虑在内,列表如下:

id:选择具有指定id 属性的元素。 name:选择具有指定name 属性的第一个元素。 link_text:选择包含与指定LinkText匹配的text的链接(锚标记)元素。 partial_link_text:选择包含与指定PartialLinkText匹配的文本的链接(锚标记)元素。 tag_name:使用Tag Name 定位元素。 class_name:使用ClassName 定位元素。 css_selector:使用CssSelectors选择元素。 xpath:使用XPath 表达式定位元素。

所以现在的问题是有什么新消息

答案是Selenium 最近发展了很多WebDriver 现在是 W3C Recommendation CandidateSelenium 内的事物变化很快。不仅仅是选择定位器。我们需要使用定位器:

唯一标识一个元素必须优化定位器的性能。

牢记这两个因素,最好的策略是模拟 DOMW3C Recommendation Candidate 确实提到了定位器列表,如下所示:

所以判决清楚明了。

【讨论】:

显然您没有正确阅读我的问题。我知道这些功能的作用,但我想知道为什么有人会选择其中一个。在某些情况下,xpaths 会比 css_selector 更有用,反之亦然。 你肯定没有完整阅读我的Answer 的全文,否则你不会错过我提到The performance of the locator must be optimized. 的那一行 我确实读过它,但该行没有指定任何内容。您所做的只是发布每个标签的功能以及一些几乎无法进入我正在寻找的信息。这个怎么样。当您访问网页并检查 HTML 文档时,您希望何时使用 xpath 而不是 css_selector,反之亦然?就点击我非常想点击的元素而言,一个比另一个更稳定吗? 稳定性取决于您编写自动化代码的效率,我在我的回答中详细说明了这一点。为了达到最佳性能,我确实为您提供了从css 开始到W3C recommendation 中以xpath 结束的顺序选项。但是 cssxpath 容易受到 DOM 更改的影响。让我知道这是否能回答您的问题。【参考方案2】:

根据我的经验,CSS 是更可取的选择器,因为它可以简洁、有据可查,并且网络开发人员可能有更多的经验和接触它。

idnametag_nameclass_name 都可以用简单的 CSS 轻松复制,所以我会避免明确使用这些。

例如

id ; #my_id

姓名[name="my_name"]

标签名称我的标签

类名.my_class

XPath 的使用经常受到诟病;标记为缓慢且不稳定。但是我不同意这个观点。

当我采访人们时,当他们说他们避免使用 Xpath 因为它又慢又脆弱时,我会感到畏缩。速度不再是一个问题,xpath 只是和编写它的人一样脆弱。但是,我更喜欢 CSS 选择器的语法,因此我会在大多数用例中选择 XPath。

在 3 种情况下 XPath 是更好的选择;

可以用一个 XPath 查询替换多个 CSS 选择器(例如,可以在一个 xpath 中执行查找元素然后遍历子元素)

XPath 可以基于文本进行选择,而 CSS 选择器不能

XPath 允许您沿着 DOM 树向上走,如果您只能通过子控件识别控件,这将非常有用

如果可能,我将始终避免按文本进行选择,但如果必须,我更愿意使用 XPath 而不是内置的 Link TextPartial Link Text 方法因为 Xpath 查询可以让我更有表现力,让我选择的不仅仅是锚标签。

最后,使用 XPath 时遇到的一个问题是,“类”被视为文字字符串,而不是 CSS 选择器支持的类名数组;

HTML: <div class="ab cd">

CSS matches: div.ab
CSS matches: div.cd
CSS matches: div.cd.ab
CSS matches: div.ab.cd

XPath matches: //div[@class="ab cd"]
XPath matches: //div[contains(@class, "ab")]
XPath matches: //div[contains(@class, "cd")]
XPath matches: //div[contains(@class, "ab") and contains(@class, "cd")]

XPath DOES NOT match: //div[@class="cd"]
XPath DOES NOT match: //div[@class="ab"]
XPath DOES NOT match: //div[@class="cd ab"]

【讨论】:

嗯,这是一本非常有趣的书。我很感激这些信息!当您说 xpath 仅与编写它的人一样脆弱时,我怎么知道我是否使用了正确的路径(假设这是弱点)? xpath 没有“正确路径”,但 CSS 选择器也是如此。以此页面和您的签名图像为例。以下 XPATH 将起作用; //body/div[3]/div[1]/div[1]/div[1]/div[2]/div[1]/table/tbody/tr[1]/td[2]/div[ 1]/table[1]/tbody/tr/td[2]/div[1]/div[2]/a/div/img 它每次都会找到你的图像但是如果HTML布局有一个小的变化,它很容易破裂。我称之为脆弱的 XPATH。很重要的一点是,我可以很容易地用 CSS 写出这样的代码! 更好的 xpath 可能是 '//div[contains(@class, "question")]//a[@href="/users/6402048/matt-i"]//img' .这将更有弹性地应对结构性变化。注意。在这种情况下,我可能会使用 CSS,因为它可能更清晰; '.question a[href="/users/6402048/matt-i"] >img' 但是,要创建 Xpath(或者实际上是 CSS 选择器),您需要了解 AUT 以及您要测试的内容 @MattI 如果您认为它解决了您的问题,请随时将其标记为答案

以上是关于在 Selenium 中的许多 findElement(s)/By 函数中,您啥时候会使用其中一个?的主要内容,如果未能解决你的问题,请参考以下文章

如何从 Selenium (Java) 中获取文本?

Selenium:如何使用Javascript将密钥发送到JQuery输入

在 Selenium 中的许多 findElement(s)/By 函数中,您啥时候会使用其中一个?

Python中的Selenium找不到任何元素

如何强制 Selenium 忽略其他应用程序中的 ctrl/shift 操作?

与Python Scrapy中的Selenium WebDriver并发