record-walkthrough
Skill5 starsChanged 54 days agoMITView on GitHub
Record a website walkthrough video with auto-zoom on clicks. Use when the user asks for a walkthrough, when a PR, MR, or issue needs a recording of a web flow, or on /record-walkthrough.
- Installs packages
In this repository15 other files it gives its agents.
- AGENTS.mdAGENTS.md
- agents-mdSkill
- agents-memorySkill
- agentsview-extractSkill
- agentsview-resumeSkill
- backfill-unit-testsSkill
- dotnet-upgradeSkill
- github-epicSkill
- gitlab-epicSkill
- miseSkill
- pr-workflowSkill
- setup-agent-ready-repoSkill
- tech-leadSkill
- tidy-commitsSkill
- write-e2e-testsSkill
The file
We split this skill into the rules it gives an agent
4 rules. About 0 are common, 1 is distinctive, and 3 are very specific to this project.
≈0
Common · estimate
Many files like this have a rule of this kind.
≈1
Distinctive · estimate
This author's own choices. Worth a look.
3
Very specific
Tied to their project's names, files or tools. Probably skip.
- Common
- Distinctive
- Very specific
- Very specific: line 25
Check first with node scripts/record.mjs --check-prereqs.
- Distinctive: line 27
When missing, ask the user for confirmation before installing:
- Very specific: line 68
Prefer role + name over selector: a caption falls back to the raw selector text (Click nav a[href…]) when a step has no name, label or …
- Very specific: line 119
Leave this step when the video, demo.clicks.jsonl, and demo.zooms.json exist and the zoom file has "status": "ok" with one region per click …
≈ “Common” is an estimate: at least 1 in 5 of the 350,495 skill files we read have a rule of the same kind, not the same words. “Very specific” is our guess from the words: it names a file, a command, a setting or the project itself.
Files
record-walkthrough
Record a website walkthrough with Playwright.
Scripts live in scripts/ next to this file.
Prerequisites
- Node.js or Bun (
bun scripts/record.mjsworks too; under Yarn PnP, runyarn node scripts/record.mjs) - Playwright 1.59+ with Chromium (global npm/pnpm/Yarn Classic/Bun, cwd, or
PLAYWRIGHT_DIR) ffmpegon PATH for auto-zoom (both.webmand.mp4), and whenever.mp4output is requested
Check first with node scripts/record.mjs --check-prereqs. Exit 0 means recording works, not that ffmpeg is present: read the ffmpeg: line. Where it says missing, check command -v ffmpeg and mise ls ffmpeg before installing, since a mise-managed ffmpeg can exist yet be off this shell's PATH.
When missing, ask the user for confirmation before installing:
- Playwright: recommend
npm i -g playwright && npx playwright install chromium(global avoids repo pollution; or-D). ffmpeg(for.mp4or auto-zoom): recommendmise use -g ffmpeg(or platform managerbrew/apt/winget, or installingmise). Or ask if the user prefers degrading to raw.webmwithout auto-zoom.
Workflow
- Scenario. A spoken brief is enough. Behind a sign-in: save state once
with
npx playwright open --save-storage=auth.json <url>, then explore and record through that state — the anonymous page is only ever a login screen.auth.expectmust be visible only when signed in, and record with--storage-state auth.json, or pass--sign-into sign in by hand at the start of the recording instead, or--connectto record a window already signed in on, so a site you cannot know ahead needs one sign-in for both exploring and recording. Seereferences/auth.md. Explore the live page and writescenario.jsonwith the start URL and every click, in order, taken from the user's brief and the live page, in the shape below. Each click needs a locator (role+name,selector,text, orlabel). Discover locators withplaywright-cli snapshotwhen that command is on PATH; otherwise a Playwright script. Reuse a cuawright-web run only when one already exists for this flow — the skill launches a fresh, stateless browser each time and cannot carry a signed-in session past a login wall. Leave this step when the file on disk starts at the brief's URL and has one step per action the brief names, in its order and with its values.
{
"url": "https://example.com",
"captionLocale": "en",
"auth": { "expect": { "role": "button", "name": "Account" } },
"steps": [
{ "action": "wait", "ms": 800 },
{ "action": "click", "role": "link", "name": "More information" },
{ "action": "press", "keys": "Control+k" },
{ "action": "scroll", "direction": "down", "amount": 500 },
{ "action": "type", "role": "textbox", "name": "Search", "text": "SSH", "pause": 1800 },
{ "action": "select", "role": "combobox", "name": "Language", "value": "English" }
]
}Prefer role + name over selector: a caption falls back to the raw
selector text (Click nav a[href…]) when a step has no name, label or text, so
give a selector step its own caption. On localized sites, name must match
the page's rendered text; within dynamic search results or lists where links share
names, use a scoped selector (e.g. .result a) to avoid false matches. A click waits up to 15 seconds for
its target to be visible (timeout changes that per step). To wait for
something without touching it, such as the row a submit just added, use
{ "action": "expect", "text": "Saved" }; state may be "hidden". To scroll
the page or a viewport without requiring element focus, use
{ "action": "scroll", "direction": "down", "amount": 500 } (direction may be "down", "up", "left", or "right"). A
wait, expect, scroll or goto shows a caption only when given one, and holds it
across reloads, so say what the viewer is watching happen. When a
step fails the error names it (step 3 of 5 {...}) and <out>.failure.png and
<out>.failure.aria.txt show what the page looked like. When the
flow creates data, do it once while exploring and note where it lands (a later
page, a filter, below the fold) so the last step targets the right place.
A secret a step types goes in "textEnv": "VAR" rather than text, and a
field the page does not mark as a password (an API key) gets
"sensitive": true so its caption shows dots.
Pointer, captions and auto-zoom are on; effects turns any off. Set
captionLocale to the language of the conversation asking for the
recording, or, for evidence on an issue or request, to the language the
repo writes those in. When the address itself is the evidence (a redirect
or reload loop), set "statusBar": true, or { "label": "Before" }, to
draw it live across the top. See references/effects.md.
For mobile/tablet, set scenario.device to "phone" (newest iPhone Pro) or
"tablet" (iPad Mini, narrower than iPad Pro so a collapsed nav still shows
— see DEVICE_PRESET_ALIASES in record.mjs) rather than shrinking
viewport. Also accepts an exact Playwright device name. A touch device
taps click/type/select targets, so touch-only handlers fire;
dblclick and a non-left button still use the mouse.
scenario.viewport/--width/--height still override it.
scenario.locale (a BCP 47 tag) sets the browser language; Playwright
otherwise starts in en-US, so set it whenever the site is localized.
"ignoreHTTPSErrors": true accepts a self-signed local certificate.
- Record. From a directory that can
import('playwright'):
node scripts/record.mjs --scenario scenario.json --out demo.mp4
# Attach to an existing browser window (scenario.url omitted; waits up to 3m for auth.expect):
node scripts/record.mjs --connect http://127.0.0.1:9222 --scenario scenario.json --out demo.mp4The --out extension picks the container. Default to .mp4 (smallest, and
plays in every browser and PR preview); use .webm only without ffmpeg or
when the user asks for it.
Leave this step when the video, demo.clicks.jsonl, and demo.zooms.json
exist and the zoom file has "status": "ok" with one region per click
cluster. Without ffmpeg, output is raw .webm without auto-zoom (pointer and
click echo are still included), and the zoom file still lists the clusters.
A passing zoom file says nothing about the picture. Before handing back, pull a
frame from the last step (ffmpeg -sseof -1 -i demo.mp4 -frames:v 1 last.png)
and look at it: the result the flow was meant to end on, such as the new row,
must be in frame, and a page you scrolled must have reached its end.
- Hand back. Give the user the video path.
Defaults
Viewport is 1280×720 CSS pixels (deviceScaleFactor 1). Override with
scenario.viewport or --width/--height (even numbers; odd values
round up). After each click, pause 2500ms; override with
scenario.pauseMs, --pause-ms, or per-step pause. Each zoom is 1.5×,
lands on the click 500ms after it starts, and holds until the step's
typing or choosing ends plus 800ms (at least 1500ms after the click).
At the default pause the view zooms out between steps; a click whose zoom
would start under 800ms after the last one ends keeps the view in and pans
to it instead, so every click stays in frame. A click near an edge is not
centred: the crop stops at the frame. Flags: record.mjs --help.
Does it work?
Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.
No reviews yet
People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.
- It worked
- Partly
- It didn't
Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.
Your trail
Files you open will collect here, so you can find them again.
Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.
Now do this for your own.
Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.

