Files
val-blog/skills/browser-automation/SKILL.md
T

6.4 KiB
Raw Blame History

Browser Automation Skill

使用 Playwright 调用本地 Chrome 进行反检测浏览器自动化。

简介

此 Skill 封装了浏览器自动化功能,专门设计用于规避常见的爬虫检测机制(如 Cloudflare、DataDome 等)。通过使用本地安装的 Chrome 并配置反检测参数,可以模拟真实用户行为。

特点

  • 反检测模式:禁用 navigator.webdriver 标记,绕过自动化检测
  • 本地 Chrome:使用系统安装的 Google Chrome,而非 Playwright 自带的 Chromium
  • 两种模式
    • launch 模式:直接启动 Chrome(带反检测参数)
    • cdp 模式:连接已运行的 Chrome 实例
  • 简洁 APInavigate, click, type, snapshot, scroll, screenshot, close

安装依赖

# 安装 Playwright
pip install playwright

# 安装 Chromiumplaywright 需要,虽然我们使用本地 Chrome)
playwright install chromium

使用方式

1. 基础用法(Launch 模式)

from browser_tool import BrowserTool

# 创建浏览器实例
browser = BrowserTool(mode="launch", headless=False)

# 导航到页面
snapshot = browser.navigate("https://example.com")
print(snapshot)

# 点击元素
browser.click("@e5")

# 输入文本
browser.type("@e3", "search query")
browser.press("Enter")

# 滚动页面
browser.scroll("down")

# 截图
path = browser.screenshot()

# 关闭
browser.close()

2. 使用上下文管理器

from browser_tool import BrowserTool

with BrowserTool(mode="launch", headless=False) as browser:
    snapshot = browser.navigate("https://example.com")
    print(snapshot)
    # 自动关闭

3. CDP 模式(连接已运行的 Chrome)

首先启动 Chrome 并开启调试端口:

/Applications/Google\ Chrome.app/Contents/MacOS/Google\ Chrome \
  --remote-debugging-port=9222 \
  --user-data-dir=/tmp/chrome_debug

然后在代码中连接:

from browser_tool import BrowserTool

browser = BrowserTool(mode="cdp", cdp_url="http://localhost:9222")
snapshot = browser.navigate("https://example.com")

4. 使用快捷函数

from browser_tool import create_browser

browser = create_browser(mode="launch", headless=False)

5. 启动 Chrome 调试实例

from browser_tool import launch_chrome_debug_port

# 启动 Chrome 并开启 9222 端口
proc = launch_chrome_debug_port(port=9222)

# 之后可以用 CDP 模式连接

API 参考

BrowserTool 类

构造函数

BrowserTool(
    mode: Literal["launch", "cdp"] = "launch",
    cdp_url: str = "http://localhost:9222",
    headless: bool = False,
    chrome_path: Optional[str] = None,
)

参数:

  • mode: 启动模式,"launch" 直接启动 Chrome"cdp" 连接已运行的 Chrome
  • cdp_url: CDP 连接地址(仅 mode="cdp" 时使用)
  • headless: 是否无头模式(建议 False 规避检测)
  • chrome_path: Chrome 可执行文件路径(默认使用 /Applications/Google Chrome.app/Contents/MacOS/Google Chrome

方法

navigate(url, wait_until="networkidle") -> str

导航到指定 URL,返回页面快照。

  • url: 目标网址
  • wait_until: 等待条件 (load, domcontentloaded, networkidle)

返回:页面快照文本,包含交互元素列表

snapshot(full=False) -> str

获取当前页面快照。

  • full: 是否返回完整页面内容(默认只返回交互元素)
click(ref, wait_for_navigation=False)

点击元素。

  • ref: 元素引用 ID,如 @e5
  • wait_for_navigation: 是否等待页面跳转
type(ref, text, clear=True)

在输入框填入文本。

  • ref: 元素引用 ID
  • text: 要输入的文本
  • clear: 是否先清空输入框
scroll(direction="down", amount=500)

滚动页面。

  • direction: "up""down"
  • amount: 滚动像素数
screenshot(path=None) -> str

截取页面截图。

  • path: 截图保存路径(默认自动命名)

返回:截图文件路径

press(key)

按下键盘按键。

  • key: 按键名称 (Enter, Tab, Escape, ArrowDown, 等)
back()

返回上一页。

close()

关闭浏览器会话。

check_detection() -> Dict

检查反检测效果,访问 https://bot.sannysoft.com/ 并返回检测结果。

返回:包含 webdriver, plugins, languages, userAgent, chrome 等字段的字典

页面快照格式

snapshot()navigate() 返回的快照文本格式如下:

URL: https://example.com
Title: Example Domain

=== Interactive Elements ===

[@e1] <a href="https://example.com/page">Link text</a>
[@e2] <button type="submit">Submit</button>
[@e3] <input type="text" placeholder="Search...">
[@e4] <textarea name="content">

使用 @e1, @e2 等引用 ID 进行点击和输入操作。

反检测原理

  1. 使用本地 Chrome:而非 Playwright 自带的 headless Chromium,避免被识别为自动化浏览器
  2. 禁用 webdriver 标记:通过 Object.definePropertynavigator.webdriver 设为 undefined
  3. 配置启动参数
    • --disable-blink-features=AutomationControlled:禁用自动化控制特征
    • --disable-web-security:禁用 web 安全(可选)
    • --window-size:设置正常 viewport
  4. 非无头模式headless=False 让 Chrome 真实显示

常见问题

Q: Chrome 路径不对?

在创建 BrowserTool 时指定路径:

browser = BrowserTool(chrome_path="/path/to/chrome")

Q: 如何查找 Chrome 路径?

# macOS
ls /Applications/Google\ Chrome.app/Contents/MacOS/Google\ Chrome

# 或使用 mdfind
mdfind -name "Google Chrome.app"

Q: CDP 模式连接失败?

确保 Chrome 已启动并开启调试端口:

/Applications/Google\ Chrome.app/Contents/MacOS/Google\ Chrome \
  --remote-debugging-port=9222

检查端口是否监听:

curl http://localhost:9222/json/version

Q: 还是被检测到了?

尝试以下方法:

  1. 确保 headless=False
  2. 使用 CDP 模式连接手动启动的 Chrome
  3. 添加更多延迟:browser._page.wait_for_timeout(2000)
  4. 使用代理或 VPN 更换 IP

文件结构

browser-automation/
├── SKILL.md           # 本文档
└── browser_tool.py    # 核心封装

依赖

  • Python 3.8+
  • Playwright
  • Google Chrome(本地安装)

参考