当前位置: 首页 > 编程日记 > 正文

selenium--driver.switchTo()

在自动化测试中,会遇到多窗口、多iframe、多alert的情况。此时,会使用driver.switchTo()来解决。

下面时关于driver.switchTo()的详细介绍:

1.多windows操作。

在页面A上操作时,点击某个元素之后,可能会打开新的窗口。如果需要操作新窗口上的元素,进必须跳转到新的窗口上。

    @Testpublic void fTest() throws InterruptedException {//launchBrowser是自己封装的方法 ,主要是为了启动浏览器驱动,打开指定url,页面加载的等待超时时间设置为3S
     //这里测试使用的是qq邮箱的登录页面
launchBrowser("https://mail.qq.com/cgi-bin/loginpage", 3);//定位并点击“手机版”元素,打开手机版页面,此时会打开新的窗口driver.findElement(By.partialLinkText("手机版")).click();Thread.sleep(3000);//获取当前窗口句柄(此时是获得https://mail.qq.com/cgi-bin/loginpage页面的句柄)String currentHandle = driver.getWindowHandle();//获得所有的窗口句柄,如果不是currentHandle,则进入Set<String> windowHandles = driver.getWindowHandles();for (String windowHandle : windowHandles) {if (!currentHandle.equals(windowHandle) ) {//进入到手机版页面的窗口 driver.switchTo().window(windowHandle);}}//此时才能操作手机版页面的元素driver.findElement(By.cssSelector("a[href='http://app.mail.qq.com/cgi-bin/appdownload?check=false&stype=1&subtype=8&fr=&url=ios&downloadclick=']")).click();;

//如果想要操作qq邮箱登录页面的元素,此时需要退回到之前的窗口
      driver.switchTo().window(currentHandle);

         }

上面是通过switchTo()方法,进入新的页面,并操作对应元素。

还有另为一种方式:

<a href="http://app.mail.qq.com/" target="_blank">手机版</a>

我们点击链接之后,打开新的窗口,就是因为这个链接中有属性 target="_blank"

所以,我们可以通过JQuery脚本来去除该元素的target的属性。去除之后再点击的时候,就不会打开新的浏览器窗口了。

这个qq邮箱的页面http://app.mail.qq.com/,首次执行JQuery会失败,第二次会成功。猜测可能是因为第一次执行之后,会触发引入jQuery的操作。为了使代码具有通用性,直接引入jQuery。

但是很多安全性高一些的网站,会限制引入的域名地址。会造成引入JQuery失败。为了解决该问题,教大家一个万能的方法:下载某页面的JQuery源代码,放到本地文件中。封装读取并执行JQuery的帮助类。

帮助类代码:

package com.claire.jing.utils;import java.io.BufferedReader;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStreamReader;import org.openqa.selenium.JavascriptExecutor;public class ImportJQueryUtil {public static void importJQueryUtil(JavascriptExecutor jse) {StringBuffer buffer = new StringBuffer();FileInputStream inputStream = null;try {inputStream = new FileInputStream("F:\\开发资料\\jQuery源码\\jquery-1.10.2.min.js");} catch (FileNotFoundException e) {// TODO Auto-generated catch block
            e.printStackTrace();}InputStreamReader reader = new InputStreamReader(inputStream);BufferedReader bufferedReader = new BufferedReader(reader);String temp=null;try {while ((temp = bufferedReader.readLine()) !=null) {buffer.append(temp);}} catch (IOException e) {// TODO Auto-generated catch block
            e.printStackTrace();}jse.executeScript(buffer.toString());}}

使用JQuery来删除元素指定属性

@Testpublic void fTest() throws InterruptedException {//方式2:使用JQuery来删除target="_blank"//launchBrowser是自己封装的方法 ,主要是为了启动浏览器驱动,打开指定url,页面加载的等待超时时间设置为3SlaunchBrowser("https://mail.qq.com/cgi-bin/loginpage", 20);//该js脚本判断是否引入了JQueryString js = "return (typeof($)==\"undefined\")";boolean flag = (boolean)((JavascriptExecutor)driver).executeScript(js);//如果没引入,则调用帮助类,执行JQuery源码。//这里之所以不使用直接增加Script节点引入JQuery,是因为很多安全性高一些的网站,会限制引入的域名地址。会造成引入JQuery失败if (flag) {ImportJQueryUtil.importJQueryUtil((JavascriptExecutor)driver);            }//这里可以判断下,是否引入成功了//System.out.println((boolean)((JavascriptExecutor)driver).executeScript(js));//<a href="http://app.mail.qq.com/" target="_blank">手机版</a>//该a链接带有属性target="_blank"--拥有该属性的链接,点击后才会打开新的页面。只要通过js来移除该属性,点击之后,就不会打开新的浏览器窗口了String jquery = "var com=$('a[href=\"http://app.mail.qq.com/\"]');"+ "com.removeAttr(\"target\");"+ "com[0].click();";((JavascriptExecutor)driver).executeScript(jquery);//观察一下执行结果Thread.sleep(4000);quit();}

2.Iframe

有些页面元素时包在IFrame中的,此时想要操作Iframe上的元素,必须先进入Iframe里面去。

下面举例多层iframe嵌套的情况:

    @Testpublic void fTest() throws InterruptedException {launchBrowser("http://XXX/index.html", 10);//为了不需要每次都登录,可以设置添加cookie()driver.manage().deleteCookieNamed("JSESSIONID");driver.manage().addCookie(new Cookie("qqq", "BD04BA5FA2019D6C9DB28E25A5B14D85"));try {//为了cookie使用的久一些,可以设置cookie的有效期。//即使这里设置了cookie有效期,cookie也是有可能会无效的(一般情况下,会将sessionId存到cookie中)://第一:服务端的session是有有效期的,如果session过期了,那么这个cookie也就无效了。//第二,当服务端的内存报警时,就可能会清除session。这种情况下,你的cookie也会失效//第三,当服务端重启之后,缓存和session都会清空的,你的cookie自然就失效了driver.manage().addCookie(new Cookie("JSESSIONID", "FB9F06DDF0D15C491EFAD6D444893F80","/lmcanon_web_auto",(new SimpleDateFormat("yyyy-MM-dd hh:m:ss")).parse("2018-12-12 12:12:12") ));} catch (ParseException e) {logger.error("日期转换出错");e.printStackTrace();}driver.get("http://XXX/index.html");logger.info("成功打开首页");driver.findElement(By.cssSelector("i[class=\"Hui-iconfont menu_dropdown-arrow\"]")).click();logger.info("成功定位习题管理,并点击");//定位习题管理子标签,该标签是需要点击父标签习题管理之后,才会可见的。//下面使用了ExpectedConditions中提供的visibilityOfElementLocated()来判断该字标签是否可见,可见之后才对其进行点击操作WebDriverWait wait = new WebDriverWait(driver, 3);            wait.until(ExpectedConditions.visibilityOfElementLocated(By.cssSelector("a[data-href=\"stem-list.html\"]"))).click();logger.info("成功定位子元素习题管理并点击");//想要点击“添加习题”按钮,发现该按钮在iframe中,必须先进入iframe才能定位并操作该元素WebElement IframeElement = waitElement(By.cssSelector("iframe[src='stem-list.html']"));driver.switchTo().frame(IframeElement);logger.info("成功进入第一层Iframe,并进入");driver.findElement(By.cssSelector("a[class=\"btn btn-primary radius\"]")).click();logger.info("成功定位第一层frame内的添加习题按钮并点击");//嵌套iframe情况,想要点击添加习题弹窗上的元素,就必须进入第二层iframe//进入第二层Iframe//首先定位第二层iframe <iframe scrolling="auto" allowtransparency="true" id="layui-layer-iframe2" name="layui-layer-iframe2" οnlοad="this.className='';" class="" frameborder="0" src="./stemAndItem-add.html" style="height: 467px;"></iframe>WebElement iframe2 = driver.findElement(By.id("layui-layer-iframe2"));driver.switchTo().frame(iframe2);logger.info("成功进入第二层iframe");//定位第二层iframe的元素//<select class="select valid" name="subjectType" aria-required="true" aria-invalid="false"><option value="0">--请选择--</option><option value="1">软件测试基础</option><option value="2">mysql数据库</option><option value="3">linux</option><option value="4">java</option></select>WebElement subjectType = driver.findElement(By.cssSelector("select[name=\"subjectType\"]"));Select select = new Select(subjectType);select.selectByIndex(2);logger.info("成功定位第二层iframe内的题目领域元素,并选择为mysql数据库");//退出当前iframe-----注意:下面方法是退回到的top window 层
        driver.switchTo().defaultContent();logger.info("成功退回到first frame.");//操作topWindow上的元素,证明成功退回driver.findElement(By.cssSelector("i[class=\"Hui-iconfont menu_dropdown-arrow\"]")).click();logger.info("成功定位习题管理,并点击");}

3.alert操作

其实现在前台系统中的alert页面越来越少了。因为它的体验不是很好。但是在一些后台系统中,还是会遇到alert操作。Alert弹窗分三种,Alert,prompt(需要输入内容的弹窗),confirm


1. alert() 弹出个提示框 (确定) 
警告消息框 alert 方法有一个参数,即希望对用户显示的文本字符串。该字符串不是 HTML 格式。该消息框提供了一个“确定”按钮让用户关闭该消息框,并且该消息框是模式对话框,也就是说,用户必须先关闭该消息框然后才能继续进行操作。

2. confirm() 弹出个确认框 (确定,取消) 
确认消息框 使用确认消息框可向用户问一个“是-或-否”问题,并且用户可以选择单击“确定”按钮或者单击“取消”按钮。confirm 方法的返回值为 true 或 false。该消息框也是模式对话框:用户必须在响应该对话框(单击一个按钮)将其关闭后,才能进行下一步操作。

3. prompt() 弹出个输入框(确定,取消)。

如果用户单击提示框的取消按钮,则返回 null。如果用户单击确认按钮,则返回输入字段当前显示的文本。

在用户点击确定按钮或取消按钮把对话框关闭之前,它将阻止用户对浏览器的所有输入。在调用 prompt() 时,将暂停对 JavaScript 代码的执行,在用户作出响应之前,不会执行下一条语。

    @Testpublic void fTest() throws InterruptedException {launchBrowser("D:\\javascript\\Untitled-3.html", 10);WebDriverWait wait = new WebDriverWait(driver, 3);Alert alert2 = wait.until(ExpectedConditions.alertIsPresent());System.out.println(alert2.getText());//取消alert2.dismiss();//确定alert2.accept();//输入内容alert2.sendKeys("hello");Thread.sleep(4000);        }

转载于:https://www.cnblogs.com/clairejing/p/9499223.html

相关文章:

代理模式-积木模式

代理模式&#xff0d;积木模式 代理模式在实际开发中的确非常常见和常用&#xff0c;表面上代理模式是产生出一个代理类&#xff0c;作为访问实际实现类的代理&#xff0c;控制了外界对实际代理类的访问&#xff0c;在此基础上增加一些增强性的功能。实际上&#xff0c;还将实际…

java调用系统时间函数_JAVA自学笔记:不使用系统函数来计算日期处于当年的第多少天...

前段时间练习了一个求闰年的功能&#xff0c;现在就可以用上啦&#xff0c;这次写一个不借助类库的时间函数&#xff0c;利用基础代码写一个计算求日期处于当年的第多少天的函数。虽然也有简单的方法&#xff0c;例如直接定义每月的天数累加&#xff0c;然后加上当月的天数就可…

c语言输入学生成绩q退出,哭诉、拜求C语言学生成绩管理系统

该楼层疑似违规已被系统折叠 隐藏此楼查看此楼/* Note:Your choice is C IDE */#include "stdio.h"#include "stdlib.h"#include "conio.h"#include "string.h"struct student{int num;char name[20];float score1;float score2;float…

php 所有魔术方法,PHP常用的魔术方法及规则

转&#xff1a;https://www.cnblogs.com/wanglijun/p/10926303.html1. __construct 具有构造函数的类会在每次创建新对象时先调用此方法;初始化工作执行。2. __desstruct 对象的所有引用都被删除或者当对象被显式销毁时执行。3.__call()在对象中调用一个不可访问方法时&#xf…

mysql启动后在哪里编程_启动mysql后怎么连接数据库

推荐答案一.mysql安装百度mysql下载一个即可。只是注意一下几个重要的数据&#xff1a;第一个就是Port Number :3306。端口号默认3306&#xff0c;一般不需要改&#xff0c;如果改了&#xff0c;请记住这个端口号。第二个就是password&#xff1a;本地数据库密码&#xff0c;默…

Python 出现 can't use a string pattern on a bytes-like object

# codingutf-8import urllib.requestimport reurl http://www.163.comfile d:/test.htmldata urllib.request.urlopen(url).read() r1 re.compile(<.*?>)c_t r1.findall(data)print(c_t)发现读取下来后,运行到第9 行,出现: cant use a string pattern on a bytes-l…

2018牛客网暑期ACM多校训练营(第十场)J(二分)

题目描述&#xff1a; 给你n个字符串&#xff0c;要让它们一个一个的合并成一个串。在合并的过程中&#xff0c;要保证被合并的串S是合并后的串r的前缀&#xff0c;模式串t是串r的子序。问你将这n个字符串合并后所得到的字典序最小的串是什么。 题目分析&#xff1a; 首先&…

实用c语言函数源码,C语言编写简单朗读小工具(有源码)

原标题&#xff1a;C语言编写简单朗读小工具(有源码)最近不少人在后台留言说学C都是面对枯燥的控制台程序&#xff0c;能不能体现一下C语言的实际用途&#xff0c;今天我们就理论结合实践一把&#xff1a;C语言结合VBS脚本编写一个简单的朗读小工具&#xff0c;做一个能够发音的…

php监听订单状态,ecshop数据库订单状态判断

order_info 表刚下完订单order_status 0shipping_status 0pay_status 0取消order_status 2shipping_status 0pay_status 0确认order_status 1shipping_status 0pay_status 0已付款order_status 1shipping_status 0pay_status 2配货中order_status 1shipping_status 3pay_status…

flask异步操作_Python Flask后端异步处理(三)

前一篇博文我们已经将基础知识和环境配置进行了介绍&#xff1a;首先编写一个celerytask.py文件进行Celery的配置&#xff0c;同时耗时任务也写在该文件中from celery import Celeryfrom init import appfrom SZheConsole import SZheScanapp.config[CELERY_BROKER_URL] redis…

Codeforces Round #308 (Div. 2) C. Vanya and Scales dfs

题目链接: http://codeforces.com/contest/552/problem/C 题意: 给你100个砝码&#xff0c;第i个砝码质量是w^i&#xff0c;然后问你能不能在有m的情况下&#xff0c;左边和右边都放砝码&#xff0c;使得这个天平平衡 题解: dfs直接暴力 对于这个砝码来说&#xff0c;只有3种选…

java中JVM的原理【转】

一、java虚拟机的生命周期&#xff1a; Java虚拟机的生命周期 一个运行中的Java虚拟机有着一个清晰的任务&#xff1a;执行Java程序。程序开始执行时他才运行&#xff0c;程序结束时他就停止。你在同一台机器上运行三个程序&#xff0c;就会有三个运行中的Java虚拟机。 Java虚拟…

switch的case使用数组C语言,使用常量数组的元素作为switch语句中的case

我正在尝试将一组按键映射到一组命令.因为我处理来自多个地方的命令,所以我想在键和命令之间设置一个抽象层,这样如果我更改底层键映射,我就不必更改很多代码.我目前的尝试看起来像这样:// input.henum LOGICAL_KEYS {DO_SOMETHING_KEY,DO_SOMETHING_ELSE_KEY,...countof_LOGIC…

PHP上传文件函数move_upload,如何使用php中move_uploaded_file函数

我们平时上传的文件保存在临时文件夹中&#xff0c;例如/ tmp&#xff0c;但临时文件夹的内容在一段时间后会被删除&#xff0c;因此为了将来要使用上传文件&#xff0c;需要将内容保存在不太可能被任意删除的专用目录中&#xff0c;这时就需要使用move_uploaded_file函数&…

java的标记接口_Java中的标记接口?

我被教授&#xff0c;Java中的Marker接口是一个空接口&#xff0c;用于向编译器或JVM发送信号&#xff0c;实现此接口的类的对象必须以特殊方式处理&#xff0c;如序列化&#xff0c;克隆等。但最近我了解到&#xff0c;它实际上与编译器或JVM无关。例如&#xff0c;在Serializ…

Java Exception

先贴上一段Exception源码注释 1 /**2 * The class {code Exception} and its subclasses are a form of3 * {code Throwable} that indicates conditions that a reasonable4 * application might want to catch.5 *6 * <p>The class {code Exception} and any subc…

c语言实验至少包括四个函数中,C语言实验报告《函数》

学号&#xff1a;__________ 姓名&#xff1a;__________ 班级&#xff1a;__________ 日期&#xff1a;__________指导教师&#xff1a;__________ 成绩&#xff1a;__________实验四 函数一、 实验目的1、掌握函数定义、调用和声明的方法2、掌握实参和形参之间的…

Android与iOS对比

最近有并行开发Android与iOS端App,想在这总结一些两种开发的相似与区别。转载于:https://www.cnblogs.com/stuwan/p/6475725.html

oracle停止一切进程,oracle启动/停止的几种方法以及 启动和停止过程中出错的解决办法...

一、启动几种方法&#xff1a;1、sqlplus /nologconnect /as sysdbastartup2、sqlplus /nologconnect /as sysdbastartup nomountalter database mountalter database open在以上两种方法中&#xff0c;1方法中的startup相当于2方法中的startup nomountalter database mountalt…

前端js判断上传是否为EXCEL表格问题

直接贴代码吧~JS部分 输入框部分&#xff1a; 转载于:https://www.cnblogs.com/aijiajia1314/p/9517541.html

java 外部类似_[求指点] 如何用java 实现类似linux中管道调用外部程序的功能

想写个小程序实现类似linux中管道的功能&#xff0c;创建一个外部子进程&#xff0c;然后主进程不断地写输入给子进程&#xff0c;而后把子进程的返回值取出。如下的小代码就是从stdin读入一个字符串&#xff0c;调用子进程(cat)返回这个串&#xff0c;然后返回。但下面的写法只…

c语言递归求五阶行列式源代码,久游堂怎么样 -官网

iOS版# -*- coding: utf-8 -*- """ author: Dell Created on Tue Dec 24 12:33:56 2019 """ import time from selenium import webdriver from selenium.webdriver.support.ui import WebDriverWait#等待一个元素加载完成 from selenium.webdri…

POJ - 3660 Cow Contest(flod)

题意&#xff1a;有N头牛&#xff0c;M个关系&#xff0c;每个关系A B表示编号为A的牛比编号为B的牛强&#xff0c;问若想将N头牛按能力排名&#xff0c;有多少头牛的名次是确定的。 分析&#xff1a; 1、a[u][v]1表示牛u比牛v强&#xff0c;flod扫一遍&#xff0c;可以将所有牛…

oracle scn与数据恢复,SCN与数据库恢复的关系

一。SCN与CHECKPOINTCKPT进程在checkpoint发生时&#xff0c;将当时的SCN号写入数据文件头和控制文件&#xff0c;同时通知DBWR进程将数据块写到数据文件。CKPT进程也会在控制文件中记录RBA(redo block address),以标志Recovery需要从日志中哪个地方开始。与checkpoint相关的SC…

Java 理解泛型的基本含义

Java 泛型 Java 泛型&#xff08;generics&#xff09;是 JDK 5 中引入的一个新特性, 泛型提供了编译时类型安全检测机制&#xff0c;该机制允许程序员在编译时检测到非法的类型。 泛型的本质是参数化类型&#xff0c;也就是说所操作的数据类型被指定为一个参数。 泛型方法 你可…

java严格区分大小写吗_Java是否区分大小写?

我在某处读到Java是区分大小写的。 我一直无法证实这一点。Java源代码是区分大小写的&#xff0c;如果你的意思是。 即Double与double不是同一个types&#xff0c;并且可以有两个不同的variablesmyData和mydata 。是吗&#xff1f; 如果是这样&#xff0c;为什么&#xff1f;区…

4、Hibernate查询语句

转载于:https://www.cnblogs.com/wyl9527/p/6484099.html

循环控制体重C语言,中年以后很容易发福变胖?4个建议帮你控制体重,保持轻盈体态...

随着年龄的增长&#xff0c;尤其是40岁以后&#xff0c;我们会发现&#xff0c;对待自己的体重与身材之时会显得很无力&#xff0c;在年轻的时候&#xff0c;减掉几斤的体重并不难&#xff0c;而到了中年以后则会变得很困难&#xff0c;即使减重成功&#xff0c;也非常容易反弹…

oracle异地迁移,数据泵实现Oracle数据迁移到异地库

今天发现impdp命令有个特殊的用途&#xff0c;可以将数据库的一个用户迁移到另一台机器上的数据库的用户中。如果目标用户不存在&#xff0c;还可以对应的创建该用户。下面就来看一下命令格式&#xff1a;Impdpusername/passwddbsnameremap_schemauserA:userB remap_tablespace…

轨迹系列1——一种基于路网图层的GPS轨迹优化方案

文章版权由作者李晓晖和博客园共有&#xff0c;若转载请于明显处标明出处&#xff1a;http://www.cnblogs.com/naaoveGIS/ 1.背景 GPS数据正常情况下有20M左右的偏移&#xff0c;在遇到高楼和桥梁等情况下偏移会更大。本方案讨论基于路网图层如何来进行轨迹优化。 2.数据预处理…