Skip to content
Back to skills

Record A Demo

ASecurity

Records a polished, human-paced video walkthrough of a finished, already-QA'd feature via Playwright's screencast API — for stakeholder review, sign-off, or sharing. This is a presentation artifact, not a testing pass. Use when asked to demo, walk through, or record a video of finished work — never for a feature that hasn't already passed verification.

  • 2 stars
  • 0 votes
  • 0 copies
  • 0 views
  • Added October 2, 2026
ai-agentsgotestingapi

Works with

  • cursor
  • cli
  • api

Security analysis

A100/100

Pro scans all 2 files and shows the line behind each finding

Scanned October 2, 2026

npx -y skills add Ghosteken/agent-harness --skill record-a-demo --agent claude-code

Installs into .claude/skills of the current project.

Are you the author of Record A Demo?

Add the live security badge to your README. It updates with every re-scan.

Security grade badge for Record A Demo
[![Security: A — Skills Directory](https://www.skillsdirectory.com/api/skills/ghosteken-record-a-demo/badge)](https://www.skillsdirectory.com/skills/ghosteken-record-a-demo)

More formats (shields.io, HTML) on the badges page. Keep it an A: scan every change in CI with Pro.

Download with Pro
SKILL.md
---
name: record-a-demo
description: Records a polished, human-paced video walkthrough of a finished, already-QA'd feature via Playwright's screencast API — for stakeholder review, sign-off, or sharing. This is a presentation artifact, not a testing pass. Use when asked to demo, walk through, or record a video of finished work — never for a feature that hasn't already passed verification.
---

# Record a Demo

## Overview

Produces a `.webm` video of working software for people to watch and sign off on — not a QA artifact. The premise going in is that the feature already works and was already verified (via `quality-assurance` or `playwright-e2e-testing`); this skill's only job is to show it working, at a natural pace, with clear visual annotation of what's happening. It does not hunt bugs, narrate a checklist, or produce a verdict.

## When to Use

- Asked to demo, walk through, or record finished work end-to-end
- Presenting a feature to stakeholders for review or sign-off
- Sharing a completed flow with colleagues
- NOT when the feature hasn't been verified yet — run `quality-assurance` (or check `playwright-e2e-testing` coverage) first; this skill assumes correctness, it doesn't establish it
- NOT for a testing artifact of any kind — a demo that surfaces a real regression is a stop-and-report situation (see Step 5), not a bug-hunting session

## Process

### 1. Resolve what to demo

In priority order: explicit instructions for specific flows, a named source (test plan, spec, curated scenario list) to extract scenarios from, or — if asked to demo "what you just worked on" — the feature context from the current session.

### 2. Draft and confirm a short outline

Write a 3-6 step outline and confirm it with the user before recording anything. This is the one checkpoint in the whole process — cheap insurance the demo matches intent, and the reason not to need further check-ins once it's approved.

### 3. Rehearse the flow before recording it

Drive the actual flow once, live, before writing any recording script: confirm the entry URL, auth steps, and exact locators; identify dynamic/async content and what it actually needs to wait on; note working selectors and element positions for later label placement. Recording a flow you haven't actually driven yet is how a demo ends up narrating a wait condition that doesn't hold or a locator that doesn't resolve.

### 4. Record

Prefer Playwright's built-in action annotation over hand-rolled cursor code: `page.screencast.start({ path, size })`, then `screencast.showActions({ cursor: 'pointer' })` for automatic cursor/click visualization during the recording. Reach for a custom synthetic-cursor script (DOM cursor injected via `page.addInitScript`, driven by a `glide()`/`show()` helper — see `patterns.md`) only when the built-in annotation doesn't give the visual result the outline calls for (e.g. precise custom label placement tied to element bounding boxes).

Either way:
- Load and let the entry screen fully settle **before** calling `screencast.start()` — starting on a half-painted page means the recording opens fighting its own load state
- Put visible motion on screen within the first ~300-500ms after `start()` — a rendered-but-motionless opening frame reads as a frozen screenshot to a viewer, which is the single most common way a demo opens poorly
- Type with `pressSequentially({ delay: ~60 })` when the typing itself is part of what's being shown; use `fill` when it isn't — cranking the delay higher doesn't read as more "human," it just reads as slow
- Target ~800-1200ms between ordinary steps, ~1500-2500ms at key beats, so a viewer has time to actually absorb the new screen
- Annotate sparingly with small, colorful, contextual labels (`showOverlay`) positioned at the actual target's bounding box — never full-page cards (`showChapter`) mid-flow, which hard-interrupt the sense of motion; reserve `showChapter` for a title card on a cold open at most
- Encode state in label color where a lifecycle applies — neutral/in-progress vs. a success color (e.g. green with a checkmark) on completion is the highest-leverage single annotation, especially for anything that streams (see below)

For a throwaway/rough clip where sign-off isn't the goal, driving the flow live with recording on (no authored script) is an acceptable lighter alternative — just don't deliver that version for sign-off.

### 5. Handle streaming or long-running UI correctly

An SSE/WebSocket-driven UI (streaming chat replies, a live agent loop) needs to record in full — showing the complete response is the point, not a truncated stand-in. Two specific traps:

- **Never gate on network-idle.** A live streaming connection stays open, so `waitForLoadState('networkidle')` (or `waitUntil: 'networkidle'`) blocks until it times out — it will never arrive on its own.
- **Advance on a real completion signal, not a fixed sleep.** Poll for the actual DOM signal that the stream finished (e.g. the response container's text length holding steady across consecutive polls, past its pre-send size) with a generously-sized timeout for a long generation — not a guessed fixed delay, and not a "send button re-enabled" check (it may not reflect stream state reliably).

### 6. Verify before delivering — you can't casually watch a webm

Review the key-beat screenshots captured along the way: cursor/annotation visible where expected, each beat actually reached the expected state, no error screens or incomplete loads. If something's visually wrong, re-record — never deliver a take you haven't confirmed. If you need to inspect the actual video content beyond what beat screenshots capture, use the Playwright-bundled ffmpeg (ships alongside the browser binaries; locate it rather than assuming a fixed path, since it differs by OS/environment) to pull a specific frame to a PNG rather than trying to "watch" the file.

### 7. Handle a failed take correctly

A flaky, transient failure (a missed wait, a stale locator, bad timing) is a recording problem — silently re-record. A real regression (the feature is actually broken) is a stop-immediately situation: report exactly what failed, and do not deliver a video that misrepresents broken work as working. This skill never fixes the implementation itself — that's a hand-off, not this skill's job.

### 8. Deliver

Save the final `.webm` (plus its key-beat screenshots) to `demos/<feature-slug>/` under the project's external output location (see `references/external-output-paths.md`) — outside the project's own repo. Tell the user the full path(s), which scenarios were demoed, and that it's ready for sign-off or change requests — not a verdict.

## Common Rationalizations

| Rationalization | Reality |
|---|---|
| "I found a bug, let me note it in the video" | This skill assumes the feature already passed QA — a real regression found here is a stop-and-report situation, not something to narrate into the recording. Run `quality-assurance` first if that assumption doesn't actually hold. |
| "I'll skip the rehearsal, I already know this flow" | An unrehearsed recording script is exactly how a demo ends up narrating a wait condition that doesn't hold — rehearse live before scripting, every time. |
| "A frozen half-second at the open is fine, it's brief" | It's the single most common way a demo reads as broken before anything's even happened — lead with visible motion, not a settled static frame. |
| "I'll wait for network-idle so the streaming reply is fully done before continuing" | A live stream keeps the connection open — network-idle never arrives, and the wait times out. Poll for an actual completion signal instead. |
| "More typing delay looks more human" | Natural pacing comes from deliberate pauses between actions, not slower typing — a higher `pressSequentially` delay just reads as sluggish. |
| "I'll hand-roll a synthetic cursor, that's how it's always done" | Playwright's `screencast.showActions({ cursor: 'pointer' })` already provides this built in — reach for a custom cursor script only when the built-in doesn't give the specific visual the outline needs. |
| "One big full-page overlay explains the whole step" | `showChapter` hard-interrupts the sense of motion — small contextual `showOverlay` labels at the actual target keep the flow feeling live. |

## Red Flags

- A demo recorded for a feature that hasn't actually passed `quality-assurance` (or equivalent) yet
- A real regression narrated into the video instead of triggering a stop-and-report
- A recording script written without first rehearsing the flow live
- `screencast.start()` called before the entry screen has settled, or with no motion in the first ~300-500ms after
- `waitForLoadState('networkidle')` (or equivalent) used to gate a streaming/long-lived-connection UI
- A fixed sleep used to "wait out" a stream instead of polling a real completion signal
- `showChapter` used mid-flow as a repeated interruption instead of only at a cold open
- A take delivered without reviewing its key-beat screenshots first
- Output saved as anything other than `.webm`, or saved inside the project's own repo instead of the external output location

## Verification

- [ ] The feature was already verified (QA'd) before this skill started — this skill didn't establish correctness itself
- [ ] A 3-6 step outline was drafted and confirmed with the user before recording
- [ ] The flow was rehearsed live before any recording script was written
- [ ] The recording opens with visible motion in the first ~300-500ms, not a settled static frame
- [ ] Any streaming/long-lived-connection UI advanced on a real completion signal, never on network-idle or a fixed sleep
- [ ] Annotations are small and contextual (`showOverlay`), with `showChapter` reserved for a cold-open title card at most
- [ ] Key-beat screenshots were reviewed and confirmed correct before delivery — no take shipped unverified
- [ ] Any failed take was correctly classified (re-recorded if flaky, reported and stopped if a real regression) — never papered over
- [ ] Final `.webm` and key-beat screenshots saved to `demos/<feature-slug>/` in the project's external output location (see `references/external-output-paths.md`)
- [ ] The user was told the full path(s) and that it's for sign-off, not a verdict

## See Also

- `quality-assurance` — establishes the correctness this skill assumes; run it first if the feature hasn't actually been verified
- `playwright-e2e-testing` — a persistent, CI-run regression suite; a different artifact and audience than a one-off demo video
- `browser-testing-with-devtools` / `playwright-skill` — live verification/automation, not video production
- `patterns.md` — the fallback synthetic-cursor script, overlay styling reference, and ffmpeg frame-extraction commands
- `references/external-output-paths.md` — where this skill's output lives

Files in this skill

  • SKILL.md10.7 KB
  • patterns.md5.8 KB

Attribution

Is this your skill, or is something wrong with this listing? Request removal or report an issue. Author removals are honored within 72 hours.

Comments

Loading comments…

Newsletter

Get the weekly list of safe new skills, and the ones we pulled.