asciinema-cast-format
Asciinema v3 .cast file format reference. TRIGGERS - cast format, asciicast spec, event codes, parse cast file.
What this skill does
# asciinema-cast-format
Reference documentation for the asciinema v3 .cast file format (asciicast v2 specification).
> **Platform**: All platforms (documentation only)
> **Self-Evolving Skill**: This skill improves through use. If instructions are wrong, parameters drifted, or a workaround was needed — fix this file immediately, don't defer. Only update for real, reproducible issues.
## When to Use This Skill
Use this skill when:
- Parsing or inspecting .cast file structure
- Understanding NDJSON header and event formats
- Building tools that read or write .cast files
- Debugging recording issues or format errors
- Learning the asciicast v2 specification
---
## Format Overview
Asciinema v3 uses NDJSON (Newline Delimited JSON) format:
- Line 1: Header object with recording metadata
- Lines 2+: Event arrays with timestamp, type, and data
---
## Header Specification
The first line is a JSON object with these fields:
| Field | Type | Required | Description |
| ----------- | ------ | -------- | ------------------------------------------- |
| `version` | int | Yes | Format version (always 2 for v3 recordings) |
| `width` | int | Yes | Terminal width in columns |
| `height` | int | Yes | Terminal height in rows |
| `timestamp` | int | No | Unix timestamp of recording start |
| `duration` | float | No | Total duration in seconds |
| `title` | string | No | Recording title |
| `env` | object | No | Environment variables (SHELL, TERM) |
| `theme` | object | No | Terminal color theme |
### Example Header
```json
{
"version": 2,
"width": 120,
"height": 40,
"timestamp": 1703462400,
"duration": 3600.5,
"title": "Claude Code Session",
"env": { "SHELL": "/bin/zsh", "TERM": "xterm-256color" }
}
```
---
## Event Codes
Each event after the header is a 3-element array:
```json
[timestamp, event_type, data]
```
| Code | Name | Description | Data Format |
| ---- | ------ | --------------------------- | -------------------- |
| `o` | Output | Terminal output (stdout) | String |
| `i` | Input | Terminal input (stdin) | String |
| `m` | Marker | Named marker for navigation | String (marker name) |
| `r` | Resize | Terminal resize event | `"WIDTHxHEIGHT"` |
| `x` | Exit | Extension for custom data | Varies |
### Event Examples
```json
[0.5, "o", "$ ls -la\r\n"]
[1.2, "o", "total 48\r\n"]
[1.3, "o", "drwxr-xr-x 12 user staff 384 Dec 24 10:00 .\r\n"]
[5.0, "m", "file-listing-complete"]
[10.5, "r", "80x24"]
```
---
## Timestamp Behavior
- Timestamps are **relative to recording start** (first event is 0.0)
- Measured in seconds with millisecond precision
- Used for playback timing and navigation
### Calculating Absolute Time
```bash
/usr/bin/env bash << 'CALC_TIME_EOF'
HEADER_TIMESTAMP=$(head -1 recording.cast | jq -r '.timestamp')
EVENT_OFFSET=1234.5 # From event array
ABSOLUTE=$(echo "$HEADER_TIMESTAMP + $EVENT_OFFSET" | bc)
date -r "$ABSOLUTE" # macOS
# date -d "@$ABSOLUTE" # Linux
CALC_TIME_EOF
```
---
## Parsing Examples
### Extract Header with jq
```bash
/usr/bin/env bash << 'HEADER_EOF'
head -1 recording.cast | jq '.'
HEADER_EOF
```
### Get Recording Duration
```bash
/usr/bin/env bash << 'DURATION_EOF'
head -1 recording.cast | jq -r '.duration // "unknown"'
DURATION_EOF
```
### Count Events by Type
```bash
/usr/bin/env bash << 'COUNT_EOF'
tail -n +2 recording.cast | jq -r '.[1]' | sort | uniq -c
COUNT_EOF
```
### Extract All Output Events
```bash
/usr/bin/env bash << 'OUTPUT_EOF'
tail -n +2 recording.cast | jq -r 'select(.[1] == "o") | .[2]'
OUTPUT_EOF
```
### Find Markers
```bash
/usr/bin/env bash << 'MARKERS_EOF'
tail -n +2 recording.cast | jq -r 'select(.[1] == "m") | "\(.[0])s: \(.[2])"'
MARKERS_EOF
```
### Get Event at Specific Time
```bash
/usr/bin/env bash << 'TIME_EOF'
TARGET_TIME=60 # seconds
tail -n +2 recording.cast | jq -r "select(.[0] >= $TARGET_TIME and .[0] < $((TARGET_TIME + 1))) | .[2]"
TIME_EOF
```
---
## Large File Considerations
For recordings >100MB:
| File Size | Line Count | Approach |
| --------- | ---------- | ------------------------------------- |
| <100MB | <1M | jq streaming works fine |
| 100-500MB | 1-5M | Use `--stream` flag, consider ripgrep |
| 500MB+ | 5M+ | Convert to .txt first with asciinema |
### Memory-Efficient Streaming
```bash
/usr/bin/env bash << 'STREAM_EOF'
# Stream process large files
jq --stream -n 'fromstream(1|truncate_stream(inputs))' recording.cast | head -1000
STREAM_EOF
```
### Use asciinema convert
For very large files, convert to plain text first:
```bash
asciinema convert -f txt recording.cast recording.txt
```
This strips ANSI codes and produces clean text (typically 950:1 compression).
---
## TodoWrite Task Template
```
1. [Reference] Identify .cast file to analyze
2. [Header] Extract and display header metadata
3. [Events] Count events by type (o, i, m, r)
4. [Analysis] Extract relevant event data based on user need
5. [Navigation] Find markers or specific timestamps if needed
```
---
## Post-Change Checklist
After modifying this skill:
1. [ ] Event code table matches asciinema v2 specification
2. [ ] Parsing examples use heredoc wrapper for bash compatibility
3. [ ] Large file guidance reflects actual performance characteristics
4. [ ] All jq commands tested with sample .cast files
---
## Reference Documentation
- [asciinema asciicast v2 Format](https://docs.asciinema.org/manual/asciicast/v2/)
- [asciinema CLI Usage](https://docs.asciinema.org/manual/cli/)
- [jq Manual](https://jqlang.github.io/jq/manual/)
---
## Troubleshooting
| Issue | Cause | Solution |
| ----------------------- | ---------------------------- | -------------------------------------------------- |
| jq parse error | Invalid NDJSON in .cast file | Check each line is valid JSON with `jq -c .` |
| Header missing duration | Recording in progress | Duration added when recording ends |
| Unknown event type | Custom extension event | Check for `x` type events (extension data) |
| Timestamp out of order | Corrupted file | Events should be monotonically increasing |
| Large file jq timeout | File too big for in-memory | Use `--stream` flag or convert to .txt first |
| Markers not found | No markers in recording | Markers are optional; not all recordings have them |
| Wrong version number | Older cast format | This skill covers v2 format (asciinema v3+) |
| Empty output from tail | File has only header | Recording may be empty or single-line |
## Post-Execution Reflection
After this skill completes, check before closing:
1. **Did the command succeed?** — If not, fix the instruction or error table that caused the failure.
2. **Did parameters or output change?** — If the underlying tool's interface drifted, update Usage examples and Parameters table to match.
3. **Was a workaround needed?** — If you had to improvise (different flags, extra steps), update this SKILL.md so the next invocation doesn't need the same workaround.
Only update if the issue is real and reproducible — not speculative.
Related in General
modeling-omnistudio-epc-catalog
IncludedSalesforce Industries CME EPC product-modeling skill for Product2-based catalog creation. Use when creating EPC products, configuring product attributes, building offer bundles with Product Child Items, or reviewing EPC DataPack JSON metadata for product catalog changes. TRIGGER when: user creates or updates Product2 EPC records, AttributeAssignment payloads, AttributeMetadata/AttributeDefaultValues, Offer bundles, or ProductChildItem relationships. DO NOT TRIGGER when: designing OmniScripts/FlexCards/Integration Procedures (use building-omnistudio-omniscript, building-omnistudio-flexcard, or building-omnistudio-integration-procedure), implementing Apex business logic (use generating-apex), or troubleshooting deployment pipelines (use deploying-metadata).
relationship-science-coach
IncludedUse this skill for direct, practical adult relationship coaching: couples conflict, repair, trust, marriage, dating, flirting, attachment patterns, emotional connection, sex, desire differences, eroticism, kink negotiation, affection, love languages, breakups, and long-term passion. Draw on Gottman, EFT and Hold Me Tight, attachment science, modern sex research, Perel, Nagoski, Kerner, Schnarch, Love and Stosny, and flexible love-language tools. Be concrete and low-hedge. Redirect only for imminent danger, abuse, coercive control, minors, non-consent, self-harm, stalking, or medical/legal/psychiatric decisions.
building-sf-integrations
IncludedSalesforce integration architecture and runtime plumbing with 120-point scoring. Use this skill to set up Named Credentials, External Credentials, External Services, REST/SOAP callout patterns, Platform Events, and Change Data Capture. TRIGGER when: user sets up Named Credentials, External Services, REST/SOAP callouts, Platform Events, CDC, or touches .namedCredential-meta.xml files. DO NOT TRIGGER when: Connected App/OAuth config (use configuring-connected-apps), Apex-only logic (use generating-apex), or data import/export (use handling-sf-data).
venue-templates
IncludedAccess comprehensive LaTeX templates, formatting requirements, and submission guidelines for major scientific publication venues (Nature, Science, PLOS, IEEE, ACM), academic conferences (NeurIPS, ICML, CVPR, CHI), research posters, and grant proposals (NSF, NIH, DOE, DARPA). This skill should be used when preparing manuscripts for journal submission, conference papers, research posters, or grant proposals and need venue-specific formatting requirements and templates.
let-fate-decide
IncludedDraws the 12 Houses of the Zodiac Tarot spread to inject entropy into planning when prompts are vague, ambiguous, or casually delegated. Interprets the spread to guide next steps. Use when the user says 'let fate decide', 'YOLO', 'whatever', 'idk', or other nonchalant phrases, makes Yu-Gi-Oh references, or when you are about to arbitrarily pick between multiple reasonable approaches. Prefer over ask-questions-if-underspecified when the user's tone is casual or playful rather than precision-seeking.
net-ops
IncludedCross-platform network troubleshooting (Windows, macOS, Linux) via local or remote shell. Use for: DNS broken, can't resolve hostnames, nslookup/dig works but apps fail, NRPT, WFP, scutil, /etc/resolver, systemd-resolved, /etc/resolv.conf, NetworkManager, VPN DNS leak residue (ProtonVPN/Mullvad/WireGuard/AnyConnect), AV/firewall blocking DNS or DoH, Tailscale DNS interaction, intermittent connectivity, remote diagnostics over SSH.