| name | playwright-automation |
| description | Playwright 浏览器自动化。用于自动化爬虫、数据采集、表单填写、UI 测试等需要浏览器自动化的场景。无需人工干预,适合 cron 定时任务。 |
| allowed-tools | Bash, Exec, Read, Write |
Playwright 浏览器自动化
概述
Playwright 是一个强大的浏览器自动化工具,可以模拟真实用户操作,支持:
- 无头浏览器模式(后台运行)
- 数据采集和爬虫
- 表单自动填写
- UI 自动化测试
- 截图和 PDF 生成
为什么需要 Playwright
⚠️ 资源清理原则(强制)
所有涉及浏览器的 cron 任务完成后,必须自动关闭 Chrome/Chromium 进程!
import subprocess
await browser.close()
await context.close()
subprocess.run(['pkill', '-f', 'chrome'], capture_output=True)
subprocess.run(['pkill', '-f', 'chromium'], capture_output=True)
原因: 避免内存泄漏和资源占用,防止 Gateway CPU 100% 过载
与 browser tool 的区别
| 特性 | browser tool | Playwright |
|---|
| 需要用户参与 | ✅ 需要手动打开浏览器 | ❌ 完全自动 |
| 适合定时任务 | ❌ | ✅ |
| 后台运行 | ❌ | ✅ |
| 调试友好 | ✅ 可视化操作 | ⚠️ 需要日志 |
| 无需安装 | ✅ 已集成 | ❌ 需要安装 |
使用场景
使用 Playwright:
- ✅ 定时监控(cron 任务)
- ✅ 大规模数据采集
- ✅ 无人值守运行
- ✅ 生产环境部署
使用 browser tool:
- ✅ 交互式调试
- ✅ 需要人工决策的操作
- ✅ 一次性任务
- ✅ 绕过复杂验证码
快速开始
1. 安装 Playwright
pip install playwright
playwright install chromium
python3 -c "from playwright.sync_api import sync_playwright; print('✅ 安装成功')"
2. 基本使用
同步 API(简单任务)
from playwright.sync_api import sync_playwright
with sync_playwright() as p:
browser = p.chromium.launch(headless=True)
page = browser.new_page()
page.goto('https://example.com')
print(page.title())
browser.close()
异步 API(推荐,性能更好)
import asyncio
from playwright.async_api import async_playwright
async def main():
async with async_playwright() as p:
browser = await p.chromium.launch(headless=True)
page = await browser.new_page()
await page.goto('https://example.com')
title = await page.title()
print(title)
await browser.close()
asyncio.run(main())
常用功能
1. 页面导航
await page.goto('https://example.com', wait_until='domcontentloaded')
2. 元素定位
await page.click('button.submit')
await page.fill('input[name="username"]', 'myuser')
await page.click('xpath=//button[@type="submit"]')
await page.click('text=登录')
await page.click('div.login-form >> text=登录')
3. 提取数据
text = await page.text_content('h1.title')
href = await page.get_attribute('a.link', 'href')
items = await page.query_selector_all('div.item')
for item in items:
text = await item.text_content()
print(text)
result = await page.evaluate('() => document.title')
html = await page.content()
4. 表单操作
await page.fill('input[name="username"]', 'myuser')
await page.fill('input[name="password"]', 'mypass')
await page.click('button[type="submit"]')
await page.select_option('select#country', 'China')
await page.check('input#agree')
await page.set_input_files('input[type="file"]', 'path/to/file.pdf')
5. 等待策略
await page.wait_for_selector('div.result', timeout=5000)
async with page.expect_navigation():
await page.click('a.link')
await page.wait_for_function('() => document.title.includes("加载完成")')
import asyncio
await asyncio.sleep(2)
6. 滚动和交互
await page.evaluate('window.scrollTo(0, document.body.scrollHeight)')
await page.locator('div.footer').scroll_into_view_if_needed()
await page.hover('div.menu')
await page.drag_and_drop('div.draggable', 'div.dropzone')
7. 截图和 PDF
await page.screenshot(path='screenshot.png')
await page.screenshot(path='full.png', full_page=True)
await page.locator('div.content').screenshot(path='element.png')
await page.pdf(path='page.pdf', format='A4')
8. 处理弹窗
async with page.expect_event('dialog') as dialog_info:
await page.click('button')
dialog = await dialog_info.value
await dialog.accept()
async with page.expect_event('dialog') as dialog_info:
await page.click('button')
dialog = await dialog_info.value
await dialog.accept('my input')
反爬策略
1. User-Agent 轮换
user_agents = [
'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36',
'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36',
'Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36'
]
browser = await p.chromium.launch(
user_agent=random.choice(user_agents)
)
2. 随机延迟
import random
import asyncio
await asyncio.sleep(random.uniform(2, 5))
3. Cookie 保存和加载
context = await browser.new_context()
await page.goto('https://example.com/login')
await context.storage_state(path='cookies.json')
context = await browser.new_context(storage_state='cookies.json')
4. 代理设置
browser = await p.chromium.launch(
proxy={
'server': 'http://proxy.example.com:8080',
'username': 'user',
'password': 'pass'
}
)
5. 浏览器上下文隔离
context = await browser.new_context(
viewport={'width': 1920, 'height': 1080},
user_agent='Custom UA',
locale='zh-CN'
)
page = await context.new_page()
调试技巧
1. 显示浏览器
browser = await p.chromium.launch(headless=False, slow_mo=1000)
2. 截图调试
await page.goto('https://example.com')
await page.screenshot(path='step1.png')
await page.click('button')
await page.screenshot(path='step2.png')
3. 查看日志
page.on('console', lambda msg: print(f'Console: {msg.text}'))
page.on('request', lambda request: print(f'Request: {request.url}'))
page.on('response', lambda response: print(f'Response: {response.status}'))
4. Playwright Inspector
PWDEBUG=1 python3 your_script.py
常见问题
Q: 如何处理验证码?
A: 几种方案
- 使用打码平台(超级鹰、若快打码)
- 手动处理:暂停等待用户输入
- 降级:用 browser tool 让用户手动操作
input("遇到验证码,请在浏览器中完成,然后按回车继续...")
await asyncio.sleep(2)
Q: 元素找不到怎么办?
A: 检查以下几点
- 是否在 iframe 中(需要切换)
- 是否动态加载(需要等待)
- 选择器是否正确
frame = page.frame('iframe-id')
await frame.click('button')
await page.wait_for_selector('div.dynamic-content')
Q: 如何提高性能?
A:
- 使用异步 API
- 并发多个页面
- 减少不必要的等待
async def fetch(url):
page = await browser.new_page()
await page.goto(url)
tasks = [fetch(url) for url in urls]
await asyncio.gather(*tasks)
与 OpenClaw 集成
在 healthcare-monitor 中的使用
from playwright.async_api import async_playwright
async with async_playwright() as p:
browser = await p.chromium.launch(headless=True)
context = await browser.new_context(
user_agent="Mozilla/5.0 ..."
)
page = await context.new_page()
await page.goto(url)
await browser.close()
与 browser tool 配合
- Playwright → 日常自动监控
- browser tool → 调试和异常处理
资源
快速命令
pip install playwright && playwright install chromium
python3 script.py
PWDEBUG=1 python3 script.py
playwright --version
记住: Playwright 让你的自动化任务完全无人值守!🚀