chrome-devtools-skill について
Chrome DevTools Skill は、Chrome DevTools Protocol と chrome-devtools-mcp を使ったブラウザー操作を AI に案内するスキルです。Web ページのデータ抽出、自動化、分析向けに、Chrome の起動からページ操作、ネットワークリクエストの確認、性能トレースまでの手順を示します。
主な機能
- 01デバッグモードで Chrome を起動
- 02MCP による Web ページ操作
- 03ページや表のデータ抽出
- 04スクリーンショットとリクエスト確認
- 05性能トレースとフォーム自動化
活用シーン
- 01Web ページの一覧や商品情報を収集
- 02ページが読み込む API を調査
- 03フォーム入力とスクリーンショット撮影
- 04Web ページの性能を分析
MCP 対応
このスキルは chrome-devtools-mcp を起動し、Chrome のローカルリモートデバッグポートに接続します。MCP ツールでページ遷移、読み込み待機、内容抽出、スクリーンショット撮影、ネットワークリクエスト確認を行います。
インストール
コマンドをコピーしてターミナルで実行します。
npx skills add https:/ / github.com/ steelan9199/ wechat-publisher --skill chrome-devtools-skillインストール後、Claude Code で/chrome-devtools-skillを入力して読み込まれたか確認します。
同梱ファイル
SKILL.md と一緒にインストールされる参考資料やスクリプト。
references/baidu-search-frontend-mode-guide.mdbaidu-search-template.pycdp-frontend-mode-cheatsheet.mdREADME.mdscripts/baidu_search_example.pybaidu_search_visual.pycdp_helper.pyREADME.md詳細
Chrome DevTools スキル
Chrome DevTools Protocol を使用して、ウェブページのデータを取得・分析します。
ワークフロー(AI が自動実行)
ユーザーがこのスキルを使用した場合、AI はユーザーに手動で実行させるのではなく、以下のすべての手順を自動的に完了する必要があります。
1. Chrome のリモートデバッグを自動で開始
AI は OS を自動検出し、Chrome を起動します。
Windows:
start chrome --remote-debugging-port=9222 --user-data-dir="%TEMP%\chrome-devtools-profile" [URL]
重要: 固定の
--user-data-dir(例:chrome-devtools-profile)を使用し、起動するたびに異なるフォルダーを使わないでください。これにより、Chrome はログイン状態、Cookie、キャッシュを記憶し、次回の起動が速くなります。
macOS:
/Applications/Google\ Chrome.app/Contents/MacOS/Google\ Chrome --remote-debugging-port=9222 --user-data-dir="$TMPDIR/chrome-profile-stable" [URL]
Linux:
google-chrome --remote-debugging-port=9222 --user-data-dir="/tmp/chrome-profile-stable" [URL]
2. MCP サーバーを自動で起動
AI は MCP サーバーをバックグラウンドで自動的に起動します。
npx -y chrome-devtools-mcp@latest --browser-url=http://127.0.0.1:9222
3. ユーザーのリクエストされた操作を実行
以下の MCP ツールを使用して、ユーザーのタスクを完了します。
mcp__chrome-devtools__navigate_page- ページに移動mcp__chrome-devtools__wait_for- ページの読み込みを待機mcp__chrome-devtools__take_snapshot- ページのスナップショットを取得mcp__chrome-devtools__evaluate_script- JavaScript を実行してデータを抽出mcp__chrome-devtools__screenshot- スクリーンショットを撮影mcp__chrome-devtools__list_network_requests- ネットワークリクエストを一覧表示
標準的な操作手順(AI が使用)
ユーザーからウェブページを開く、分析する、または取得するよう依頼された場合、AI は次の順序で実行します。
1. 启动 Chrome(调试模式)
2. 启动 MCP 服务器
3. 导航到目标 URL
4. 等待页面加载
5. 执行用户请求的操作(截图/提取数据/监控网络等)
6. 返回结果给用户
データ抽出のコツ
リストデータの抽出:
() => {
const items = document.querySelectorAll(".item");
return Array.from(items).map((item) => ({
title: item.querySelector(".title")?.innerText,
link: item.querySelector("a")?.href,
}));
};
表データの抽出:
() => {
const rows = document.querySelectorAll("table tr");
return Array.from(rows).map((row) =>
Array.from(row.querySelectorAll("td, th")).map((cell) => cell.innerText)
);
};
よくあるユースケース
- ウェブページを開いてスクリーンショットを撮影: Chrome を起動 → 移動 → スクリーンショットを撮影 → 結果を返す
- 商品情報の取得: 移動 → スクロールして読み込み → リストを抽出
- フォームの自動化: 移動 → fill_form → click → wait_for
- API の監視: 移動 → list_network_requests → get_network_request
- パフォーマンス分析: performance_start_trace → 操作 → performance_stop_trace
ベストプラクティス
- すべての事前手順を自動で処理する - Chrome や MCP サーバーを手動で起動するようユーザーに求めないでください
- 固定のユーザーデータディレクトリを使用する -
--user-data-dirを常に同じ値にして、毎回再読み込みされるのを防ぎます - まず
take_snapshotを使ってページの構造を確認します - 複雑な抽出では
evaluate_scriptを使って JavaScript を実行します - 返すデータが JSON にシリアライズ可能であることを確認します
- 動的コンテンツを処理する際は
wait_forを使用します
技術的な仕組み
Chrome DevTools Protocol (CDP) の通信方式
| 方式 | プロトコル | 用途 |
|---|---|---|
| HTTP | http://127.0.0.1:9222/json/list | ページ一覧と基本情報を取得 |
| WebSocket | ws://127.0.0.1:9222/devtools/page/{pageId} | ページをリアルタイムで制御し、スクリプトを実行 |
WebSocket の通信フロー
import asyncio
import websockets
import json
async def cdp_example():
# 1. 连接到 Chrome DevTools WebSocket
ws_url = "ws://127.0.0.1:9222/devtools/page/{pageId}"
async with websockets.connect(ws_url) as ws:
# 2. 启用 Runtime 域
await ws.send(json.dumps({
"id": 1,
"method": "Runtime.enable"
}))
# 3. 执行 JavaScript
await ws.send(json.dumps({
"id": 2,
"method": "Runtime.evaluate",
"params": {
"expression": "document.title",
"returnByValue": True
}
}))
# 4. 循环接收响应,匹配 id
while True:
msg = await ws.recv()
data = json.loads(msg)
if data.get('id') == 2: # 匹配请求 id
return data['result']['result']['value']
重要な注意事項
- 応答の照合: WebSocket は複数種類のメッセージ(
consoleAPICalled、executionContextCreatedなど)を受信します。リクエストと応答を照合するには、必ずidを使用してください - ページの読み込みを待つ: 操作を実行した後、
await asyncio.sleep(2)を使用するか、特定の要素が表示されるまで待ちます - エンコーディングの問題: Windows のターミナルで中国語を正しく表示するには、
sys.stdout.reconfigure(encoding='utf-8')が必要です
実践的な知見と注意点
問題 1: Windows で中国語を出力すると文字化けする
現象: 取得した中国語の内容が文字化けして表示される、または UnicodeEncodeError: 'gbk' codec can't encode character が発生する
原因: Windows のターミナルはデフォルトで GBK エンコーディングを使用しているため、Python が UTF-8 の中国語を出力すると競合します
解決策: Python スクリプトの先頭にエンコーディング設定を追加します。
import sys
sys.stdout.reconfigure(encoding='utf-8')
重要: すべてのサンプルスクリプト(baidu_search_example.py、cdp_helper.py)には、このエンコーディング設定が追加済みです。そのまま実行すれば文字化けしません。
問題 2: HTML 文字実体のエスケープ
現象: JavaScript コード内の => アロー関数が、JSON で転送する際に => にエスケープされる
原因: JSON 標準では、一部の文字が Unicode エスケープされる場合があります
解決策: これは正常な動作で、実行には影響しません。Python で処理する必要がある場合は、次を使用できます。
import codecs
decoded = codecs.decode(string, 'unicode_escape')
問題 3: ページ ID の取得
現象: 現在のページの WebSocket URL がわからない 解決策: HTTP インターフェースからページ一覧を取得します。
curl -s http://127.0.0.1:9222/json/list
次に、webSocketDebuggerUrl フィールドを抽出します。
注意: ページ ID は動的に生成されるため、Chrome を起動するたびに変わります。ハードコードするのではなく、コード内で動的に取得してください。
import urllib.request
import json
def get_ws_url():
req = urllib.request.Request('http://127.0.0.1:9222/json/list')
with urllib.request.urlopen(req) as response:
pages = json.loads(response.read().decode())
return pages[0]['webSocketDebuggerUrl'] if pages else None
問題 4: Windows の待機コマンドにおけるクロスプラットフォーム互換性の問題
現象: Git Bash で timeout /t 3 /nobreak を使用すると、invalid time interval エラーが発生する
原因: timeout は Windows CMD のコマンドであり、Bash とは構文に互換性がありません
解決策: クロスプラットフォームで使える待機方法を使用します。
# Windows CMD
timeout /t 3 /nobreak >nul
# Git Bash / Linux
sleep 3
# 跨平台通用(Windows)
ping -n 4 127.0.0.1 > nul
問題 5: Claude Code のファイル書き込み制限
現象: Write ツールを直接使って新しいファイルを作成すると、"File has not been read yet" と表示される 原因: Claude Code では、安全機構により、書き込む前にファイルを読み取る必要があります 解決策:
- まず Read ツールでファイルを読み取ります(ファイルが存在しない場合はエラーになるため、Bash を使って空のファイルを作成する必要があります)
- または Bash の
echoコマンドやcatコマンドを使って直接書き込みます - または Python スクリプトでコードを動的に生成して実行します
問題 6: 動的コンテンツの抽出が不完全
現象: 抽出した検索結果の一部のフィールド(概要など)が空になる 原因:
- ページが動的読み込みを使用しており、すべてのコンテンツを表示するにはスクロールが必要です
- ウェブサイトによって異なる class 名が使用されています
- 一部のコンテンツは非同期で読み込まれます
解決策:
- 複数のセレクターを使って照合します。
const abstract = item.querySelector('.c-abstract, .abstract, [class*="abstract"]')?.innerText;
- ページをスクロールして、さらにコンテンツを読み込みます。
window.scrollTo(0, document.body.scrollHeight);
- 非同期コンテンツの読み込みが完了するように、待機時間を長くします
問題 7: ブラウザーのフォアグラウンド操作とバックグラウンド操作
CDP は 2 種類の操作モードに対応しています。ユーザーの要望に応じて選択してください。
バックグラウンド操作(デフォルト):
- WebSocket 経由で JavaScript コマンドを送信し、DOM を直接操作します
- ブラウザーの画面には操作の過程が表示されません(ユーザーは入力やクリックなどの動作を確認できません)
- データ取得や自動テストなど、視覚的なフィードバックが不要な場面に適しています
- コード例:
# 直接设置输入框的值(用户看不到输入过程)
await ws.send(json.dumps({
"method": "Runtime.evaluate",
"params": {
"expression": "document.querySelector('#kw').value = '美女';"
}
}))
フォアグラウンド操作(可視化):
- CDP の Input ドメインを使って、実際のユーザー入力をシミュレートします
- ブラウザーに操作の全過程が表示されます(キーボード入力、マウスクリックなど)
- デモ、チュートリアル、ユーザーが操作の過程を確認する必要がある場面に適しています
- コード例:
# 1. 先聚焦输入框
await ws.send(json.dumps({
"method": "Runtime.evaluate",
"params": {
"expression": "document.querySelector('#kw').focus();"
}
}))
# 2. 模拟键盘输入(用户能看到逐字输入)
for char in "美女":
await ws.send(json.dumps({
"method": "Input.dispatchKeyEvent",
"params": {
"type": "char",
"text": char
}
}))
await asyncio.sleep(0.1) # 模拟真实打字间隔
# 3. 模拟点击搜索按钮(用户能看到点击效果)
await ws.send(json.dumps({
"method": "Input.dispatchMouseEvent",
"params": {
"type": "mousePressed",
"x": 100,
"y": 200,
"button": "left"
}
}))
選択の目安:
| 場面 | 推奨モード | 理由 |
|---|---|---|
| データ取得 | バックグラウンド | 高速で、可視化が不要です |
| 自動テスト | バックグラウンド | 安定していて、UI の影響を受けません |
| 検索タスク | バックグラウンド | URL を直接組み立てるほうが簡単で確実です |
| 操作のデモ | フォアグラウンド | ユーザーが全過程を確認できます |
| チュートリアル | フォアグラウンド | 観察して理解しやすくなります |
| フォーム入力 | どちらでも可 | バックグラウンドは高速で、フォアグラウンドはより直感的です |
検索タスクの推奨方法:
- バックグラウンド方式(推奨):
https://www.baidu.com/s?wd=キーワードのように、検索 URL を直接組み立てます - フォアグラウンド方式: ユーザーが「可視化」や「操作の過程を確認できること」を明確に求めた場合にのみ使用します
问题 8: 搜索类任务的最佳实践
场景: 用户要求"在百度/谷歌搜索某某关键词并抓取结果"
方案对比:
| 方案 | 实现方式 | 优点 | 缺点 | 推荐度 |
|---|---|---|---|---|
| A | 后台直接访问搜索URL | 简单、快速、稳定 | 用户看不到过程 | ⭐⭐⭐⭐⭐ |
| B | 前台模拟输入点击 | 可视化、有反馈 | 复杂、慢、需处理坐标 | ⭐⭐⭐ |
推荐方案 A(后台方式):
# 直接构造搜索URL,一步到位
url = f"https://www.baidu.com/s?wd={urllib.parse.quote(keyword)}"
await client.navigate(url)
await asyncio.sleep(3) # 等待加载
results = await client.evaluate(extract_script)
何时使用方案 B(前台方式):
- 用户明确要求"可视化操作"、"让我看到过程"
- 教学演示场景
- 需要展示自动化操作过程
前台方式注意事项:
- 必须先
focus()输入框 - 打字间隔 0.1-0.15 秒最合适
- 百度搜素按钮坐标约 x:650, y:230(1920x1080分辨率)
- 需要启用 Input 域:
Input.enable
前台输入文字详细步骤(以百度搜索框为例):
# 步骤 1: 启用 Input 域(必须先启用才能发送键盘事件)
await ws.send(json.dumps({
"id": 1,
"method": "Input.enable"
}))
# 步骤 2: 聚焦输入框(关键步骤,否则键盘事件可能无效)
await ws.send(json.dumps({
"id": 2,
"method": "Runtime.evaluate",
"params": {
"expression": "document.querySelector('#kw').focus();", # '#kw' 是百度搜索框ID
"returnByValue": True
}
}))
await asyncio.sleep(0.5) # 等待聚焦完成
# 步骤 3: 清空输入框(可选,确保输入框为空)
await ws.send(json.dumps({
"id": 3,
"method": "Runtime.evaluate",
"params": {
"expression": "document.querySelector('#kw').value = '';",
"returnByValue": True
}
}))
# 步骤 4: 逐字输入文字(用户能看到逐字输入动画)
text = "hello 你好呀"
for i, char in enumerate(text):
await ws.send(json.dumps({
"id": 10 + i,
"method": "Input.dispatchKeyEvent",
"params": {
"type": "char", # 输入字符
"text": char # 要输入的字符
}
}))
await asyncio.sleep(0.15) # 打字间隔,让用户能看到动画
关键要点:
type: "char"用于输入普通字符- 必须先
focus()输入框,否则输入可能无效 - 间隔时间建议 0.1-0.2 秒,太短可能漏字,太长用户等待久
- 支持中文输入,无需额外编码处理
问题 9: 表单自动化执行顺序
正确顺序:
- 启用 Runtime → 2. 填充输入框 → 3. 点击按钮 → 4. 等待页面加载 → 5. 提取数据
示例代码(百度搜索后台方式):
# 1. 填充搜索词
await ws.send(json.dumps({
"id": 2,
"method": "Runtime.evaluate",
"params": {
"expression": "document.querySelector('#kw').value = '搜索词';",
"returnByValue": True
}
}))
# 2. 点击搜索按钮
await ws.send(json.dumps({
"id": 3,
"method": "Runtime.evaluate",
"params": {
"expression": "document.querySelector('#su').click();",
"returnByValue": True
}
}))
# 3. 等待加载
await asyncio.sleep(3)
# 4. 提取结果
await ws.send(json.dumps({
"id": 4,
"method": "Runtime.evaluate",
"params": {
"expression": """
(() => {
const items = document.querySelectorAll('.result');
return Array.from(items).map(item => ({
title: item.querySelector('h3')?.innerText,
link: item.querySelector('a')?.href
}));
})()
""",
"returnByValue": True
}
}))
用户使用指南
如何使用此 Skill
用户可以通过以下方式触发此 skill:
- 直接说明需求 - 描述你想对网页做什么
- 使用
/chrome-devtools-skill命令 - 显式调用 skill - 提及网页操作 - 任何涉及"打开网页、抓取数据、截图"等关键词
提示词示例
以下是一些用户可以使用的提示词模板:
基础操作
打开 https://www.example.com 并截图
抓取 https://www.example.com 的页面内容
分析一下这个网页:https://github.com/xxx/xxx
数据提取
打开 https://www.jd.com,提取首页所有商品标题和价格
访问 https://www.zhihu.com/explore,获取热门问题列表
抓取 https://www.example.com 页面中的所有链接
监控和分析
打开 https://www.example.com,监控页面加载的所有 API 请求
分析 https://www.example.com 的页面性能
访问 https://www.example.com,提取页面中的所有图片地址
自动化操作
打开 https://www.example.com,在搜索框输入"关键词"并搜索
访问 https://www.example.com,点击"加载更多"按钮,抓取所有列表数据
提示词技巧
- 明确 URL - 提供完整的网页地址
- 说明目标 - 清楚描述你想获取什么数据或执行什么操作
- 指定格式 - 如果需要特定格式,可以说明(如"以表格形式返回")
- 复杂任务分步 - 对于多步骤任务,可以分步描述
示例对话
用户: 帮我打开百度,看看热搜榜有什么内容
AI: [自动启动 Chrome → 打开百度 → 提取热搜数据 → 返回结果]
用户: 抓取 https://news.ycombinator.com 的前 10 条新闻标题和链接
AI: [自动启动 Chrome → 打开 Hacker News → 提取新闻数据 → 返回表格]
用户: 分析一下淘宝首页都加载了哪些接口
AI: [自动启动 Chrome → 打开淘宝 → 监控网络请求 → 返回 API 列表]
参考资源
- 示例脚本: 见
scripts/目录baidu_search_example.py- 百度搜索完整示例cdp_helper.py- CDP 客户端封装类README.md- 快速开始指南
Chrome DevTools MCP 配置信息
如果用户询问chrome-devtools MCP怎么配置,提供以下 JSON 配置信息:
{
"mcpServers": {
"chrome-devtools": {
"command": "npx",
"args": [
"chrome-devtools-mcp@latest",
"--browser-url=http://127.0.0.1:9222"
]
}
}
}
// 测试修改 // 另一个测试修改 // 测试修改 pre-push 方案