Skip to content

selenium_webdriver_introduction

Selenium WebDriver 是 Selenium 套件的现代核心,提供了一个编程接口用于创建和运行 Web 应用程序的自动化测试。相对于其前身 Selenium RC (Selenium 1),它代表着巨大的进步,并通常被称为 Selenium 2、3 或 4(取决于版本,但核心概念始终是 WebDriver)。

与 Selenium RC 不同,Selenium RC 依赖于通过代理服务器将 JavaScript 注入浏览器,而 WebDriver 通过浏览器内置的自动化支持或特定的浏览器驱动程序更直接地与浏览器交互。

  • 直接浏览器通信: 直接与浏览器的自动化 API 交互,从而实现更快、更稳定的测试。
  • W3C 标准: WebDriver 协议现已成为 W3C 标准,促进了不同浏览器驱动程序之间的一致性。
  • 面向对象 API: 与 Selenium RC 相比,提供了更直观、更清晰的面向对象 API。
  • 跨浏览器支持: 通过特定的驱动程序可执行文件支持所有主流浏览器(Chrome、Firefox、Edge、Safari、IE*)。
  • 多语言支持: 允许使用各种流行的编程语言编写测试(Java、Python、C#、Ruby、JavaScript、Kotlin)。
  • 处理现代 Web 特性: 更好地处理复杂元素、动态内容 (AJAX)、多窗口/多标签页、警告框 (alerts)、框架 (frames) 等。
  • 本地执行无需服务器: 与 RC 不同,WebDriver 在基本的本地测试执行时无需独立的服务器进程。
  • 平台独立: 测试可以在 Windows、macOS 和 Linux 上运行。

*注意:Internet Explorer 支持需要特定的配置,并且通常不如现代浏览器稳定。

交互过程通常如下:

  1. Selenium 测试脚本: 您的代码(例如 Java, Python)使用 WebDriver API 命令。
  2. JSON Wire Protocol / W3C WebDriver Protocol: 您的脚本通过 HTTP 将命令发送到特定的浏览器驱动程序。
  3. 浏览器驱动程序: 特定于浏览器的可执行文件(例如 chromedriver.exe、geckodriver.exe)充当服务器。它接收 HTTP 请求。
  4. 浏览器: 驱动程序将 HTTP 命令转换为浏览器理解并执行的操作。
  5. 响应: 浏览器将操作结果发送回驱动程序,驱动程序再将 HTTP 响应发送回您的测试脚本。

这种架构消除了 JavaScript 注入的需要,并允许与浏览器进行更原生的交互。

WebDriver 对比 Selenium RC(已弃用)

Section titled “WebDriver 对比 Selenium RC(已弃用)”

WebDriver 是明确的继任者和当前标准。以下是强调其优势的快速比较:

特性Selenium WebDriverSelenium RC(已弃用)
架构更简单,通过驱动程序直接控制浏览器。更复杂,需要 RC Server 作为代理。
通信驱动程序与浏览器直接通信 (W3C Protocol)。脚本 -> RC Server -> 浏览器 (通过 Selenium Core JS)。
速度由于直接交互,通常更快。由于服务器延迟和 JS 执行,较慢。
API更简洁,面向对象。面向对象程度较低,更冗长。
无头模式支持大多数现代浏览器/驱动程序原生支持。不支持。
移动端测试Appium 等移动端测试工具的基础。未针对移动端设计。
当前状态积极开发和支持中 (W3C Standard)。已弃用,不再支持或开发。

WebDriver 基本脚本示例(Java 与 TestNG)

Section titled “WebDriver 基本脚本示例(Java 与 TestNG)”

此示例演示了使用 Java 和 TestNG 的 WebDriver 测试的基本结构。它假设您已经设置了 Maven/Gradle 项目,并添加了 Selenium 和 TestNG 依赖项,同时使用 WebDriverManager(或 Selenium Manager)处理驱动程序设置。

package com.example.tests;
import io.github.bonigarcia.wdm.WebDriverManager;
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.chrome.ChromeDriver;
import org.openqa.selenium.support.ui.ExpectedConditions;
import org.openqa.selenium.support.ui.WebDriverWait;
import org.testng.Assert;
import org.testng.annotations.AfterMethod;
import org.testng.annotations.BeforeMethod;
import org.testng.annotations.Test;
import java.time.Duration;
public class WebDriverDemoTest {
private WebDriver driver;
private WebDriverWait wait;
@BeforeMethod
public void setUp() {
// WebDriverManager 自动下载并设置 ChromeDriver
WebDriverManager.chromedriver().setup();
// 或者,Selenium 4.6+ 内置了 Selenium Manager
// System.setProperty("webdriver.chrome.driver", "/path/to/chromedriver"); // 手动设置(不太推荐)
driver = new ChromeDriver();
driver.manage().window().maximize();
// 初始化显式等待(推荐,优于隐式等待)
wait = new WebDriverWait(driver, Duration.ofSeconds(10));
}
@Test
public void calculatePercentTest() {
// 1. 导航到网站
driver.get("https://www.calculator.net/");
// 2. 点击 Math Calculators 链接(使用显式等待)
WebElement mathCalculatorsLink = wait.until(ExpectedConditions.elementToBeClickable(By.linkText("Math Calculators")));
mathCalculatorsLink.click();
// 3. 点击 Percent Calculator 链接
WebElement percentCalculatorLink = wait.until(ExpectedConditions.elementToBeClickable(By.linkText("Percentage Calculator"))); // 已更新的链接文本
percentCalculatorLink.click();
// 4. 在第一个输入字段中输入值 10
WebElement input1 = wait.until(ExpectedConditions.visibilityOfElementLocated(By.id("cpar1")));
input1.clear();
input1.sendKeys("10");
// 5. 在第二个输入字段中输入值 50
WebElement input2 = driver.findElement(By.id("cpar2")); // 假设在 input1 后立即可用
input2.clear();
input2.sendKeys("50");
// 6. 点击计算按钮
// 定位器可能需要根据实际 HTML 结构进行调整
WebElement calculateButton = driver.findElement(By.xpath("//input[@value='Calculate']"));
calculateButton.click();
// 7. 获取结果文本并断言
// 结果定位器可能需要调整
WebElement resultElement = wait.until(ExpectedConditions.visibilityOfElementLocated(By.cssSelector(".h2result")));
String resultText = resultElement.getText();
System.out.println("Raw Result Text: " + resultText);
// 示例断言:检查结果文本是否包含 'Result: 5'
Assert.assertTrue(resultText.contains("5"), "Calculation result is not correct!");
System.out.println("Calculation test passed!");
}
@AfterMethod
public void tearDown() {
if (driver != null) {
driver.quit(); // 关闭所有浏览器窗口并结束 WebDriver 会话
}
}
}

此示例展示了导航、使用不同策略定位元素、交互(click、sendKeys、clear)、使用显式等待(WebDriverWait)以及使用 TestNG 进行基本断言。