Selenium自动化测试 常见API的使用

本篇文章内容是关于 Selenium 自动化测试工具的常见 API 的使用

Selenium版本:4.23.1

编程语言:Java JDK22

编译器:IDEA 2024.2.0.2

浏览器版本:谷歌浏览器128.0.6613.36(正式版本) (64 位)

ChromeDriver:128.0.6613.84
依赖项下载地址:https://mvnrepository.com/

谷歌浏览器驱动下载地址(一定要和浏览器对应的版本匹配):https://googlechromelabs.github.io/chrome-for-testing/#stable

或者版本比较旧的 https://chromedriver.storage.googleapis.com/index.html

接下来所有的 Web 页面操作示例都会以百度的页面演示

findment 定位页面元素操作

cpp 复制代码
    private static void test001() {
        ChromeOptions options = new ChromeOptions();
        //允许所有请求
        options.addArguments("--remote-allow-origins=*");
        //打开百度页面
        WebDriver webDriver = new ChromeDriver();
        webDriver.get("https://www.baidu.com/");
        //定位元素
        webDriver.findElement(By.cssSelector(".s_ipt"));
    }

"允许所有请求"操作在 Selenium4 后可以不用添加

页面元素定位可以在页面按F12,然后使用元素选择作即可,找到对应的代码进行 CSS 样式的复制

sendKeys 在搜索框中输入信息

cpp 复制代码
    private static void test001() {
        ChromeOptions options = new ChromeOptions();
        //允许所有请求
        options.addArguments("--remote-allow-origins=*");
        WebDriver webDriver = new ChromeDriver();
        webDriver.get("https://www.baidu.com/");
        WebElement element = webDriver.findElement(By.cssSelector(".s_ipt"));
        element.sendKeys("测试在搜索框中输入数据");
    }

click 模拟点击操作

cpp 复制代码
    private static void test001() {
        ChromeOptions options = new ChromeOptions();
        //允许所有请求
        options.addArguments("--remote-allow-origins=*");
        WebDriver webDriver = new ChromeDriver();
        webDriver.get("https://www.baidu.com/");
        WebElement element = webDriver.findElement(By.cssSelector(".s_ipt"));
        element.sendKeys("测试在搜索框中输入数据");
        //找到"百度一下按钮" 模拟确认操作
        webDriver.findElement(By.cssSelector("#su")).click();
    }

clear 清空搜索框信息

cpp 复制代码
    private static void test001() {
        ChromeOptions options = new ChromeOptions();
        //允许所有请求
        options.addArguments("--remote-allow-origins=*");
        WebDriver webDriver = new ChromeDriver();
        webDriver.get("https://www.baidu.com/");
        WebElement element = webDriver.findElement(By.cssSelector(".s_ipt"));
        element.sendKeys("测试在搜索框中输入数据");
        //找到"百度一下按钮" 模拟确认操作
        webDriver.findElement(By.cssSelector("#su")).click();
        webDriver.findElement(By.cssSelector("#kw")).clear();
    }

等待操作 (sleep,隐式等待,显式等待)

普通的等待

调用sleep() API即可

智能等待

智能等待可以提前结束等待,比如设置了等待 3 秒,如果 3 秒内满足了条件,就会提前结束等待。最长等待结束时间为 3 秒

智能等待分为 隐式等待 和 显示等待

两者的区别是 隐式等待要等待当前页面的所有元素加载出来后才会提前结束等待。显示等待可以设置为页面上某一个元素加载出来后就可以提前结束等待。

隐式等待

cpp 复制代码
    private static void test002() {
        WebDriver webDriver = new ChromeDriver();
        webDriver.get("https://www.baidu.com/");

        webDriver.manage().timeouts().implicitlyWait(Duration.ofSeconds(3));
    }

显示等待

cpp 复制代码
    private static void test03() {
        WebDriver webDriver = new ChromeDriver();
        webDriver.get("https://www.baidu.com/");
        //元素出来后,等待结束。
        WebDriverWait wait = new WebDriverWait(webDriver, Duration.ofSeconds(3));
        //等待该元素加载出来后就可以提前结束等待
        wait.until(ExpectedConditions.titleIs("百度一下,你就知道"));
    }

自动化操作浏览器(后退,刷新,前进,滑动滚动条,最大化窗口,全屏,设置窗口大小)

cpp 复制代码
    private static void test04() throws InterruptedException {
        ChromeOptions options = new ChromeOptions();
        //允许所有请求
        options.addArguments("--remote-allow-origins=*");
        WebDriver webDriver = new ChromeDriver();
        webDriver.get("https://www.baidu.com/");
        //在搜索框搜索
        webDriver.findElement(By.cssSelector("#kw")).sendKeys("软件");
        webDriver.findElement(By.cssSelector("#su")).click();
        //浏览器后退
        sleep(3000);
        webDriver.navigate().back();
        sleep(3000);
        //刷新
        webDriver.navigate().refresh();
        sleep(3000);
        //前进
        webDriver.navigate().forward();
        sleep(3000);
       //滚动条操作 ((JavascriptExecutor)webDriver).executeScript("document.documentElement.scrollTop=10000");
        //最大化窗口
        webDriver.manage().window().maximize();
        sleep(3000);
        //全屏
        webDriver.manage().window().fullscreen();
        sleep(3000);
        //设置窗口大小
        webDriver.manage().window().setSize(new Dimension(600,1000));
    }

自动化键盘操作(CTRL + A ,CTRL + X ,CTRL + V)

cpp 复制代码
    private static void test05() throws InterruptedException {
        ChromeOptions options = new ChromeOptions();
        //允许所有请求
        options.addArguments("--remote-allow-origins=*");
        WebDriver webDriver = new ChromeDriver();
        webDriver.get("https://www.baidu.com/");
        //在搜索框搜索
        webDriver.findElement(By.cssSelector("#kw")).sendKeys("软件");
        // ctrl A + X + V
        sleep(3000);
        webDriver.findElement(By.cssSelector("#kw")).sendKeys(Keys.CONTROL,"A");
        sleep(3000);
        webDriver.findElement(By.cssSelector("#kw")).sendKeys(Keys.CONTROL,"X");
        sleep(3000);
        webDriver.findElement(By.cssSelector("#kw")).sendKeys(Keys.CONTROL,"V");

    }

自动化鼠标操作(单击左键,单击右键)

cpp 复制代码
    private static void test06() throws InterruptedException {
        WebDriver webDriver = new ChromeDriver();
        webDriver.get("https://www.baidu.com/");
        webDriver.findElement(By.cssSelector("#kw")).sendKeys("跑步");
        webDriver.findElement(By.cssSelector("#su")).click();
        sleep(3000);
        //找到图片按钮
        WebElement webElement = webDriver.findElement(By.cssSelector("#s_tab > div > a.s-tab-item.s-tab-item_1CwH-.s-tab-pic_p4Uej.s-tab-pic"));
        Actions actions = new Actions(webDriver);
        sleep(3000);
        //鼠标右击
        actions.moveToElement(webElement).contextClick().perform();
        sleep(3000);
        //鼠标左击
        actions.moveToElement(webElement).click().perform();
    }

解释一下 perform

在Selenium WebDriver中,perform() 方法用于执行之前通过 Actions 类构建的一系列鼠标或键盘操作。当你构建了一个动作序列之后,必须调用 perform() 方法来实际执行这些操作。这是因为 Selenium 设计 Actions 类时采用了"构建-执行"模式,这样可以让你灵活地构建一系列连续的动作,然后再一次性执行它们。

为什么需要perform()

构建动作序列:Actions 类允许你构建一系列动作,如移动鼠标、点击等,而不立即执行它们。这使得你可以组合多个动作,形成更复杂的操作。

执行动作序列:一旦构建好了动作序列,你必须调用 perform() 方法来实际执行这些动作。如果不调用 perform() ,构建的动作将不会被执行。

模拟浏览器操作(quit 、close)

cpp 复制代码
    private static void test07() throws InterruptedException {
        WebDriver webDriver = new ChromeDriver();
        webDriver.get("https://www.baidu.com/");
        webDriver.findElement(By.cssSelector("#s-top-left > a:nth-child(1)")).click();
        sleep(3000);
        //webDriver.quit(); // 关闭整个浏览器
        //webDriver.close();  //关闭get方法打开的页面
    }

quit 和 close 的区别

quit 关闭的是整个浏览器,而close 只是关闭get打开的页面

quit 会清空缓存,close 不会清空

获取新窗口的操作句柄

当打开一个新的窗口或标签页时,WebDriver会保持在原来的窗口。为了能够与新打开的窗口进行交互,需要使用窗口句柄来切换到那个窗口

cpp 复制代码
    private static void test08() throws InterruptedException {
        WebDriver webDriver = new ChromeDriver();
        webDriver.get("https://www.baidu.com/");
        webDriver.findElement(By.cssSelector("#s-top-left > a:nth-child(1)")).click();
        sleep(3000);
        //通过 getWindowHandles 获取所有的窗口句柄
        //通过 getWindowHandle 获取get打开的页面的窗口句柄
        Set<String> handles = webDriver.getWindowHandles();
        String target_handle = "";
        for(String handle:handles)
        {
            target_handle = handle;
        }
        webDriver.switchTo().window(target_handle);
        //一定要获取到当前页面句柄才能进行下面的操作
        //否则会找不到元素,原因是元素默认是在 get 打开的页面找的
        webDriver.findElement(By.cssSelector("#ww")).sendKeys("新闻联播");
        webDriver.findElement(By.cssSelector("#s_btn_wr")).click();
    }

模拟截图操作

截图后需要设置图片的存放路径,设计到文件的操作,需要在 POM 文件引入新的依赖项

xml 复制代码
        <!-- https://mvnrepository.com/artifact/commons-io/commons-io -->
        <dependency>
            <groupId>commons-io</groupId>
            <artifactId>commons-io</artifactId>
            <version>2.11.0</version>
        </dependency>
cpp 复制代码
    private static void test09() throws InterruptedException, IOException {
        WebDriver webDriver = new ChromeDriver();
        webDriver.get("https://www.baidu.com/");
        webDriver.findElement(By.cssSelector("#kw")).sendKeys("软件测试");
        webDriver.findElement(By.cssSelector("#su")).click();
        sleep(3000);
        //图片保存路径
        File file = ((TakesScreenshot)webDriver).getScreenshotAs(OutputType.FILE);
        FileUtils.copyFile(file,new File("D://test.png"));
    }

findElements 定位一组元素

webdriver 可以很方便的使用findElement 方法来定位某个特定的对象,不过有时候我们却需要定位一组对象,这时候就需要使用findElements 方法。

定位一组对象一般用于以下场景:

批量操作对象,比如将页面上所有的checkbox 都勾上先获取一组对象,再在这组对象中过滤出需要具体定位的一些对象。比如定位出页面上所有的checkbox,然后选择最后一个

以下是 html 代码,页面为一组checkbox 元素,方便演示

html 复制代码
<html>
<head>
    <meta http-equiv="content-type" content="text/html;charset=utf-8" />
    <title>Checkbox</title>
</head>
<body>
<h3>checkbox</h3>
<div class="well">
    <form class="form-horizontal">
        <div class="control-group">
            <label class="control-label" for="c1">checkbox1</label>
            <div class="controls">
                <input type="checkbox" id="c1" />
            </div>
        </div>
        <div class="control-group">
            <label class="control-label" for="c2">checkbox2</label>
            <div class="controls">
                <input type="checkbox" id="c2" />
            </div>
        </div>
        <div class="control-group">
            <label class="control-label" for="c3">checkbox3</label>
            <div class="controls">
                <input type="checkbox" id="c3" />
            </div>
        </div>
        <div class="control-group">
            <label class="control-label" for="r">radio</label>
            <div class="controls">
                <input type="radio" id="r1" />
            </div>
        </div>
        <div class="control-group">
            <label class="control-label" for="r">radio</label>
            <div class="controls">
                <input type="radio" id="r2" />
            </div>
        </div>
    </form>
</div>
</body>
</html>

页面如下:

java 复制代码
    private static void page01() {
        WebDriver webDriver = new ChromeDriver();
        webDriver.get("D:\\code\\java\\seleniumstudy\\src\\page\\page01.html");
        List<WebElement> webElements = webDriver.findElements(By.cssSelector("input"));
        for(int i = 0;i < webElements.size();i++)
        {
            //如果每个元素type值等于checkbox进行点击
            //getAttribute 获取页面上的元素属性值,里面的type是当前的元素属性
            if(webElements.get(i).getAttribute("type").equals("checkbox"))
            {
                webElements.get(i).click();
            }
            else{}
        }
    }

frame 多层级框架定位

多层级框架定位在Selenium WebDriver中非常重要,尤其是在测试使用了嵌套框架的Web页面时。框架(Frames)是一种HTML元素,用于在一个页面中嵌入另一个独立的文档。当页面包含多个嵌套的框架时,就需要使用多层级框架定位来进行测试。

如果不使用多层级框架定位,就会出现无法定位的情况

前端演示页面代码:

html 复制代码
<head>
  <meta http-equiv="content-type" content="text/html;charset=utf-8" />
  <title>frame</title>
<!--  <link-->
<!--          href="http://netdna.bootstrapcdn.com/twitter-bootstrap/2.3.2/css/bootstra-->
<!--p-combined.min.css" rel="stylesheet" />-->
  <script type="text/javascript">$(document).ready(function(){
});
  </script>
</head>
<body>
<div class="row-fluid">
  <div class="span10 well">
    <h3>frame</h3>
    <iframe id="f1" src="inner.html" width="800",
            height="600"></iframe>
  </div>
</div>
</body>
<!--<script-->
<!--        src="http://netdna.bootstrapcdn.com/twitter-bootstrap/2.3.2/js/bootstrap.-->
<!--min.js"></script>-->
</html>

inner.html

cpp 复制代码
<html>
<head>
  <meta http-equiv="content-type" content="text/html;charset=utf-8" />
  <title>inner</title>
</head>
<body>
<div class="row-fluid">
  <div class="span6 well">
    <h3>inner</h3>
    <iframe id="f2" src="http://www.baidu.com"
            width="700"height="500"></iframe>
    <a href="javascript:alert('watir-webdriver better than
selenium webdriver;')">click</a>
  </div>
</div>
</body>
</html>

前端页面图

现在想定位 click 这个元素,如果不使用多层级框架定位的 API 是无法定位到的。

cpp 复制代码
    private static void page02() {
        WebDriver webDriver = new ChromeDriver();
        webDriver.get("D:\\code\\java\\seleniumstudy\\src\\page\\page02.html");
        webDriver.switchTo().frame("f1");
        webDriver.findElement(By.cssSelector("body > div > div > a")).click();
    }

模拟 下拉框操作

前端页面代码

html 复制代码
<html>
<body>
<select id="ShippingMethod"
        onchange="updateShipping(options[selectedIndex]);" name="ShippingMethod">
  <option value="12.51">UPS Next Day Air ==> $12.51</option>
  <option value="11.61">UPS Next Day Air Saver ==> $11.61</option>
  <option value="10.69">UPS 3 Day Select ==> $10.69</option>
  <option value="9.03">UPS 2nd Day Air ==> $9.03</option>
  <option value="8.34">UPS Ground ==> $8.34</option>
  <option value="9.25">USPS Priority Mail Insured ==> $9.25</option>
  <option value="7.45">USPS Priority Mail ==> $7.45</option>
  <option value="3.20" selected="">USPS First Class ==> $3.20</option>
</select>
</body>
</html>

前端页面图

java 复制代码
    private static void page03() {
        WebDriver webDriver = new ChromeDriver();
        webDriver.get("D:\\code\\java\\seleniumstudy\\src\\page\\page03.html");
        WebElement webElement = webDriver.findElement(By.cssSelector("#ShippingMethod"));
        Select select = new Select(webElement);
        //通过下标选中
        //select.selectByIndex(3);
        //通过值选中
        select.selectByValue("12.51");
    }

模拟alert 弹窗操作

前端页面图

点击按钮后,出现弹窗,可以输入信息,并显示到页面

前端代码

cpp 复制代码
<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>弹窗输入信息示例</title>
  <style>
    #message {
        margin-top: 20px;
        font-weight: bold;
        color: blue;
    }
  </style>
</head>
<body>
<h1>点击按钮输入信息</h1>
<button onclick="showPrompt()">点击我</button>
<p id="message"></p>

<script>
  function showPrompt() {
      var input = prompt("请输入一些信息:");
      if (input !== null) {
          document.getElementById('message').innerText = "你输入的是: " + input;
      }
  }
</script>
</body>
</html>

自动化操作

cpp 复制代码
    private static void page04() throws InterruptedException {
        WebDriver webDriver = new ChromeDriver();
        webDriver.get("D:\\code\\java\\seleniumstudy\\src\\page\\page04.html");
        webDriver.findElement(By.cssSelector("body > button")).click();
        sleep(3000);
        // alert 弹窗取消
        webDriver.switchTo().alert().dismiss();
        sleep(3000);
        //点击按钮
        webDriver.findElement(By.cssSelector("body > button")).click();
        //在 alert 弹窗中输入 信息
        webDriver.switchTo().alert().sendKeys("测试");
        //alert 弹窗确认
        sleep(3000);
        webDriver.switchTo().alert().accept();
    }

模拟文件上传操作

前端页面

点击按钮后可选择文件上传

前端代码

c 复制代码
<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>文件上传示例</title>
</head>
<body>
<h1>点击按钮上传文件</h1>
<input type="file" id="fileInput" onchange="displayFileName()">
<p id="fileName"></p>

<script>
  function displayFileName() {
      var fileInput = document.getElementById('fileInput');
      var fileName = document.getElementById('fileName');
      fileName.innerText = "你选择了文件: " + fileInput.files[0].name;
  }
</script>
</body>
</html>
cpp 复制代码
    private static void page05() {
        WebDriver webDriver = new ChromeDriver();
        webDriver.get("D:\\code\\java\\seleniumstudy\\src\\page\\page05.html");
        webDriver.findElement(By.cssSelector("#fileInput")).sendKeys("C:\\qg1.ini");
    }
相关推荐
小薛博客11 分钟前
4、前后端联调文生文、文生图事件
java·ai
愛~杦辷个訾1 小时前
芋道项目,商城模块数据表结构
java·sql·芋道·yudao-cloud·芋道商城
C_Liu_5 小时前
C语言:深入理解指针(5)
java·c语言·算法
佛祖保佑永不宕机5 小时前
麒麟系统ARM64架构部署mysql、jdk和java项目
java·arm
qqxhb6 小时前
零基础学Java——第十一章:实战项目 - 桌面应用开发(JavaFX入门)
java·开发语言·javafx
hy.z_7776 小时前
【数据结构】链表 LinkedList
java·数据结构·链表
Akiiiira7 小时前
【数据结构】队列
java·开发语言·数据结构
程序媛学姐7 小时前
Java级联操作:CascadeType的选择与最佳实践
java·开发语言
不知几秋7 小时前
Maven
java·数据库·maven
jackson凌8 小时前
【Java学习笔记】equals方法
java·笔记·学习