Agent Skills: Webwright

Use when the user needs to automate a real web task through a browser — filling forms, applying filters, extracting data, clicking through multi-step flows, or building reusable web automation scripts. Use when a task requires interacting with a live website where the agent must navigate, select, verify, and capture evidence. Do NOT use for API calls, static scraping, or tasks that don't need a real browser.

UncategorizedID: dbmcco/claude-agent-toolkit/webwright

Install this agent skill to your local

pnpm dlx add-skill https://github.com/dbmcco/claude-agent-toolkit/tree/HEAD/skills/webwright

Skill Files

Browse the full folder contents for webwright.

Download Skill

Loading file tree…

skills/webwright/SKILL.md

Skill Metadata

Name
webwright
Description
Use when the user needs to automate a real web task through a browser — filling forms, applying filters, extracting data, clicking through multi-step flows, or building reusable web automation scripts. Use when a task requires interacting with a live website where the agent must navigate, select, verify, and capture evidence. Do NOT use for API calls, static scraping, or tasks that don't need a real browser.

Webwright

Overview

Webwright is a code-as-action browser automation approach. Instead of clicking one button at a time, the agent writes full Playwright scripts, runs them, inspects screenshots and output, then iterates. The browser is disposable — the code and logs are the persistent artifact.

When to Use Webwright

Use Webwright when:

  • Automating a web workflow (search, filter, form-fill, multi-step flow)
  • Extracting structured data from a site that requires interaction
  • Building a reusable, parameterized web automation CLI tool
  • The user explicitly asks to "automate a website", "fill out a form", "search and extract", "build a web scraper", etc.
  • A task needs screenshot evidence that specific filters/selections were applied

Do NOT use Webwright when:

  • The target has a REST API — call the API directly instead
  • The task is static HTML scraping with no interaction — use httpx + beautifulsoup
  • The task only needs a web search — use Perplexity skill
  • The task is browser testing (e.g., testing our own apps) — write standard Playwright tests
  • The user just needs to read a webpage — use curl/httpx to fetch it

Decision Flowchart

Need to interact with a website?
├─ Is there an API? → Use the API directly
├─ Just fetching static content? → httpx / curl
├─ Just searching the web? → Perplexity skill
├─ Testing our own app? → Standard Playwright tests
└─ Need to drive a real browser (forms, filters, clicks, multi-step)?
   └─ → Webwright

Prerequisites (one-time)

pip install playwright && playwright install firefox

Firefox is preferred over Chromium — some sites (Akamai-protected, Cloudflare) reject Playwright Chromium with TLS/H2 fingerprinting but load cleanly under Firefox.

No API keys required. The agent itself provides visual verification (no external LLM calls).

Modes

  • One-shot (default): final_script.py solves the task for the literal values provided.
  • CLI tool (/webwright:craft): final_script.py is a reusable, parameterized CLI with argparse. Use when the user says "make it reusable", "parameterize", "I want to run this again with different values".

Workspace Contract

Every Webwright run follows this structure:

WORKSPACE_DIR/               # e.g., outputs/<task_id>/
├── plan.md                  # Critical points checklist
├── screenshots/             # Exploration screenshots
├── final_script.py          # The automation script
└── final_runs/
    ├── run_001/
    │   ├── final_script.py
    │   ├── final_script_log.txt
    │   └── screenshots/
    │       ├── final_execution_1_open_page.png
    │       ├── final_execution_2_apply_filter.png
    │       └── final_execution_3_results.png
    └── run_002/             # If run_001 failed verification
        └── ...

Rules:

  • Work only inside WORKSPACE_DIR
  • Each clean execution gets its own final_runs/run_<id>/ (incrementing integer)
  • Viewport is always 1280x1800. Never use full_page=True screenshots
  • Browser is headless Firefox, launched fresh each run — no persistent session

Workflow

1. Plan

Parse the task into critical points (CPs) — every constraint, filter, sort, selection, or datum. Write to plan.md:

# Task
<task description>

# Critical Points
- [ ] CP1: <constraint>
- [ ] CP2: <constraint>

Each CP must be independently verifiable from a screenshot or log line.

2. Explore

Run scratch Playwright scripts to discover selectors and confirm controls exist. Use the browser launch skeleton from reference/playwright_patterns.md. Print ARIA snapshots, URLs, titles. Save exploration screenshots to WORKSPACE_DIR/screenshots/.

3. Author final_script.py

Place in final_runs/run_<id>/. Instrument it:

import asyncio
from pathlib import Path
from playwright.async_api import async_playwright

RUN_DIR = Path(__file__).parent
SCREENSHOTS = RUN_DIR / "screenshots"
SCREENSHOTS.mkdir(parents=True, exist_ok=True)
LOG = RUN_DIR / "final_script_log.txt"
LOG.write_text("")  # reset

def log(step: int, msg: str) -> None:
    line = f"step {step} action: {msg}\n"
    LOG.open("a").write(line)
    print(line, end="")

async def main():
    async with async_playwright() as p:
        browser = await p.firefox.launch(headless=True)
        ctx = await browser.new_context(viewport={"width": 1280, "height": 1800})
        page = await ctx.new_page()

        await page.goto("<URL>", wait_until="domcontentloaded")
        await page.screenshot(path=str(SCREENSHOTS / "final_execution_1_open.png"))
        log(1, "opened start page")

        # ... apply filters, click buttons, extract data ...
        # One screenshot + log line per critical point

        final_value = "<extracted result>"
        LOG.open("a").write(f"\nFINAL_RESPONSE: {final_value}\n")
        await browser.close()

asyncio.run(main())

4. Execute and Verify

Run the script. Then verify every CP against the screenshots and log:

  1. Identify screenshot/log evidence for each CP
  2. Read each PNG and confirm evidence is unambiguous
  3. Tick the CP only when evidence is concrete
  4. If any CP fails → diagnose, fix, re-run in run_<id+1>/

5. Report

Report the final result to the user with evidence summary.

Hard Rules

  • Use stable selectors (get_by_role, aria-label) — never brittle CSS classes
  • If a site exposes a dedicated control for a requirement, you MUST use it (not search-box queries)
  • Numeric/date/quantity constraints are exact — wider buckets are failures
  • Ranking language ("cheapest", "best-selling") must use the site's actual sort/filter
  • If a selected state becomes hidden (closed drawer, collapsed accordion), reopen it before capturing
  • Prefer interactive form filling over deep-link URLs — deep links silently drop parameters
  • Do not install extra packages — playwright, httpx, etc. are already available

Reference Files

  • reference/playwright_patterns.md — browser launch skeleton, ARIA snapshot recipes, screenshot naming, targeting patterns
  • reference/workflow.md — detailed plan → explore → final → verify walkthrough
  • reference/cli_tool_mode.md — contract for parameterized CLI tool mode

Slash Commands

  • /webwright:run <task> — one-shot mode
  • /webwright:craft <task> — reusable CLI tool mode