Selenium WebDriver提供了先进的技术定位网页上的元素,Selenium丰富的API提供了多种定位元素的策略,例如如姓名、XPath ID、CSS选择器等等,也能自定义定位方法来定位元素
一、通过fidElement方法定位元素
WebDriver and WebElement class.提供findElement()和findElements()方法来定位元素
findElement()方法会通过特殊的索引返回web元素的信息,或者抛出异常(没有找到匹配的元素)
findElements()方法返回一个web元素列表或者空列表(为匹配到元素)
(1)通过ID属性找元素
在页面上,通过ID属性定位元素的方法最为实用,W3C建议为页面上每一个元素提供独一无二的ID,这个独一无二的ID属性能够明确的和可靠的定位元素
在处理DOM,浏览器使用id作为首选方法和识别元素这提供了最快的定位策略。
eg:现在让我们看看如何使用id属性定位元素的登录表单。
定位用户名和密码的区域,我们可以使用id属性以下的方式:
WebElement username = driver.findElement(By.id("username"));
WebElement password = driver.findElement(By.id("password"));
(2)通过name属性找元素
通过ID属性定位元素是首选的策略,但是你可能会发现不能用ID定位元素的情况,如下:
1)页面上并不是所有的元素都有其独特的ID属性
2)对于页面上的关键元素的ID属性不是独有的
3)元素的ID属性自动生成
eg:登录表单用name属性代替了ID属性
可以通过一下方式用name属性定位元素:
WebElement username = driver.findElement(By.name("username"));
WevElement password = driver.findElement(By.name("password"));
不像ID那样,name属性在一个页面可能不是唯一的,你可能会找到不同的相似的name属性,在这种情下,页面上第一个带有这个特殊数值的元素将会被选中。如果这个元素不是你想要的那个元素,将会引起错误
(3)通过元素的类属性寻找
除了使用ID和name属性寻找元素之外,也可以使用类属性定位元素。这个类属性是元素上应用的CSS提供的
eg:登录表单用类属性替代ID属性
可以通过一下的方法利用类属性定位元素
WebElement username = driver.findElement(By.className("username"));
WebElement password = driver.findElement(By.className("password"));
Selenium WebDriver API提供的findElement()方法定位元素是要求要在测试页面的测试下,当通过特殊的标准定位一个元素的时候,系统遍历DOM(文档对象模型)去匹配元素,并且返回第一个匹配成功的元素
2、补充
WebElement类也提供了定位子元素的方法。例如想象一下页面上有很多重复的元素,但是他们是在不同的<div>中的元素,我们可以先定位父<div>中的元素,然后在定位子元素,结合上下文中的<div>有如下的方法
WebElement div = driver.findElement(By.id("div1"));
WebElement topLink = driver.findElement(By.linkText("top"));
NoSuchElementFoundException异常:找不到元素的时候报错
用fidElements方法定位元素
Selenium WebDriver提供findElements()方法,他能够手机元素列表,与搜索标准相匹配,这个方法是非常有用的,如果你想定位一大批相似的元素,例如我们可以获取页面上所有的展示的链接,或者从一个表中获取行等等,我们可以通过findElements()方法来获取所有链接,并打印他们
eg:创建一个测试能够获取页面上所有的link,核实link数量,并打印每个link的目标
findElements()方法会返回所有元素的匹配作为一个WebElement列表,在JAVA中可以使用List类创建WebElement的一个实例
List<WebElement> links = driver.findElements(By.tagName("a"));
List类中的size()告诉我们列表中有多少元素
assertEquals(4, links.size());判断links中的元素是不是4
还向下面这样迭代的使用这个列表获取链接并打印目标
for(WebElement link : links)
System.out.println(link.getAttribute("href"));
定位一个元素使用findElements()方法
二、link定位
Selenium WebDriver提供了多种方法定位links,我们不但可以通过links的文本定位links,还可以通过部分文本。当links在动态文本中,通过部分文本定位links会更方便,在这一节中,我们将会知道怎么样用这些方法定位页面上的links
让我们举一个例子是验证如何用下面的方法在selenium webdriver中定位links
(1)通过他的文本找到links
selenium webdriver的By类提供linksTest()方法定位使用文本方式展示为链接的links,下面的例子中,我们将定位谷歌邮箱的链接
WebElement gmailLink = driver.findElement(By.linkTest("GMail"));
assertEquals("http://mail.google.com/",gmailLink.getAttribute("href"));
(2)通过部分文本寻找links
selenium webdriver的By类也提供了通过部分文本定位links的方法,如果开发者使用动态文本创建此link,这种定位的方法是非常有用的。下面这个例子中,是一个打开收件箱的链接,这个链接也能展示新邮件的数量,这个方法可能会改变动态,下面可以使用partialLinkTest()方法定位统一标准或者已知部分的链接文本
WebElement inboxLink = driver.findElement(By.partialLinkTest("Inbox"));
System.out.println(inboxLink.getTest());
这个linkTest()和partialLinkTest()方法会匹配所有这个特殊文档中的links,并返回结果值,另外,如果开发者提供id,name,class属性,我们也可以通过在这些属性来定位links
注意:当所定位应用存在于多个模块,使用文本定位元素会产生问题,使用参数化文本定位器也是可以工作的,
(3)使用tagName()方法定位元素
回顾:定位单个元素使用findElement()方法
定位多个元素使用findElements()方法
selenium webdriver的By类还提供了tagName()通过他的HTML tagName定位元素,这于JS中getElementsByTagName()方法有些相似,用tagname定位元素是很方便的,例如在标签中定位所有的<tr>
eg:
假设页面上有一个单一按钮,我们可以通过一下方法定位这个按钮
WebElement loginButton = driver.findElement(By.tagName("button"));
loginButton.click();
下面的例子:展示table标签中有多少行
WebElement table = driver.findElement(By.id("summerTable"));
List<WebElement> rows = table.findElement(By.tagName("tr"));
assertEquals(10,rows.size());
tagName()方法通过DOM查询定位元素并返回一个与特殊tagname相匹配的列表,当定位单个元素,或者页面上有多饿元素实例时,这种方法可能是不可信的
(4)使用CSS选择器来定位元素
与Xpaths相比,这种方法更快更可信
这部分,我们将探讨一些基本的CSS选择器,然后以后我们将深入先进的CSS选择器。
利用css选择器,selenium webdriver的By类提供了cssSelector()方法定位元素
绝对路径寻找元素
考虑到元素的结构层次,CSS绝对路径参考元素非常具体的位置
下面的例子就是通过绝对路径定位用户名输入的区域,在提供绝对路径的同时也给予元素之间的空间
WebElement userName = driver.findElement(By.sccSelector("html body div div form input"));
也可以用以前选择器的写法
WebElement userName = driver.findElement(By.cssSelector("html > body >div > div > form > input"));
但是这种方法有一定的局限:他依赖于页面元素的层级结构,如果层级结构变化,则定位失败。
通过相对路径定位元素
通过相对路径我们能够直接定位元素,不依赖于他在DOM中的位置。
例如我们可以用下列方法定位用户名输入的区域,假设这个元素在DOM文件第一个<input>中
WebElement userName = driver.findElemet(By.cssSelect("input"));
下面是css选择器是通过相对路径的方法使用Class和Id属性定位元素,与className()和id(),除了这个,我们还可以未包含在By类里面的其他方法对元素的其他属性进行定位。
用class选择器定位元素
在使用CSS选择器定位元素的同时,我们还能使用类的属性定位元素,可以使用制定的HTML标记来完成这件事,然后在class属性值后面添加一个点
WebElement userName = driver.findElemet(By.cssSelect("input.login"));
这个方法能够定位login按钮的input标签,这个标签的属性值是login。
还有一种简写方式,就是用一个.加属性值,就可以忽略html的标签,但是这将返回所有带有登录类的元素,并且返回的可能不是正确的结果
WebElement loginButton = driver.findElement(By.cssSelect(.login));
用id选择器定位元素
我们可以使用分配给元素的id定位元素,这个可以用指定类型的html标签来完成,然后输入一个散列后面跟着类属性的值。
WebElement userName = driver.findElement(By.cssElement("input#username"));
还有一个简写的形式,缺点同上,
WebElement userName = driver.findElement(By.cssElement("#username"));
同id定位的方法
用属性选择器定位元素
用属性选择器定位元素
除了class和id属性,css选择器也可以用元素的其他属性定位元素,下面的例子是使用name属性定位<input>元素
WebElement userName = driver.findElement(By.cssElement("input[name=username]"));
用name属性定位元素类似与By类下的name()方法
用其他的属性定位元素,比如使用alt属性定位<img>元素
WebElement userName = driver.findElement(By.cssElement("img[slt=Previous]"));
有这样的情况,那就是一种属性可能不能准确的定位元素,还需要结合附加属性来精确定位,
eg:用多属性定位login按钮的<input>元素
WebElement preciousButton = driver.find.Element(By.cssSelect("input[type='sumbit'][value='Login']"));
用属性名称选择器定位元素
这种方法与之前的方法有所不同,不同之处在于之前定位元素仅仅是基于元素被定义的特殊的属性,并不是属性值,比如想寻找所有的<img>元素中有alt属性的元素
List<WebElement> p_w_picpathsWithAlt = driver.findElement(By.cssSelect("img[alt]"));
布朗not()伪类也能定位那些不符合标准的元素
List<WebElement> p_w_picpathsWithAlt = driver.findElement(By.cssSelect("img:not([alt])"));
执行属性值的部分匹配
css提供了一个部分属性值匹配的方法定位元素。当属性值动态分配,页面每一次请求都活改变的时候,这种方法对测试应用来说是非常有效的。例如ASP.NET的id就是动态的,下面的表格解释了CSS部分匹配方法的语法。
25
免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。