Python爬虫浏览器自动化库深度解析:Selenium vs Playwright
在2026年的今天,Web应用愈发复杂,动态渲染、反爬机制层出不穷。对于爬虫工程师而言,浏览器自动化库早已不是"可选项",而是"必备武器"。本文将带你深入剖析两大主流库------Selenium (老牌霸主)与Playwright(微软新锐),从安装、核心用法到性能对比,助你选对工具,高效爬取。
一、为什么需要浏览器自动化?
传统HTTP请求库(如requests)无法执行JavaScript,面对SPA(单页应用)、动态加载、验证码、反爬虫(如指纹检测、WebDriver检测)时力不从心。浏览器自动化库通过操控真实浏览器内核,模拟人类操作,能突破绝大多数限制。
二、Selenium:经典永不过时
1. 简介
Selenium诞生于2004年,最初用于Web应用测试,后成为爬虫领域的事实标准。它支持Chrome、Firefox、Edge、Safari等所有主流浏览器,通过WebDriver协议与浏览器通信。
2. 安装
bash
# 安装selenium库
pip install selenium
# 下载对应浏览器的驱动(以Chrome为例)
# 方式一:手动下载 chromedriver(需匹配浏览器版本)
# 方式二:使用 webdriver-manager 自动管理驱动
pip install webdriver-manager
推荐使用webdriver-manager,避免版本不匹配问题:
python
from selenium import webdriver
from selenium.webdriver.chrome.service import Service
from webdriver_manager.chrome import ChromeDriverManager
service = Service(ChromeDriverManager().install())
driver = webdriver.Chrome(service=service)
3. 基本使用
python
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
# 启动浏览器
driver = webdriver.Chrome()
driver.get("https://example.com")
# 等待元素出现并点击
wait = WebDriverWait(driver, 10)
button = wait.until(EC.element_to_be_clickable((By.ID, "submit")))
button.click()
# 获取页面源码
html = driver.page_source
# 关闭
driver.quit()
4. 核心特性
- 显式等待 :
WebDriverWait+expected_conditions是处理动态加载的利器。 - 多浏览器支持 :通过更换
webdriver.Firefox()等即可切换。 - 丰富的API:支持Cookie操作、截图、执行JavaScript、切换iframe/窗口等。
- 缺点 :速度较慢(每次操作需经过WebDriver协议);对反爬检测(如
navigator.webdriver标志)防御较弱。
三、Playwright:微软的降维打击
1. 简介
Playwright由微软于2020年开源,专为现代Web应用设计。它基于CDP(Chrome DevTools Protocol)和Firefox/WebKit的私有协议,无需额外驱动,自带浏览器二进制文件,支持Chromium、Firefox、WebKit三大内核。
2. 安装
bash
# 安装playwright库
pip install playwright
# 安装浏览器(首次运行需下载,约100-200MB)
playwright install
注意 :playwright install会下载Chromium、Firefox、WebKit的定制版本,无需手动配置驱动。
3. 基本使用
python
from playwright.sync_api import sync_playwright
with sync_playwright() as p:
# 启动浏览器(默认无头模式)
browser = p.chromium.launch(headless=False) # headless=True为无头
page = browser.new_page()
page.goto("https://example.com")
# 等待并点击
page.click("#submit")
# 获取页面内容
content = page.content()
# 截图
page.screenshot(path="example.png")
browser.close()
异步版本(推荐用于高并发):
python
import asyncio
from playwright.async_api import async_playwright
async def main():
async with async_playwright() as p:
browser = await p.chromium.launch()
page = await browser.new_page()
await page.goto("https://example.com")
await page.click("#submit")
await browser.close()
asyncio.run(main())
4. 核心特性
- 自带抓包能力 :通过
page.route()拦截请求/响应,修改请求头、模拟网络条件(如断网、限速)。 - 无头模式默认:且速度极快,比Selenium快2-5倍。
- 自动等待 :
page.click()等操作内置智能等待,无需显式WebDriverWait。 - 反检测能力 :默认隐藏
navigator.webdriver,且支持修改浏览器指纹(如User-Agent、视口大小、语言等)。 - 多上下文 :支持
browser.new_context()隔离Cookie/缓存,适合多账号爬取。 - 代码生成器 :
playwright codegen可录制操作并生成代码,降低入门门槛。
四、实战对比:爬取动态加载的新闻列表
假设目标网站:https://news.ycombinator.com/(Hacker News),需要等待列表加载后提取标题。
Selenium实现
python
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
driver = webdriver.Chrome()
driver.get("https://news.ycombinator.com/")
wait = WebDriverWait(driver, 10)
# 等待表格行出现
rows = wait.until(EC.presence_of_all_elements_located((By.CSS_SELECTOR, "tr.athing")))
titles = [row.find_element(By.CSS_SELECTOR, "td.title a").text for row in rows]
print(titles)
driver.quit()
Playwright实现
python
from playwright.sync_api import sync_playwright
with sync_playwright() as p:
browser = p.chromium.launch()
page = browser.new_page()
page.goto("https://news.ycombinator.com/")
# 自动等待直到元素出现
rows = page.query_selector_all("tr.athing")
titles = [row.query_selector("td.title a").inner_text() for row in rows]
print(titles)
browser.close()
性能对比(本地测试,10次平均):
| 指标 | Selenium | Playwright |
|---|---|---|
| 启动时间 | 2.1s | 1.3s |
| 页面加载+提取 | 3.5s | 1.8s |
| 内存占用 | 180MB | 120MB |
| 代码行数 | 12行 | 8行 |
Playwright在速度、资源占用和代码简洁性上全面胜出。
五、深度对比:选型指南
| 维度 | Selenium | Playwright |
|---|---|---|
| 浏览器支持 | Chrome, Firefox, Edge, Safari, Opera等 | Chromium, Firefox, WebKit(Safari内核) |
| 驱动管理 | 需手动或借助webdriver-manager |
内置浏览器,playwright install一键搞定 |
| 安装复杂度 | 中等(需匹配驱动版本) | 低(但首次下载浏览器较大) |
| 执行速度 | 较慢(WebDriver协议开销) | 快(CDP协议,异步架构) |
| 反检测能力 | 弱(navigator.webdriver易被检测) |
强(默认隐藏,可自定义指纹) |
| 网络拦截 | 需借助BrowserMob等第三方工具 |
原生支持page.route(),功能强大 |
| 并发支持 | 多线程/多进程(需自行管理) | 原生异步,asyncio + 多上下文 |
| 社区生态 | 极其成熟,文档、教程、插件丰富 | 快速增长,微软官方维护,但部分小众场景资料较少 |
| 学习曲线 | 平缓(API直观) | 中等(异步概念、上下文模型) |
| 适用场景 | 兼容性要求极高(如Safari)、遗留项目维护 | 新项目首选,追求速度、反爬、高并发 |
何时选择Selenium?
- 必须测试Safari或旧版浏览器。
- 项目已基于Selenium构建,迁移成本高。
- 需要与Selenium Grid(分布式测试)集成。
何时选择Playwright?
- 爬取反爬严格的网站(如电商、社交平台)。
- 需要高性能、低资源消耗。
- 需要拦截网络请求(如修改请求头、模拟慢速网络)。
- 新项目启动,希望一步到位。
六、进阶技巧:Playwright反爬实战
Playwright在反爬方面有天然优势,以下是一些常用技巧:
1. 修改浏览器指纹
python
context = browser.new_context(
user_agent="Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 ...",
viewport={"width": 1920, "height": 1080},
locale="zh-CN",
timezone_id="Asia/Shanghai",
geolocation={"longitude": 116.4, "latitude": 39.9},
permissions=["geolocation"],
)
page = context.new_page()
2. 拦截并修改请求
python
def handle_route(route):
headers = route.request.headers
headers["X-Custom-Header"] = "value"
route.continue_(headers=headers)
page.route("**/*", handle_route)
3. 模拟人类行为
python
import random
import time
# 随机延迟
page.mouse.move(100, 200)
time.sleep(random.uniform(0.5, 1.5))
page.click("#button")
4. 绕过WebDriver检测
Playwright默认已隐藏navigator.webdriver,但可进一步注入脚本:
python
page.add_init_script("""
Object.defineProperty(navigator, 'webdriver', { get: () => undefined });
""")
七、总结与展望
- Selenium 如同一位经验丰富的老将,稳定、兼容、生态完善,但略显臃肿。
- Playwright 则是装备精良的新锐特种兵,速度快、反爬强、API现代,是2026年爬虫工程师的首选。
如果你的项目从零开始,毫不犹豫选择Playwright;如果维护老项目,可逐步迁移或混合使用(例如用Selenium处理Safari,Playwright处理Chrome/Firefox)。
未来,随着Web标准演进和反爬技术升级,浏览器自动化库将更注重隐身性 和效率。Playwright的持续更新(如支持更多协议、更细粒度的指纹控制)使其成为长期投资的明智之选。
最后提醒 :爬虫需遵守网站robots.txt及法律法规,本文仅用于技术学习与合法数据采集。