Skip to main content

paces

Turn instructional media into structured, interactive learning material. Put it through its paces.

Take a video of someone teaching something — a dance routine, a kata, a recipe — plus, optionally, notes and a steering prompt. paces segments it into named steps, builds a structured step document (an AST for step-by-step instruction), and renders that into learning material: a practice page with counts and deep links today, other guides later.

pip install paces

Quick example

from paces import segment, to_document, render_html

seg = segment(
    "https://youtu.be/q_TUyxUhoEw",
    steps=[
        ("Mise en place", 2),
        ("Pas pieds pointe et ronde", 6),
        ("Soleil avec les bras", 4),
        ("Déhanchés", 8),
    ],
    grid={"unit": "eight", "subdivisions": 8, "tempoBpm": "129.2", "origin": "51.2"},
)
doc = to_document(
    seg,
    doc_id="que-calor",
    title="Chorégraphie Que Calor",
    source="https://youtu.be/q_TUyxUhoEw",
)
open("page.html", "w").write(render_html(doc))

The page lists every step with its counts, links each one back into the video (both the at-tempo run-through and the slow breakdown, when both are known), and — because the document carries a metric grid — includes a count-along transport that paces you through the routine at the measured tempo.

Same thing from the shell:

paces segment VIDEO_URL --steps steps.json --grid grid.json --output seg.json
paces to-document seg.json --source VIDEO_URL --title "My routine" --output document.json
paces suggest-excerpts document.json --output document.json   # mark each block's loop window
paces derive document.json --media routine.mp4   # real loop clips + gifs + posters
paces render document.json --output page.html

derive (pip install paces[media]) cuts a loopable mp4, a palette-quality gif and a poster for every excerpt-bearing span, writes them to media/ next to the document, and the practice page embeds them as looping clips. Crop recipes persist in a hand-overridable document.recipes.json sidecar; the subject_locator= seam (default: no crop) is where pose-based auto-crop plugs in. Design record: docs/adr/0005-media-derivation.md.

How it thinks

Analysis and rendering are separate phases with a serialisable document between them — like a parser emitting an AST and a backend interpreting it. Renderers depend on the document, never on the analyser.

Segmentation is a seam, not a stage. segment(media, segmenter=...) — segmenters are registered capabilities, the default follows from what is present, and "the user typed the boundaries" is a first-class segmenter, not a fallback. A segmenter that cannot name steps returns honest unnamed boundaries (flags: ['naming-abstained']) rather than inventing names.

The document keeps what the learner actually counts. A dance step lasts "4 eights", not "14.86 seconds" — seconds are derived from the metric grid (tempo + origin), never stored. A step can have several source spans (the run-through and the breakdown are the same step seen twice). Uncertainty is content (OpenQuestion), and human edits are protected from regeneration (Lock).

The pieces

you want reach for
cut media into steps segment(media, steps=..., grid=...) → Segmentation
explicit/human boundaries segment(media, boundaries=[...], steps=[names])
use the video's own chapters segment(media, metadata=<yt-dlp info.json>)
measure the grid from the media segment(local_media, steps=[(name, counts), ...]) — no grid needed; tempo + structure measured, origin estimated and flagged (pip install paces[audio])
protect edits from regeneration apply_edits(doc, patches, by="user:you") + merge_regenerated(committed, fresh)
the committed artifact to_document(seg, ...) → StepDocument
real clips/gifs/posters for the page derive_document(doc, media=..., doc_path=...) / paces derive (pip install paces[media])
a practice page render_html(doc)
wall-clock times from counts resolve(doc)
sanity checks validate_document(doc)
what segmenters exist capabilities() / paces list-segmenters
add a segmenter register(Capability(name=..., gives="segmentation", target="mymod:fn", needs={...})) — a new file, nothing edited

Status

Young and moving. The document schema is validated by round-tripping a real proof of concept (an interactive dance-practice page) through it — see tests/test_roundtrip_poc.py. Media derivation (auto-cropped looping clips), intrinsic segmenters (scene/beat/speech detection), and the evidence layer are designed (see docs/) and arrive next.

Metadata

Release files for paces 0.0.7

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for paces 0.0.7
File Size Uploaded
paces-0.0.7.tar.gz 96.1 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for paces 0.0.7
File Interpreter ABI Platform
paces-0.0.7-py3-none-any.whl Python 3 none any Details

Total release size: 154.2 kB

Release files / paces-0.0.7.tar.gz

Download URL paces-0.0.7.tar.gz
Size 96.1 kB
Tags Source
SHA-256 checksum
How to use checksums
c57293a793d52a4098b3468e9f513ecc636ad91b96b8ebc983b20d3c77f7f493
BLAKE2b-256 checksum
How to use checksums
b709fd18ae4a23b301cbb832218bd5dbcb8ca06e486ec7af6fa5fd05c570bfe9
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via uv/0.12.9 {"installer":{"name":"uv","version":"0.12.9","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

Release files / paces-0.0.7-py3-none-any.whl

Download URL paces-0.0.7-py3-none-any.whl
Size 58.1 kB
Tags Python 3
SHA-256 checksum
How to use checksums
7d34d4437d7b48c1e3154da29f62b50908f4bad301e31e5a6425c95ab9eb0617
BLAKE2b-256 checksum
How to use checksums
ec6d51714613fd13c334e2e42e090ba918fd38bddb6a1c8d376295bfedb6a06e
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via uv/0.12.9 {"installer":{"name":"uv","version":"0.12.9","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

Release history Release notifications | RSS feed

0.0.12

2 release files

0.0.9

2 release files

0.0.8

2 release files

This release

0.0.7 This release

2 release files

0.0.6

2 release files

0.0.5

2 release files

0.0.4

2 release files

0.0.3

2 release files

0.0.2

2 release files

0.0.1

2 release files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page