peach-e2e-scenario について
peach-e2e-scenarioは、ブラウザーE2Eシナリオの作成と実行を行い、失敗時にはスクリプトを修正するスキルです。既存パターンを参照し、必要に応じて実際のDOMを調べ、回数制限付きの修正と実行承認を適用します。
主な機能
- 01作成・実行・両方のモード
- 02デバッグ時のDOMとセレクター確認
- 03node --checkによるスクリプト検証
- 04最大3回のスクリプト修正
- 05実行前のタブ選択確認
- 06センシティブなセッションの実行承認
活用シーン
- 01タスク説明からブラウザーテストを生成
- 02既存シナリオを実行して失敗を修正
- 03codegenの記録コードをシナリオに変換
インストール
コマンドをコピーしてターミナルで実行します。
npx skills add https:/ / github.com/ peachsolution/ peach-harness --skill peach-e2e-scenarioインストール後、Claude Code で/peach-e2e-scenarioを入力して読み込まれたか確認します。
同梱ファイル
SKILL.md と一緒にインストールされる参考資料やスクリプト。
references/daemon-잔류-대응.mddialog-handler-패턴.mdvalidation-통과-패턴.md변환규칙.md시나리오-생성-패턴.md자동수정-판단트리.md코드패턴.md프레임워크-대응.md詳細
E2E シナリオ統合エキスパート
シナリオの作成、実行、自動修正を単一のループで処理します。 既存のシナリオコードのパターンを参考にし、必要に応じて DOM をリアルタイムで調査してシナリオを作成します。 実行に失敗した場合は、エラーを分析してスクリプトを直接修正し、再実行します。
モード
| モード | トリガー | 動作 |
|---|---|---|
auto(デフォルト) | /peach-e2e-scenario [説明] | 作成+実行+自動修正ループ |
create | /peach-e2e-scenario create [説明 or codegen] | シナリオ作成のみ |
run | /peach-e2e-scenario run [パス or 番号] | 実行+自動修正ループ |
ツールの役割分担
| 用途 | ツール |
|---|---|
| シナリオ実行 | ./e2e.sh run(playwright-cli ベース) |
| セレクターのデバッグ/DOM の確認 | agent-browser eval(高速) |
| iframe のデバッグ | ./e2e/pwc.sh eval(フォールバック) |
| 構文検証 | node --check |
強制ゲート
- Chrome Beta の起動には、まず
cd e2e && ./e2e.sh chromeを使用します。直接起動する必要がある場合は、必ず--user-data-dir=$HOME/.chrome-beta-e2e-profileを含めます。 ./e2e.sh statusでタブ一覧を確認し、ユーザーが実行するタブを指定するまでは、./e2e.sh run、agent-browser eval、タブの切り替えを開始しません。- Google ログイン、OAuth、管理コンソール、決済、既存の Chrome Beta プロファイルのセッション維持が重要な作業は、シナリオの作成/分析まで進め、実際の実行はユーザーの確認後に開始します。
agent-browserのデバッグに問題がある場合、OS レベルでブラウザーを迂回する方法(open -a、別のブラウザーの起動、別のプロファイルパスの使用)は行いません。- ログイン/2 要素認証が必要な場合、AI が直接対応することはありません。ユーザーに Chrome Beta の固定プロファイルで事前に認証を完了するよう案内します。
Chrome Beta 起動時の不変ルール
Chrome Beta を CDP モードで起動する場合、固定プロファイルのオプションは必須です。プロファイルオプションがない起動は、セッション維持に失敗したものとみなします。
- 許可:
cd e2e && ./e2e.sh chrome - 直接起動時の必須オプション:
--remote-debugging-port=9222、--remote-allow-origins=*、--user-data-dir=$HOME/.chrome-beta-e2e-profile、--disable-extensions - macOS での直接起動の標準形式:
/usr/bin/open -na "Google Chrome Beta" --args ... - 禁止:
open -a "Google Chrome Beta"のみでの実行、--argsのないopenの実行、--user-data-dirのない Chrome Beta の起動、別のプロファイルパスの任意使用、標準の Chrome または別のブラウザーによる迂回
ワークフロー
共通:環境確認+タブ確認
cd e2e && ./e2e.sh setup
setup はすべての環境(Chrome Beta、agent-browser、playwright-cli、CDP 接続)を自動で確認/インストールします。
CDP に接続されていない場合は、次の順序で自動復旧をまず試します。
cd e2e && ./e2e.sh chrome &を実行sleep 4で待機cd e2e && ./e2e.sh statusで再確認- それでも接続されない場合は、ユーザーに
cd e2e && ./e2e.sh chromeの手動実行を案内
./e2e.sh chromeは、固定プロファイル($HOME/.chrome-beta-e2e-profile)で Chrome Beta を起動する標準的な方法です。このコマンドの代わりに Chrome を直接起動する場合も、--user-data-dirオプションを省略しないでください。
cd e2e && ./e2e.sh status
タブ一覧をユーザーに表示して、**「何番のタブで実行しますか?」**と確認します。
タブ番号は0 番から開始します。
chrome://タブは除外します。[番号] は--tab Nの N と同じです。 ユーザーがログイン済みのタブをそのまま使用します。環境(local/test/prod)の区別はありません。 タブ番号を受け取るまでは実行しません。機密性の高いセッションを扱う作業は、タブ番号を受け取った後も、ユーザーの承認を得るまでは分析のみ行います。 タブのドリフト防止:ユーザーがタブ番号を回答した後、agent-browser tab Nの直後にagent-browser eval "document.title + ' | ' + location.href"を実行し、タブが正しいか再確認します。 想定と異なる場合は./e2e.sh statusを再表示して、選び直します。デバッグ/再現時にはE2E_TAB_IDの固定を推奨します。 (詳細:peach-e2e-browse/references/탭-선택-패턴.md)
ファイルアップロードのシナリオ:シナリオコードで
page.setInputFiles()または file input の操作が必要な場合は、 OS ネイティブのファイルダイアログをブロックするため、Page.setInterceptFileChooserDialog方式を使用します。 CDP Escape/agent-browser press Escapeでは、macOS ネイティブのダイアログを閉じられません。 (詳細:peach-e2e-browse/references/SPA-프레임워크-입력패턴.md §3)
auto モード(デフォルト)
- 入力ソースの判定 — 自然言語のリクエストか、codegen の録画コードかを判定
- 既存シナリオのパターンを参照 —
e2e/시나리오/以下にある既存コードを読み、パターンを把握references/시나리오-생성-패턴.mdを参照
- DOM の事前調査(必要に応じて)— agent-browser eval で URL の構造とセレクターを事前確認
- シナリオ作成 —
references/코드패턴.mdを参照してスクリプトを作成- codegen 入力の場合は
references/변환규칙.mdも追加で参照 - フレームワークごとの違いは
references/프레임워크-대응.mdを参照
- codegen 入力の場合は
- 情報確認 — シナリオ名(韓国語)、保存先のカテゴリーフォルダー(韓国語の業務ドメイン)、カテゴリー内の連番(
NN-)、このシナリオが残す state の契約、このシナリオが必要とする前提 state の契約 - 構文検証 —
node --checkの成功を確認 - 実行承認の確認
- 通常の画面:タブ番号とシナリオのパスを確認してから実行
- Google/OAuth/管理者/決済/既存の Chrome Beta プロファイルのセッション維持を伴う作業:
./e2e.sh runの実行前に、必ずユーザーに実際の実行を承認するか再確認
- 実行 —
./e2e.sh run --tab N 시나리오/경로 - 自動修正ループ — 失敗した場合は、以下の自動修正ループに進む
- 結果報告
create モード
- 入力ソースの判別
- 自然言語のリクエスト →
references/시나리오-생성-패턴.md+references/코드패턴.mdを参照 - codegen の記録 →
references/변환규칙.md+references/코드패턴.mdを参照
- 自然言語のリクエスト →
- 情報の確認 — シナリオ名(韓国語)、保存先のカテゴリーフォルダー(韓国語の業務ドメイン)、カテゴリー内の連番(
NN-)、このシナリオが残す state 契約、このシナリオが必要とする先行 state 契約 - シナリオの作成
- 必須の変換項目(codegen 入力の場合):
chromium.launch()→connect()(lib/connect.js を使用)page.goto('/path')→ 現在のタブの状態を確認してから条件付きで移動- 機密性の高いセッションの場合、またはユーザーの承認がない場合は自動移動しない
- 機密性の低いセッションで、ユーザーの承認を得ている場合に限り
page.goto()
browser.close()/context.close()を削除page.pause()を削除- ダイアログハンドラーを追加(
setDialogHandlerで置き換え、finally で必ず元に戻す) - try-catch-finally + exitCode パターンでラップ(
process.exit(0)による固定終了は禁止) - 絵文字ログを追加
waitForTimeoutを最小限にする → 条件待ちに変換- ポップアップ(
waitForEvent('popup'))→ 閉じたことの検知にはwaitForEvent('close')を使用
- 必須の変換項目(codegen 入力の場合):
- 構文の検証 —
node --checkが通ることを確認 - 保存先の報告 —
e2e/시나리오/{한글카테고리}/{NN}-{시나리오명}.js- カテゴリーフォルダーがない場合は自動作成
- 既存のフラット構造のファイルはすぐに一括移動せず、修正・再作成時にのみ新しいルールへ段階的に移行
- 移行時は、既存のパスと新しいパスを完了報告に明記
run モード
- シナリオの選択
cd e2e && ./e2e.sh list - 実行承認の確認
- ログイン済みの実タブ/固定プロファイルのセッション維持が重要なシナリオでは、実行前にユーザーの承認が必須
- 実行
cd e2e && ./e2e.sh run --tab N 시나리오/경로 - 自動修正ループ — 失敗した場合は、以下の自動修正ループを実行
- 結果の報告
自動修正ループ(最大 3 回)
シナリオの実行結果が ❌ エラー: の場合は、スクリプトを直接修正して再実行します。
単にデバッグ方法を案内するだけでなく、原因を特定し、シナリオファイルを修正して再実行するところまでがこのスキルの責任です。
自動修正中にセレクター/DOM/フレームワークとのインタラクションの問題が疑われる場合は、
peach-e2e-browse の意思決定ツリーを適用し、現在のタブで DOM とインタラクション方法を再確認します。
確認したセレクターとイベントパターンをシナリオコードに反映してから再実行します。
詳細:references/자동수정-판단트리.md を参照
判断基準
| エラーの種類 | 対処方法 |
|---|---|
| セレクターの不一致(timeout、locator not found) | agent-browser eval で実際の DOM を確認 → シナリオのセレクターを修正 |
dialog の自動クローズ(기록하지 못했습니다、dismiss) | daemon の残留を確認してから kill → setDialogHandler パターンが適用されていない場合は修正 |
popup waitForEvent('close') エラー | Promise.race + .catch(() => {}) パターンを適用 |
URL パターンの不一致(waitForURL timeout) | 実際の遷移先 URL を確認 → パターンを修正 |
タイミングの問題(waitForTimeout の直後に失敗) | 固定待機 → waitForEvent または waitForFunction によるイベントベースの待機に置き換え |
Target page, context or browser has been closed | ポップアップ/タブが想定より早く閉じた → .catch(() => {}) または closeTarget オプションを追加 |
| navigation timeout(AJAX submit) | waitForNavigation を削除するか、waitForURL に置き換え |
| サーバーエラー(500、ネットワークエラー) | 自動修正不可 → ユーザーに報告して中断 |
ループの手順
1. 에러 메시지 파싱 → 유형 판별
2. agent-browser eval로 실제 DOM/URL 확인
3. 시나리오 스크립트 수정
4. 재실행
5. 여전히 실패? → 1로 돌아감 (최대 3회)
6. 3회 실패 → 진단 패키지 출력 → 사용자에게 보고 → peach-e2e-browse 안내
3 回失敗した場合の診断パッケージの出力
自動修正が 3 回すべて失敗すると、anchoring(誤答の蓄積による偏り)リスクが高まります。 同じコンテキストで無理に 4 回目・5 回目へと増やさず、新しい会話ウィンドウでクリーンなコンテキストからデバッグできるよう、診断パッケージを構造化して出力します。
出力形式
🩺 자동수정 3회 실패 — 진단 패키지
## 시나리오
- 파일: <시나리오 파일 절대경로>
- 대상 URL: <실행 대상 URL>
- 탭 ID: <E2E_TAB_ID>
## 시도 이력 (3회)
| 회차 | 추정 원인 | 적용한 수정 | 재실행 결과 |
|------|----------|------------|-----------|
| 1 | <유형> | <변경 요약> | <에러 메시지 첫 줄> |
| 2 | <유형> | <변경 요약> | <에러 메시지 첫 줄> |
| 3 | <유형> | <변경 요약> | <에러 메시지 첫 줄> |
## 마지막 실패 컨텍스트
- 마지막 에러 메시지 (전문)
- 실패 시점 DOM 스냅샷 또는 셀렉터 평가 결과
- 실패 시점 URL
## 추정 막힌 지점
<3회 모두 같은 유형이면 그 유형, 다르면 "다중 원인 의심" 명시>
## 사용자 다음 액션 가이드
1. 새 대화창에서 위 패키지를 첨부하여 디버깅 진행
2. peach-e2e-browse로 현재 탭 상태 직접 확인
3. 시나리오 의도 자체 재검토 필요 가능성
原則
- コンテキストを新しく開始できるように、絶対パス・エラー全文・すべての試行履歴をインラインですべて含めます(要約禁止)
- 4 回目・5 回目へ自動的に拡張しません(Bounded Autonomy:提案可能な範囲であり、ユーザーが決定)
- ユーザーが同じセッションで続けることを希望する場合は追加で試行しますが、anchoring のリスクについて一度案内します
修正後の再実行
E2E_TAB_ID=<id> ./e2e.sh run '시나리오/대상.js'
dialog 関連のエラーの場合、実行前に必ず daemon の残留を確認します:
lsof -iTCP:9222 -sTCP:ESTABLISHED -n -P | awk '/node/{print $2}' | xargs kill -9 2>/dev/null
セレクターのデバッグ(agent-browser eval を優先)
# CDP 연결 (1회)
agent-browser connect 9222
# 현재 URL 확인
agent-browser eval "location.href"
# 셀렉터 존재 여부
agent-browser eval "document.querySelector('.target') !== null"
# 버튼 목록
agent-browser eval "JSON.stringify(Array.from(document.querySelectorAll('button')).map(function(b){return b.innerText}))"
# 요소 개수
agent-browser eval "document.querySelectorAll('tr').length"
iframe 内部のデバッグは agent-browser では不可 → playwright-cli にフォールバック:
./e2e/pwc.sh eval "document.querySelector('iframe[src*=target]').contentDocument.querySelector('#element').innerText"
native dialog シナリオのルール
window.alert/confirmの JS monkey-patch は動作しません — Playwright CDP による自動 dismiss が先に実行されます。使用禁止。- native dialog の処理には、必ずCDP レイヤーの handler(
page.on('dialog', handler))を使用します。 connect.jsのsetDialogHandler(page, prevHandler, newHandler)ユーティリティで handler を置き換え、finally で必ず元に戻します。page.on('dialog')を複数登録するとすべて実行され、競合("already handled")が発生します — 置き換えパターンが必須です。- popup(
waitForEvent('popup'))はconnect.jsを経由しないため、別途 handler の登録が必要です。 process.exit(0)による固定終了は禁止 →try/catch/finally + exitCodeパターンを使用します。- ページ状態に依存するロジックでは、クリック前に明示的に待機します。
- dialog の待機には固定の
waitForTimeoutではなく、page.waitForEvent('dialog')によるイベントベースの方法を使用します。
詳細:peach-e2e-browse/references/native-dialog-주의사항.md を参照
外部サービスへの遷移
外部サイト(Google、Gmail など)への遷移には、load + 2초 지연 + 직접 이동 fallback パターンを使用します。
詳細:peach-e2e-browse/references/외부서비스-링크전환-패턴.md を参照
タブ選択ルール
- 通常実行:
--tab N(高速実行用) - デバッグ/再現/障害分析:
E2E_TAB_IDを優先(インデックスのずれを防止)
# targetId 조회
curl -s http://127.0.0.1:9222/json | jq -r '.[] | select(.type=="page" and (.url|startswith("chrome")|not)) | [.id,.title,.url] | @tsv'
# targetId로 실행
cd e2e && E2E_TAB_ID=<targetId> ./e2e.sh run '시나리오/대상.js'
詳細:peach-e2e-browse/references/탭-선택-패턴.mdを参照
単体と統合の責任範囲
- 単体シナリオ(peach-e2e-scenario):1つの画面/1つのアクションの動作が正しいかを検証します。開始データを自分で用意し、独立して実行でき、再利用可能です。
- 統合 suite(peach-e2e-suite):複数の単体シナリオをビジネスライフサイクル単位で組み合わせ、ユーザーフローが最後まで完了するかを検証します。単体の.jsは変更しません。
同じフローが単体シナリオで繰り返される場合は、統合 suite の組み合わせとして表現します。
単体シナリオの作成原則
単体シナリオは、suiteで組み合わせて利用できる再利用可能な部品です。以下の原則に従います。
- 単一責任:1つの画面、または1つのビジネスアクションのみを検証します。2つ以上の主要なフローを1つのシナリオにまとめません。
- 開始データを自分で用意:「既存のデータがある」と仮定しません。シナリオ自体が必要な開始状態を作成します(または明示的な入力として受け取ります)。
- 独立して実行可能:他のシナリオの実行結果に依存しません。どの順序で実行しても同じ結果になります。
- 再利用可能:suiteで単体の.jsを変更せず、そのまま使用できるように作成します。外部から注入する値がある場合は、明示的な入力(環境変数/state.json)として受け取ります。
- 失敗の分離:1つの単体シナリオが失敗しても、他の単体シナリオの実行に影響しません。クリーンアップの責任を明記します。
保存先はe2e/시나리오/{한글카테고리}/{NN}-{시나리오명}.jsの形式に従います。
詳細:peach-e2e-suite/references/suite-scenario-파일구조.mdを参照
E2E_BASEパターン(ドメイン環境変数)
すべてのシナリオファイルの最上部で、E2E_BASE環境変数のパターンを使用します。ドメインのハードコーディングは、複数環境での実行を妨げるアンチパターンです。
// 시나리오 파일 최상단 필수
const BASE = process.env.E2E_BASE || 'http://local.example.com';
実行時:
# 로컬 (기본값)
./e2e.sh run --tab N 시나리오/경로.js
# 개발서버 지정
E2E_BASE=https://dev.example.com ./e2e.sh run --tab N 시나리오/경로.js
DBを使用しない設計(役割分担の原則)
シナリオの.jsファイルは、UIの操作とUI結果の検証のみを担当します。構造上、DBに接続できないため、シナリオ内では読み取り・書き込みのどちらも試みません。
- 構造上の制約:e2e.shの実行環境にあるNODE_PATHにはmysql/postgresクライアントが含まれていないため、シナリオでDBライブラリ(
mysql、dbQueryなど)をrequireすると、ENOENTで失敗します。DB接続情報をシナリオに含めると、環境の移植性もゼロになります。 - そのため、DBが必要なすべての操作はシナリオの外(suite fixture Step、
peach-db-queryスキル、管理画面のアクション、TDD API)に分離します。 - 上記の境界に違反するシナリオの依頼(例:「このシナリオ内でINSERTして事前条件を作ってください」)を受けた場合は、すぐにユーザーに伝え、以下の回避策のいずれかを先に提案してから、同意を得ます。
| 目的 | シナリオ内での試行(不可) | 回避策 |
|---|---|---|
| PKの抽出 | SELECT pk FROM table WHERE name='...' | 管理画面のlist DOMにあるinput.pk_check[request_name]属性 |
| 保存の検証 | SELECT column FROM table WHERE pk=N | 画面を再読み込みして、入力要素の.valueを確認 |
| DBの事前条件 | INSERT INTO ... | suite fixture Stepまたはpeach-db-queryスキル |
| 状態の強制変更 | UPDATE ... SET status=... | suite fixture Stepまたは管理画面のアクションをシナリオに追加 |
| 残存データの削除 | DELETE FROM ... | suite fixture StepまたはhardDelete TDD APIの呼び出し |
| DBの整合性確認 | — | suite MDの「DB検証(任意)」セクション+peach-db-queryスキル(SELECT) |
PK抽出の標準パターン
登録後に管理画面のlist DOMからPKを抽出する標準パターン:
await page.evaluate((name) => { $('#page_keyword').val(name); searchFormSubmit(); }, TEST_NAME);
await page.waitForTimeout(1500);
const N = await page.evaluate((name) => {
const el = document.getElementById('list_inner_html') || document.body;
const cb = el.querySelector(`input.pk_check[request_name="${name}"]`);
return cb ? parseInt(cb.value, 10) : null;
}, TEST_NAME);
if (!N || N <= 0) throw new Error('PK 추출 실패');
前提:管理画面のlistにinput.pk_checkチェックボックスがあり、request_name属性に名前、valueにPKが設定されていること。
主要な原則
- 必ず
lib/connect.jsのconnect()関数を使用します。 - 実行には必ず
nodeを使用します —bunではCDP WebSocketに接続できません。 - 対象プロジェクトのDOM構造を把握し、適切なセレクター戦略を適用します。
- モーダルの処理:フレームワークごとのパターンを参照します(iframeとPortal/Teleport)。
- dialog handlerはグローバルではなく、条件付きで設定します。
- 外部サービスへのリンク遷移では、
click()を1行実行するのではなく、フォールバックURLに到達するルールを適用します。 - 保存直後に
node --checkで構文を検証する必要があります。 - タブが未確認の状態や、機密セッションを扱う場合は分析のみを行い、実行はユーザーの確認後に進めます。
参照ドキュメント
| ドキュメント | 用途 | 読み込み条件 |
|---|---|---|
references/코드패턴.md | シナリオの基本構造(IIFE、exitCode、絵文字) | create、auto |
references/변환규칙.md | codegenからCDPへの変換ルール | codegenの入力時 |
references/프레임워크-대응.md | レガシー/モダンフレームワークの分岐 | create、auto |
references/시나리오-생성-패턴.md | 既存コードを参考にした生成ガイド | create、auto |
references/validation-통과-패턴.md | form validationを回避するパターン | create、auto |
references/자동수정-판단트리.md | エラーの種類ごとの自動修正戦略 | run、autoの失敗時 |
references/daemon-잔류-대응.md | CDP daemonの問題解決 | dialogエラー時 |
references/dialog-handler-패턴.md | native dialogの処理メカニズム | dialogシナリオ |