Skip to main content
Glama

PyPI Python CI License: PolyForm Shield 1.0.0

An AI video editor that proves its cuts. Your recordings in, a finished, mastered film out: cut by transcript, with b-roll, cards, music and captions, and every step an agent can call. proofcut renders on your own machine, then transcribes the render and checks that it says what the edit says.

https://github.com/user-attachments/assets/4153d180-3d7c-4c70-af5f-54d63d0a8bd5

Above: an agent cutting a demo video, unattended. The two runs it was cut from, uncut (silent: the recorder took frames only, and the voice is in the film the agent cut): the workspace (2:26) and Claude Code with the proofcut plugin (3:09).

Why it exists

Most of the work in a narrated video, whether an essay, a tutorial, a screencast or a talk, is bookkeeping. Find the retakes and cut them clean. Put the right footage under each line. Level the music under the voice, caption it, end on a card, render it, master it. An agent can do that bookkeeping now, given an editor it can drive.

What an agent cannot do on its own is know that the file it rendered is the film it meant. ffmpeg, melt and auto-editor all exit 0 on some failures, so a render can drop a line, keep a retake, add a frame of black or carry no captions and still report success. Every check that reads the project rather than the file agrees with it. The usual way to find out is to watch the whole thing.

proofcut is an editor built around that gap. You, or an agent, edit a timeline addressed by the words in it. proofcut renders it on your machine, then transcribes the render, counts its frames, and says where the file and the edit disagree.

Related MCP server: CutPilot

Run, not staged

TRIAL.md scores three unattended runs, each handed a goal and no steps, and each passed every one of its checks:

  • The demo cut, the one above.

  • Real footage. 96 seconds of narration with its fluffed takes left in, plus four clips of film footage. The agent cut it to 45 seconds, chose footage by what each line was about, burned captions, and checked its own render: all 123 expected words heard back.

  • A whole film. The demo material plus a score, briefed as a finished film ready to upload. In 192 seconds and $2.27 the agent cut it, laid the music under the voice, ended on a card, mastered it to −16 LUFS, and checked it. The score, the level and the end card were each measured in the delivered file, not taken from the project.

What it can do

One project, and proofcut's own commands from the first import to the delivered file. No NLE finishes the film, and nothing else touches the render. Each stage is one command, and each row links the section of the manual that walks it.

Two video essays of five to six minutes, first finished in Kdenlive, have been rebuilt with these commands alone and measured against the delivered files. One came out the same length to the frame. The other matched all 63 of its voiceover ranges to the millisecond, with the voice aligned to the sample. Both master at the original's −16 LUFS. The measurements are in HISTORY.md.

Beyond those stages:

  • Cuts stay addressable. A word's index never renumbers, so cut vo 111:114 names the same words however many cuts came before it, and a cue hung off a phrase stays addressed through every cut around it.

  • An agent that can look. shot-sheet draws the whole picture track as one labelled grid, and footage-sheet browses a clip you haven't cut yet. Both return the image itself over MCP, not a path the agent can't open.

  • B-roll by description. describe writes what is on screen in each ~10-second window of footage, so an agent can choose a clip by what a line is about.

  • Transcript self-checks. Retake seams, invented words, swallowed repeats and suspect durations are reported when a transcript is attached, and unspoken lets the render itself testify to words nobody said.

  • Reframing for another aspect. Per-shot crop windows, face-aware proposals (reframe-detect), a review sheet, and stacked splits for two speakers. Cards are redrawn at the new frame size, never stretched.

  • Screen recordings. Named instants (events) that a crop, a sound or a speed change can hang off, a clip inset into the recording, and a retime for the slow parts.

  • Animated graphics. A graphic is a web page an agent writes or fills from a template (typing, a highlighter sweep, a letter build, chips), captured frame by frame by a headless browser and placed over a span of words. It animates in, holds as long as the span lasts, and animates out, so a cut never breaks one. Saved graphics carry across projects.

  • Stills and stickers. Photos and cut-outs go in once, upright, and play full frame or ride over the film as stickers: placed, sized, turned, framed as a photo card, popping or sliding in. Paste one into the agent's prompt and it is added.

  • Built for agents. 132 MCP tools with typed inputs, structured returns and read/write annotations, so Claude Code, Codex or your own agent can drive it and a permission layer can tell a look from a change.

  • No lock-in. The timeline is OpenTimelineIO, the manifest is JSON, and the render is ffmpeg's and MLT's. Export a .kdenlive or OTIO file and finish anywhere.

Frame mode: a shot list beside the selected shot's windows, each crop
drawn as a rect on three of the source's own frames, over a filmstrip of the
whole shot with the sampled instants ticked on it, the window's rect quoted
in source pixels, Approve/Re-frame beside it, and coverage chips for stale
framing and unexplained steps

How people use it

Tell an agent what film you want. In Claude Code, install the plugin and describe the film: which recording is the voice, what the b-roll is, where the music goes, what it ends on. The agent imports, transcribes, cuts the retakes, hangs footage off the lines it belongs to, scores, masters and checks the render, using proofcut's tools and nothing else. It can look at the picture track as a labelled grid while it works, so it sees what it placed rather than a filename. Every MCP client runs the same server; the plugin is the one that needs no setup.

/plugin marketplace add tydude001/proofcut
/plugin install proofcut@proofcut

Cut from a shell, by naming words. Every tool is also a proofcut subcommand printing JSON, so a cut is a script you can read, re-run and diff. --plan prints what a range says before anything changes, and undo walks it back.

uv run proofcut -C myproject cut vo 111:114 --plan

Edit by hand in the workspace. Strike words in the transcript, drag-trim and razor on the timeline, review every crop in place, and export from Finish. It plays the source through the edit, so seeing a cut costs no render, and the truth strip warns while you edit if the film would ship wrong. The agent sits in a side rail of the same window.

uv run proofcut -C myproject open

Finish elsewhere, and still prove the file. Rough-cut here, export a .kdenlive or OpenTimelineIO file, finish in Kdenlive, Resolve or Premiere, and bring the trim back with import-edit. Then point verify at the delivered file, and a retake left in is caught before anyone watches.

uv run proofcut -C myproject verify final.mp4

Cut a vertical teaser from the film. reel copies a span of the finished film into a second project at another canvas, so the film itself is never reshaped to take one render. It names every picture the teaser will not have and pins the ones it keeps to the frames the film showed, so the teaser shows what the film showed. Frame mode then reviews each crop on the source's own frames.

uv run proofcut -C myproject reel ../teaser 1:32+44 --canvas 1080x1920

Split a pile of recordings into shorts. Seed every recording as one timeline, cut the retakes once, then split it by first and last word. Each short becomes its own project beside the pile, holding only the recordings it uses, and any stretch no short took is named rather than lost.

uv run proofcut -C dump seed reel1 reel2 reel3
uv run proofcut -C dump split intro=reel1:0..reel1:46 demo=reel2:0..reel3:88

The first three are walked in § Try it; the reel, the split and the round-trip are in the manual.

The proofcut workspace on the demo project: the transcript with a retake struck
through, the preview drawing the shot under the playhead with its captions, the
side rail on its agent tab reporting a finished render against the timeline,
and the layered timeline below: picture, waveform and captions as three
projections of one edit

What it holds to

  • The file is the evidence. A check reads the render, never the project. What verify, frames and hold check report is measured off the delivered file, because a project can say captions are burned, or a line is in, about a file that has neither.

  • Your recordings, cut, not invented. proofcut makes no footage and writes no script. It takes what you recorded to a film, in an order you or your agent chose. It is not a text-to-video generator.

  • Your machine, no meter. Commercial AI editors are apps around a metered cloud service. proofcut transcribes, edits and renders locally: no account, no per-minute billing, and no cloud service of its own. The only thing that talks to a model provider is the agent you choose to run, and your footage stays where it is.

  • Nothing an agent does is out of your reach. The MCP server, the command line and the workspace call the same operations, and a test holds every tool to a matching command printing JSON. Changes take --plan to show what they would do first, anything addressed by word echoes the words it resolved to, and undo --steps N walks back an agent's whole turn.

  • Say what is not measured. The design record is public: the plans, and a dated history of what shipped and what the evidence said, failures included. Where only a CI runner has done something, the docs say a runner did it, not a person; where a check is a model's reading of a picture, it is reported and never gates.

Try it

Nothing below installs anything until you say so, and every step prints what it would do first. § What it puts on your machine is the whole footprint and how to reverse it.

Check your machine, before cloning anything. proofcut doctor probes every tool proofcut uses and prints the fix for anything missing (§ Requirements has the list). It only looks. It installs nothing and writes nothing. With uv installed:

uvx proofcut doctor

That first run downloads Python 3.13 if uv has none, plus proofcut's dependencies. That is about 230 MB, all of it inside uv's own cache, which uv cache clean empties.

Then read what an install would do. On Linux, Windows and a Mac of either kind, proofcut setup --plan prints every piece it would fetch, its size, and which doctor row asked for it, then stops without touching anything:

uvx proofcut setup --plan
proofcut setup — installs into /home/you/.local/share/proofcut/deps

Will install
  ffmpeg — n8.1.2 (BtbN autobuild-2026-08-31-13-27), about 126 MB
      because: ffmpeg is not on PATH. ffprobe is not on PATH.
  whisper — openai-whisper (uv tool, Python 3.12, cpu torch), about 1.9 GB
      because: whisper is not on PATH.
  auto-editor — 31.6.0, about 46 MB
      because: auto-editor is not on PATH.
  melt — Shotcut 26.8.1 (melt 7.41.0), about 155 MB
      because: melt is not on PATH.
  total: about 2.2 GB

That is a bare machine. Yours will be shorter, because setup installs nothing doctor passed, so a working ffmpeg or melt of your own is never touched. With an NVIDIA GPU the whisper row is CUDA torch and the total is about 5.8 GB.

Drop --plan to go ahead. It reprints the plan, asks once, and installs for you alone, with no sudo or administrator rights; proofcut setup --uninstall removes exactly what it added, and nothing you already had.

uvx proofcut setup

The demo and your own recordings run from a checkout:

git clone https://github.com/tydude001/proofcut && cd proofcut
uv sync

The two-minute demo

No footage needed. docs/DEMO.md makes a voiceover with a real retake, b-roll and a score, then walks a whole small film: cut the retake by naming its words, hang b-roll off a phrase, lay the score under the voice, render and master it, end on a card, and check the render against the timeline.

uv run python scripts/make_demo.py ~/proofcut-demo

In Claude Code

The plugin registers proofcut's MCP server, so every tool is available with no setup of your own:

/plugin marketplace add tydude001/proofcut
/plugin install proofcut@proofcut

The first start downloads about 175 MB of Python dependencies, and Claude Code gives a server 30 seconds to connect. On a slow connection, start that first session as MCP_TIMEOUT=300000 claude, or reconnect proofcut in /mcp once the download has finished.

Any other MCP client runs the same server, from a checkout or with no checkout at all:

uv run --project /path/to/proofcut proofcut mcp
uvx proofcut mcp

On your own recording

uv run proofcut init myproject
uv run proofcut -C myproject import VO.wav --clip-id vo
uv run proofcut -C myproject transcribe vo                  # whisper, word-timed
uv run proofcut -C myproject seed vo                        # auto-editor strips silences
uv run proofcut -C myproject transcript vo --search "here's the thing"
uv run proofcut -C myproject cut vo 111:114 --plan          # what do those indices say?
uv run proofcut -C myproject cut vo 111:114 --pad 0.1       # inclusive word range
uv run proofcut -C myproject export final.mp4 --render      # or a .kdenlive to finish in an NLE
uv run proofcut -C myproject verify final.mp4               # did the render say what you edited?

To watch the edit instead, open the workspace:

uv run proofcut -C myproject open        # server plus an app window
uv run proofcut -C myproject web --open  # the same page in a browser tab

proofcut is 0.x software. A project from an older version is refused rather than guessed at, and proofcut migrate brings it forward.

What it puts on your machine

proofcut is a local tool that needs real media binaries, so proofcut setup does download a few hundred megabytes. Here is all of it, where it goes, and what takes it away. Sizes are a Linux x86_64 bare machine; proofcut setup --plan prints yours.

What

Where

Size

Removed by

ffmpeg, ffprobe

setup's folder, with symlinks in ~/.local/bin

126 MB

proofcut setup --uninstall

auto-editor

setup's folder

46 MB

proofcut setup --uninstall

melt (Shotcut's portable build)

setup's folder

155 MB

proofcut setup --uninstall

whisper

a uv tool, plus the Python 3.12 uv fetches for it

1.9 GB, or 5.5 GB with an NVIDIA GPU

proofcut setup --uninstall

proofcut and its Python dependencies

uv's cache

230 MB

uv cache clean, uv tool uninstall proofcut

the demo's media

the directory you name it

under 2 MB

delete that directory

the model store: what whisper, the vision model and the face detector said about each source

~/.local/share/proofcut/store, beside setup's folder

tens of MB a year of shoots

proofcut setup --clear, or --uninstall

"Setup's folder" is one directory: ~/.local/share/proofcut/deps ($XDG_DATA_HOME if you set it), or %LOCALAPPDATA%\proofcut\deps on Windows. It holds everything except whisper, which is a uv tool because that is how whisper ships.

Five rules it holds to, each one enforced by a test rather than promised here:

  • --plan writes nothing at all, and its exit code reports only what is missing (test_setup_plan_writes_nothing_and_exits_by_what_is_missing), so reading the plan can never turn into performing it.

  • Doctor's report is the input. A piece is installed only when its row is ✗. A tool you already have is never replaced, and never upgraded behind your back.

  • Every download is pinned by URL and SHA-256, bumped by hand, never resolved from a latest tag. A hash that does not match leaves nothing behind.

  • No sudo, no administrator rights, no distribution packages, and nothing is ever written over an existing file.

  • Every link, file, folder and uv tool is recorded, and --uninstall removes exactly those, including the Python uv fetched for whisper. tests/test_install.py installs the lot into a fake home, uninstalls, and asserts the home's listing is what it was before (test_install_then_uninstall_leaves_the_home_as_it_was), so "removes exactly what it added" is checked on every run of the suite, not just meant. A link you repointed yourself is left alone, because it is yours now.

To see a removal before it happens:

proofcut setup --uninstall --plan

Two things setup deliberately does not do: it is a command you type and never an MCP tool, so an agent cannot start a 2 GB download or change your PATH; and it touches nothing outside your own user account.

Help wanted: a Mac or a Windows run

GitHub's macOS and Windows runners take the demo to a checked render, but a runner never reads the instructions. On a Mac, one person has taken the demo to a checked render, on an Intel Mac (i7-8850H, macOS 15.7.9); on Apple silicon only the runner has. On Windows, the author's own Windows 11 laptop has, twice, and nobody else's PC; Windows 10 and ARM64 PCs have not been tried at all. If you have one of these machines and half an hour, one script installs what proofcut needs, makes a short test video, has proofcut cut, score, master and check it, and puts a report on your Desktop. It asks before it starts, records what it added, and removes exactly that on request, nothing you already had. A run that stops at the first step is just as useful, because where it stops is the finding.

On a Mac:

git clone https://github.com/tydude001/proofcut
bash proofcut/scripts/mac_trial.sh

It downloads uv into ~/proofcut-mac-trial and uses it to run proofcut setup, which fetches whatever of ffmpeg, auto-editor, Shotcut's renderer and whisper your Mac is missing (§ What it puts on your machine). It asks for no password; an Intel Mac needs Apple's Command Line Tools, and the script says so if they are missing. bash proofcut/scripts/mac_trial.sh --uninstall runs proofcut setup --uninstall and deletes that folder. Then file the report.

On Windows, from PowerShell:

git clone https://github.com/tydude001/proofcut
powershell -ExecutionPolicy Bypass -File proofcut\scripts\windows_trial.ps1

It downloads uv into one folder under %LOCALAPPDATA% and uses it to run proofcut setup, which fetches whatever of ffmpeg, auto-editor, Shotcut's renderer and whisper your PC is missing. Nothing is installed system-wide and it needs no administrator rights. The same command with -Uninstall runs proofcut setup --uninstall and deletes that folder. It puts proofcut-windows-report.zip on your Desktop with your home folder's name taken out; file the report.

Requirements

proofcut is developed on Linux (a Fedora-based desktop). On macOS and Windows the test suite passes on CI; where each OS stands by hand is § Help wanted above, and in detail docs/plans/PORTABILITY.md.

Every hard part of an editor already exists as mature open source, and proofcut is the layer that lets an agent drive those tools and check what they produced. Run uv run proofcut doctor to check everything below at once. On Linux, Windows and a Mac of either kind, uv run proofcut setup installs any of the last four that doctor marks ✗ (§ What it puts on your machine, and --plan to read it first): a static ffmpeg, whisper, auto-editor's release binary and Shotcut's melt (on Linux the portable build, which renders with no display at all; docs/plans/INSTALL.md).

You need

For

Notes

Python 3.13 and uv

everything

uv sync installs the Python side. The only runtime dependencies are mcp and OpenTimelineIO, which holds the timeline and exports it to other editors.

ffmpeg / ffprobe built with libx264, freetype and libass

cutting, concatenating, captions, rendering

Fedora's default ffmpeg-free has no libx264: use RPM Fusion's ffmpeg. On a Mac, Homebrew's ffmpeg lacks freetype and libass: install ffmpeg-full and put $(brew --prefix ffmpeg-full)/bin first on PATH (it is keg-only).

auto-editor 31+

silence and bad-take removal, single-source renders

Install the upstream binary. The PyPI package is a stale 29.x.

whisper

word-timed transcription (30+ languages), render verification

Any openai-whisper install. uv tool install --python 3.12 openai-whisper is the short route (3.12 because torch's Intel-Mac builds stop there, and on an Intel Mac also --with 'numpy<2', which that last torch needs); add --torch-backend cpu without an NVIDIA GPU (1.9 GB instead of 5.5 GB). Found via PROOFCUT_WHISPER, then PATH. The CPU build transcribed the demo's 19-second voiceover in 33 seconds.

MLT (melt)

layered renders (b-roll, cards, music)

Your distribution's MLT package (mlt on Fedora, whose melt package is an unrelated compression tool), or Kdenlive, whose flatpak copy is found automatically. PROOFCUT_MELT overrides both.

Optional. Each unlocks one feature, proofcut doctor reports whether it is available, and everything else works without it:

Optional

Unlocks

Notes

ImageMagick 7 (magick)

title and end cards, rendered from SVG templates

ImageMagick 6's convert is not used, so distributions that still ship 6 (Ubuntu 24.04) need ImageMagick's own build.

Claude Code (claude, logged in)

the agent pane in the workspace

proofcut mcp works with any MCP client; only the pane runs claude itself.

PROOFCUT_VLM

describe (b-roll search by what's on screen)

The python of a venv with torch, transformers, bitsandbytes and Pillow, on a CUDA GPU. The Qwen2.5-VL model downloads on first use.

PROOFCUT_FACE

reframe-detect (face-aware crops)

The python of a venv with insightface, onnxruntime and opencv-python.

PROOFCUT_TTS, PROOFCUT_TTS_MODEL, PROOFCUT_TTS_VOICE

vo-synth (a line in a cloned voice)

A python with qwen-tts and a CUDA torch, a local Qwen3-TTS snapshot, and a directory holding a reference clip of the voice. There is no default voice, on purpose.

Working on proofcut

Whether you're a person or a coding agent, start with CLAUDE.md. It holds the rules and the traps this repo has already hit, and Claude Code loads it automatically. CONTRIBUTING.md is the short version a pull request is checked against, and SECURITY.md says how to report a vulnerability.

Where things live:

Path

What it is

src/proofcut/ops.py

Every operation. The MCP tools, the CLI and the web UI all call these.

src/proofcut/server.py

The MCP server. Register tools with @_tool(), never @mcp.tool().

src/proofcut/cli.py

The proofcut command: one subcommand per tool, printing JSON.

src/proofcut/webui.py, src/proofcut/web/

The workspace. It posts to ops and renders what comes back; it never decides anything itself.

src/proofcut/project.py, timeline.py

The project manifest (proofcut.json) and the OTIO timeline.

tests/

test_server_stdio.py drives a real proofcut mcp subprocess; test_webui_http.py a real socket.

scripts/

The demo maker, the Mac and Windows trial kits, screenshot capture.

docs/

The manual, the demo, and the design record (below).

Run the checks:

uv sync
uv run ruff check .      # never `ruff format`; see CONTRIBUTING.md
uv run pytest

The suite talks to a real proofcut mcp subprocess, so it is slower than a pure unit suite. Tests that need whisper, auto-editor, melt or ImageMagick skip when the tool is missing. Tests that render through melt also need a display: on a headless machine use QT_QPA_PLATFORM=offscreen or xvfb-run -a (proofcut doctor tells you which your MLT needs). Without one they fail with "no display for MLT's Qt module to open", which is the environment, not a regression.

The documentation:

proofcut's reasoning is part of what it ships, so the design record is public:

  • PLAN.md: architecture, stack decisions, open questions.

  • HISTORY.md: the dated record of what shipped and what the evidence said.

  • PRIOR-ART.md: what else exists in this space, and what proofcut does that they don't.

  • NEXT.md: the directions after the queues closed, ranked.

  • TRIAL.md: an agent cutting a video end to end, unattended and scored.

  • docs/plans/: the plans, in progress and finished. A step that landed says "Shipped" and names its HISTORY.md section.

License

PolyForm Shield 1.0.0. proofcut is source-available, not open source: you can read, run, change and redistribute it for any purpose except building a product that competes with it. Cutting your own videos, running it for clients, building on it and forking it to fix a bug are all fine. For a commercial licence, ask.

The bundled typefaces are not proofcut's to relicense. The caption face in src/proofcut/fonts/ and the three browser faces in src/proofcut/web/ are OFL-1.1, each with its licence text beside it and its source in that directory's FONTS.md.

Say thanks

If proofcut cut a video for you, you can buy me a coffee on Ko-fi.

Available Tools

132 tools
add_captionsA
DestructiveIdempotent

Write word-timed ASS captions for the current timeline to output.

Timings follow the timeline, not the original recording, so captions stay correct after cuts; words that were cut are omitted and counted as words_cut.

The look comes from the project — set it with caption_style, see it with caption_view. The arguments here override it for this one file and are not written back, so regenerating after a cut is styled the project's way again. Leave them unset unless you specifically want a one-off.

The sidecar .ass is always written to output — Kdenlive loads it and it stays restylable. Pass burn (a render of THIS timeline) to burn the captions into a video as well, written to burn_output; against any other video the timings will not line up.

ParametersJSON Schema
NameRequiredDescriptionDefault
burnNoAlso burn the captions into this video with ffmpeg; the sidecar is still written to `output`. It must be a render of **this** timeline — against any other video the timings will not line up. `export --render` does not burn captions, and nothing else reports a render that was made without them.
holdNoHow long a cue lingers after its last word, in seconds.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
outputYesWhere to write the `.ass` sidecar — always, burning or not. Never a video path: a media suffix is refused. The burned video goes to `burn_output`.
presetNoOverride the project's base look for this one file — `clean`, `karaoke` or `boxed`. Nothing here is written back to the project.
clip_idNoCaption one transcript's words rather than every clip's.
max_gapNoStart a new cue when the silence between two words exceeds this many seconds.
max_wordsNoMost words in one caption cue.
burn_outputNoWhere the burned video goes, when `burn` is set. Unset, it is derived from `burn`'s own name in the project's renders folder.
max_durationNoLongest a single cue stays on screen, in seconds.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The description richly discloses behavior beyond the annotations: timings follow the timeline rather than the original recording, cut words are counted as `words_cut`, style overrides are not written back to the project, and the sidecar is always written to `output` and stays restylable in Kdenlive. This aligns with the annotations and adds substantial operational context.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but every sentence earns its place: purpose, timing behavior, style semantics, sidecar behavior, and burn constraints are all relevant. It front-loads the core purpose before diving into caveats, with no filler.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the high parameter count, rich schema, annotations, and existing output schema, the description covers all decision-relevant behavior: what is written, where, when burning is safe, and how styling works. Nothing essential is missing for an agent to select and invoke this tool correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the schema already documents each parameter thoroughly. The description adds some high-level context about one-off overrides and the `burn` constraint, but it does not need to compensate for missing parameter documentation; a baseline 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

Openly states a specific verb and resource: 'Write word-timed ASS captions for the current timeline to `output`.' It also differentiates itself from siblings by clarifying the relationship to `caption_style`, `caption_view`, and `export --render`, so an agent can distinguish this tool from nearby alternatives.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives explicit when-to-use guidance: style should be set with `caption_style` and viewed with `caption_view`, while the arguments here are described as one-off overrides. It also warns when not to pass `burn` — only a render of this timeline will have matching timings — and notes that `export --render` does not burn captions.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

assetsA
Read-onlyIdempotent

Every asset a cue can point at — clip or card — for an assets pane.

The cue vocabulary is clip_id or card:name, so this lists both: each clip with its probe metadata, transcript/description presence, role and media.playability verdict; each card with what it was made from, whether its files exist, and whether it has a re-author record. Every entry carries cues, how many cues reference it — "is this used" is the question an assets pane exists to answer. Read-only.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A3.9/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true and destructiveHint=false; the description repeats 'Read-only' but adds no further behavioral traits such as rate limits, auth needs, or side effects. It does describe output composition (probe metadata, playability, re-author record), but that is more output semantics than behavior, and with annotations covering safety, the extra value is limited.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Two sentences with the purpose front-loaded and supporting details following. The second sentence is long but dense and information-bearing; there is no fluff, though it could be slightly tightened.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the output schema exists and the tool is a read-only list with no required parameters, the description sufficiently covers what the agent needs to know. It explains the main output categories (clip/card fields and cue counts), though it does not cover when to prefer this over sibling tools, which is already handled in usage guidelines.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The single parameter `path` is fully documented in the input schema with detailed resolution semantics. The tool description adds nothing about `path`, so per the rule for >80% schema coverage, a baseline of 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with 'Every asset a cue can point at — clip or card — for an assets pane,' which is a specific verb-resource statement. It clearly distinguishes itself from siblings like list_media by covering both clips and cards and including cue reference counts, so an agent can tell it apart without opening schemas.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The phrase 'the question an assets pane exists to answer' provides clear context for when to use this tool. However, it does not explicitly mention alternatives or state when not to use it, so it stops short of full routing guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

attach_transcriptA
DestructiveIdempotent

Ingest an existing word-timed whisper JSON as this clip's transcript.

Checks the transcript against itself for near_duplicates — adjacent runs of words that sound like the same line said twice. That is a retake verify can never catch once both takes are cut into the edit, since nothing then disagrees with the timeline. A hit is not a verdict: a deliberate callback line looks the same as a swallowed retake here.

Also reports suspect_durations, overlaps and repeats. An overlaps seam is a retake splice whisper read straight across, interleaving both takes and inventing words nobody said — check it before drawing anything derived from this transcript. repeats is a back-to-back duplicated phrase, the shape a retake makes when it survives as distinct words rather than as a seam — a different subset of retakes than overlaps finds, not a smaller one. Use transcript_checks to see all four again later.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
clip_idYesThe clip this transcript belongs to. Its words become `(clip_id, word_index)`, which is how every cue, mark and caption addresses them afterwards.
transcript_pathYesThe whisper JSON to ingest. It has to carry word-level timings — proofcut addresses words, not segments.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.5/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the annotations, the description explains that the tool runs self-checks (near_duplicates, suspect_durations, overlaps, repeats), warns that a hit is not a verdict, and cautions about overlaps seams inventing words. This is rich, non-obvious behavioral context that materially helps an agent trust and interpret results.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The purpose is front-loaded in the first sentence, and the subsequent paragraphs each explain a distinct behavioral check or caveat. The description is longer than minimal, but every sentence adds operational value and there is no fluff.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the output schema exists and annotations flag destructive/idempotent behavior, the description is largely complete: it defines input requirements, explains all four diagnostic checks, and warns about interpretation. A small gap is that it does not explicitly state that ingesting replaces any existing transcript, but annotations and the meaning of 'as this clip's transcript' cover it.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3, but the description adds meaningful detail: clip_id words become (clip_id, word_index) and are used by every cue, mark, and caption afterward. This explains the downstream impact of the parameter beyond the schema's simple field documentation.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The first sentence states a specific action ('Ingest an existing word-timed whisper JSON') and target ('as this clip's transcript'), clearly distinguishing it from tools like transcribe. It names the exact resource and the ownership outcome in a way an agent can act on.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description makes clear this tool is for ingesting an already-existing whisper JSON rather than generating one, which implicitly routes an agent away from transcribe. It also gives follow-up guidance ('Use transcript_checks to see all four again later'), but it does not explicitly name alternatives or state when not to use it.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

attenuate_noisesA
DestructiveIdempotent

Pull down short loud non-speech events instead of cutting them out.

An event only qualifies automatically when it is both short (max_event_seconds) and sitting in a word-map gap narrow enough to prove the map is dense around it (max_gap_seconds) — a wide gap disqualifies even a very short event, which is the false-positive class this exists to prevent (speech sitting in a hole the transcript never wrote down). Qualifying events are pulled down db via one ffmpeg pass, never cut, and written as a new derived copy that media_path() picks up automatically everywhere downstream; the original is always what a re-run reads from, so repeated calls never compound gain.

Unlike cut_by_transcript/cut_by_time, nothing here ever raises on what the scan finds — this is an automatic multi-candidate scan, not a handful of explicit ranges, so withholding is done per event rather than refusing the whole call. suspect_neighbours (a bounding word itself has a suspect duration — withheld unless confirm_suspect=True or plan=True) and disqualified (too long, or too wide a gap — never written, no override) are always reported in full, not only under plan=True.

ParametersJSON Schema
NameRequiredDescriptionDefault
dbNoHow far to pull each qualifying event down, in dB. Negative is quieter.
padNoSeconds added either side of each event before it is pulled down.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
clip_idYesThe clip to scan. It always reads that clip's **original** media, never a previous attenuated copy, so repeated calls never compound gain.
confirm_suspectNoGo ahead even though a boundary word claims a suspect duration. Read the echoed words first — a suspect duration usually means whisper hid a retake inside that word, so the edge is not where it reads.
max_gap_secondsNoHow wide the word-map gap around an event may be. A wide gap disqualifies even a very short event — that is the false-positive class this exists to prevent, speech sitting in a hole the transcript never wrote down.
max_event_secondsNoLongest an event may run and still qualify automatically. Anything longer is reported as `disqualified` and never written.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.9/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the annotations, the description explains the exact write behavior: a new derived copy is written, the original is always read first, repeated calls never compound gain, and nothing ever raises on scan findings. It also documents per-event withholding versus whole-call refusal, and the behavior of suspect_neighbours and disqualified events.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but every sentence contributes: it front-loads the core purpose, explains the qualification rule, discloses write behavior, and then distinguishes this tool from siblings. Despite its length, it is efficiently structured with clear paragraphs and no filler.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's complexity, the description fully covers the qualification criteria, the no-compound-gain guarantee, the difference from sibling tools, and the reporting behavior for suspect and disqualified events. The output schema handles return value specifics, so nothing essential is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The input schema already covers all parameters with detailed descriptions (100% coverage), so the baseline is 3. The tool description adds value by explaining how db, max_event_seconds, max_gap_seconds, confirm_suspect, and plan work together in the qualification and withholding logic, going beyond individual schema comments.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific verb and resource: 'Pull down short loud non-speech events instead of cutting them out.' It clearly distinguishes itself from cut_by_transcript/cut_by_time by describing the difference in granularity and failure mode, so an agent can select it correctly.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explicitly contrasts this tool with cut_by_transcript/cut_by_time, explaining that this is an automatic multi-candidate scan rather than explicit ranges. It also clarifies when plan=True should be preferred and how confirm_suspect gates a specific case.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

attribute_speakersA
Idempotent

Label each word with the mic that was loudest while it was spoken.

For a co-hosted recording captured on one mic per speaker. It is one pass over the transcript that is already attached — never a second ASR run, and transcribing each mic separately is measured and dead: half of each mic's own transcript is the other person, at every isolation tried. Transcribe once, from the mix or either mic, then call this.

streams are ffmpeg audio ordinals into the registered container (0, 1), and labels names them in the same order — one label per stream, defaulting to speaker1, speaker2. The speaker lands on the word: it is a label and never an address, so every cue, description, mark, music anchor and caption still resolves through (clip_id, word_index) and nothing else moves.

It reports; it does not decide below the floor. apply is off by default. The rule is ~99% correct per word on clear speech and at chance on words spoken over each other, and margin_db is what half-knows the difference — anything under it comes back in ambiguous_spans to go and listen to, with the three words either side. Read unmeasurable separately from ambiguous: it means the mics ran out before the transcript did, which is a different recording problem. Applying keeps any label already on a word this refuses to call.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
applyNoWrite the labels onto the words. Off by default — it reports first, and applying keeps any label already on a word this refuses to call.
limitNoHow many ambiguous spans to return; the reply also says how many there are in total.
labelsNoWhat to call each stream, in the same order — one per stream. Unset, `speaker1`, `speaker2`.
clip_idYesThe co-hosted clip: one container, one mic per speaker, one transcript already attached.
streamsNoWhich audio streams the speakers are on, as ffmpeg audio ordinals (`[0, 1]`). Unset, the container's readable audio streams in order.
margin_dbNoHow much louder one mic has to be to be believed, in dB. It reports a default and is not a threshold to trust: on words spoken over each other the rule is at chance, and anything under this margin comes back in `ambiguous_spans` to go and listen to.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.8/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond annotations (readOnlyHint false, idempotentHint true), the description discloses behavior richly: it reports without applying by default, keeps existing labels on words it refuses to call, distinguishes 'unmeasurable' from 'ambiguous', and states accuracy figures (~99% on clear speech, chance on overlap). It also explains that margin_db is not a threshold to trust, which is a nuanced behavioral caveat.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long, but it is well-structured with bold headings and logical flow: purpose first, then how it differs from alternatives, then parameter explanations, then behavioral caveats. Each sentence earns its place; nothing is redundant. It is appropriately detailed for a complex tool with many edge cases, though it could be tightened slightly.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's complexity (7 parameters, output schema present, multiple edge cases), the description covers everything an agent needs: the core operation, when to use it, how parameters interact, the difference between ambiguous and unmeasurable, and the apply behavior. The presence of an output schema further reduces the burden of explaining return values. Nothing critical is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The input schema already provides descriptions for all 7 parameters (100% coverage), so the baseline is 3. The description adds significant meaning beyond the schema: it explains streams as ffmpeg audio ordinals in order, labels as names in the same order, margin_db as a reporting floor rather than a decision threshold, and the interplay between apply and existing labels. This extra context lifts the score to 4.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a crisp, specific verb-resource statement: 'Label each word with the mic that was loudest while it was spoken.' This clearly distinguishes it from transcription tools (transcribe, hear) and from tools that manipulate transcript structure. It also frames the tool as a post-transcription step, which separates it from ASR workflows.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives explicit when-to-use and when-not-to-use guidance: it is a single pass over an attached transcript, never a second ASR run, and it warns that transcribing each mic separately is 'measured and dead' with concrete evidence. It also tells the user to transcribe once first, then call this tool. This is actionable and leaves no ambiguity about prerequisites.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

broll_briefA
Read-onlyIdempotent

The whole b-roll question as data: what there is, and what it goes under.

Returns the footage catalogue with each clip's synopsis and duration, then every shot position on the timeline with the narration that plays over it, how long it is held, and what is currently there. card: true positions are shown for rhythm and are not choices.

This is the half proofcut can do. Choosing is the other half, and it belongs to you: read the brief, decide which clip goes under which sentence, and write the answers back with cue_add, where the picture plan checks each one. Ranking the catalogue by text similarity was measured and does not work — the sentence that earns a clip routinely shares no word with any description of it.

missing_synopsis is the thing to fix first. A clip with no synopsis is invisible to any reasoning about the catalogue, so it will simply never be chosen.

ParametersJSON Schema
NameRequiredDescriptionDefault
fpsNoThe frame grid the shot positions are projected on. Defaults to the rate `export` would use.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.6/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true and destructiveHint=false, so the safety profile is known. The description adds substantial behavioral context beyond those: it explains that `card: true` positions are shown for rhythm and are not choices, that ranking by text similarity was measured and does not work, and that `missing_synopsis` clips will never be chosen. These are non-obvious traits an agent needs to interpret the output correctly, and they do not contradict any annotation.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but well-structured: it front-loads the purpose, then explains the workflow, and closes with a priority instruction. Every sentence contributes useful guidance, though the opening line ('The whole b-roll question as data...') is somewhat poetic and less concrete than the rest. It is appropriately sized for the tool's complexity, but slightly verbose.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The tool has an output schema (not shown but flagged as present), and the description explains exactly what the output contains: clip synopsis, duration, shot positions, narration, hold length, current content, and card positions. It also explains how to act on that output via `cue_add`, and what to fix first. For a read-only briefing tool, this is complete enough for an agent to call it correctly and interpret the result.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the baseline is 3. The description does not add any parameter-specific meaning beyond what the schema already provides for `fps` and `path`. It focuses on the output and usage context, not the parameters, so it neither enhances nor detracts from the schema's documentation.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a clear statement of what the tool returns: the footage catalogue with clip synopsis and duration, plus shot positions with narration, hold duration, and current content. It explicitly notes that `card: true` positions are shown for rhythm and are not choices, which distinguishes this read-only briefing tool from the write-oriented `cue_add` sibling. The verb 'Returns' and the specific resource make the purpose unmistakable.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives explicit usage direction: it states this is the half that reads the brief, and that choosing belongs to the user via `cue_add`. It also warns that ranking by text similarity does not work, guiding the agent away from a common but flawed heuristic, and instructs to fix `missing_synopsis` first because such clips are invisible to reasoning. This is clear when-to-use and when-not-to-use guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

build_shotsA
Read-onlyIdempotent

Project the cue table into contiguous shots over the current edit.

Maps each cue's word through the edit's surviving ranges to a timeline frame, resolves its asset to a checked path (card:name under assets/cards/, else a registered video clip_id), and runs each shot to the next cue — the last to the edit's own frame total. Refuses if a cue's word was cut from the edit; fix it with cue_rm/cue_add first.

fps picks the frame grid; it defaults to the project's timebase, which for an audio-only project is milliseconds rather than frames. Pass the rate export will use to see the frames the export actually cuts at.

ParametersJSON Schema
NameRequiredDescriptionDefault
fpsNoThe frame grid to project onto. Unset, the project's timebase — which on an audio-only project is milliseconds rather than frames. Pass the rate `export` will use to see the frames the export actually cuts at.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.3/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint, idempotentHint, and destructiveHint false, and the description adds meaningful behavioral detail beyond that: the exact mapping algorithm, asset resolution rules, shot extension to the next cue and final frame, refusal on cut cues, and the subtle fps/timebase default behavior. This is rich, non-contradictory context.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is well-structured and front-loaded with a one-line summary, followed by concise technical detail and a parameter note. Each sentence adds value; there is no padding or repetition of obvious annotation facts.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the annotations, full schema descriptions, and presence of an output schema, the description covers the critical behavior, failure mode, how shots are ended, asset resolution, and fps selection. An agent has everything needed to select and invoke this tool correctly without additional inference.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The input schema has 100% description coverage for both fps and path, so the baseline is 3. The description reinforces the fps behavior and timebase nuance, but that information already appears in the schema description; no new semantic detail is added for path or beyond what the schema provides.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states a specific verb and resource: 'Project the cue table into contiguous shots over the current edit.' It explains the core operation in detail and differentiates itself from generic edit operations, though it does not explicitly name or contrast sibling tools such as shot_sheet or cut_by_transcript.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Clear context is provided: the tool projects cues into shots, and it will refuse if a cue's word was cut, with a directive to fix it via cue_rm/cue_add first. It also gives practical guidance on the fps parameter for export alignment, but it does not explicitly state when to prefer this tool over alternatives or list exclusions.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

canvasA
DestructiveIdempotent

Read or change the shape this project renders at.

The canvas is project state and every frame size derives from it — the MLT profile and the captions' reference canvas both read it, so a project cannot quote caption sizes against one shape and render another. Call it with no size to read what is in force plus the footage-derived shape it would fall back to; reset drops the override and returns to that shape.

size is "WIDTHxHEIGHT", e.g. "1080x1920" for a vertical reel. Both edges must be even.

Setting one has a routing consequence, reported as routes_through: an overridden project renders through the MLT writer whatever its source count, because auto-editor cannot be handed a canvas it will honour. An override that changes the aspect crops to fill rather than pillarboxing, so cropped names every clip that loses footage to it — use reframe to see or change which part of each one is kept.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
sizeNo`WIDTHxHEIGHT`, e.g. `1080x1920` for a vertical reel. Both edges must be even. Omit it to read what is in force plus the footage-derived shape it would fall back to.
resetNoDrop the override and return to the footage-derived shape.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.9/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations flag `destructiveHint` and `idempotentHint`; the description goes beyond by detailing the routing consequence (override forces MLT writer), the cropping behavior (aspect change crops to fill, not pillarbox), and the side‑effect on caption quoting. It even mentions the `plan` flag as a safer alternative, which is exactly the kind of operational detail an agent needs. No contradiction with annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is moderately long but every sentence is packed with unique, actionable information. It is front‑loaded with the core purpose, then flows naturally into call patterns, behavioral consequences, and parameter details. There is no fluff or redundancy.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a state‑changing tool with subtle rendering implications, the description covers everything: what it does, when to call it, what happens on override (routing, cropping), how to preview safely, and which sibling to use for fine‑grained adjustments. The presence of an output schema and rich parameter descriptions further reduces any missing context. Nothing essential is left out.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The input schema already covers all four parameters with detailed descriptions (100% coverage). The main description adds extra meaning for `size` (even edges, vertical example) and `reset` (drops override), and explains the consequences of setting a size (routing, cropping). This goes beyond the schema, so a 4 is warranted; it stops short of a 5 because the schema already does much of the heavy lifting.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb-resource pairing ('Read or change the shape this project renders at') and goes on to explain exactly what the canvas is, how it relates to project state and rendering, and why it matters (caption quoting consistency). It also names a related tool (reframe) for a specific sub‑task, which distinguishes it from siblings without needing to list them.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives explicit call patterns: reading with no `size`, resetting with `reset`, and using `plan` to preview. It also tells the agent when to delegate to `reframe` for changing which part of a crop is kept, effectively stating when not to use this tool. This is model guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

caption_span_addA
Idempotent

Captions off over a stretch of the film, or a different look there.

off=True draws none (over an end card or logo). style changes caption_style fields over the span only; {"max_words": 1, "size": 150, "position": "middle"} over one word draws it alone and large, a beat inside ordinary lines. Addressed like overlay_add: start at a word, phrase or event; end at a word, phrase, event or length. A line never crosses a span's edge; later spans win where two overlap. caption_view draws the result; add_captions writes it.

ParametersJSON Schema
NameRequiredDescriptionDefault
offNoDraw no captions over the span. Give this or `style`.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
afterNoA forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start.
eventNoStart on this event of clip_id: `name`, or `name#k` when the name repeats.
styleNocaption_style fields (any but `preset`) that differ over the span, on top of the project's look: {"max_words": 1, "size": 150, "position": "middle"} draws each word alone and large. Give this or `off`.
phraseNoStart on this phrase's FIRST word, resolved against clip_id's transcript.
clip_idYesThe clip whose words or events address the span — the transcript the word indices index, or the recording the events belong to.
secondsNoEnd this long after the start.
occurrenceNoDisambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at.
word_indexNoThe word the span starts on. One of word_index, phrase or event.
until_eventNoEnd on this event of clip_id.
until_phraseNoEnd as this phrase's LAST word ends.
until_word_indexNoEnd as this word ends. One of until_word_index, until_phrase, until_event or seconds.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the annotations, the description discloses important behavior: span-only style changes, line-breaking never crossing span edges, later spans winning on overlap, and where the result is drawn versus written by add_captions. The idempotent and non-destructive hints are not contradicted.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but compact, front-loading the core purpose and then adding only high-value operational details: mode semantics, an example, addressing approach, overlap behavior, and downstream tools. No sentence is filler.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's complexity — 14 parameters, multiple start/end addressing modes, and overlap semantics — the description is complete enough for an agent to call it correctly. It covers the mode selection, span boundaries, overlap resolution, and the relationship to caption_view and add_captions, while the schema handles parameter details and the output schema handles return values.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

With 100% schema description coverage, the schema already documents every parameter. The description adds valuable structural context by summarizing the addressing model (start at word/phrase/event, end at word/phrase/event/length) and by clarifying the off-vs-style relationship. This is an enhancement over the schema rather than a necessary compensation.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The opening sentence states a specific action and resource: applying either no captions or a different caption style over a film stretch. It then names the two modes (off and style) with a concrete example and distinguishes the tool from caption_view and add_captions by clarifying the pipeline roles.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives clear contextual guidance: off is for end cards/logos, style is for temporary per-span caption_style changes, and the one-word example illustrates a typical use. It also points to overlay_add for addressing semantics. It does not explicitly state when not to use the tool or name an alternative span-editing tool, so it stops short of a perfect 5.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

caption_span_lsB
Read-onlyIdempotent

Every caption span, later ones winning, with where each plays now. Read-only.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

B3.2/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint and idempotentHint, and the description's 'Read-only' merely repeats that. But it adds genuinely new behavioral detail: 'later ones winning' indicates precedence among overlapping spans, and 'where each plays now' describes the current placement. These go beyond the annotations and outline non-obvious behavior.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact and free of filler; every clause contributes meaning except 'Read-only,' which duplicates the annotation. The phrasing is terse to the point of being cryptic, but the structure is appropriately short.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given that an output schema exists and the path parameter is fully documented, the description covers the essential semantic points: it enumerates spans, expresses precedence via 'later ones winning,' and indicates positional output. It does not elaborate on ordering or format, but the output schema can carry that burden.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, and the single `path` parameter is documented thoroughly in the schema itself. The description adds no parameter information, which is acceptable under the baseline for fully documented schemas.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose3/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description identifies the resource ('every caption span') and one returned attribute ('where each plays now'), so an agent can infer this is an inventory/list operation. However, it never states an explicit verb such as 'list' or 'return,' and 'later ones winning' is unexplained shorthand that could confuse an agent about what the tool actually does.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

No guidance is given about when to use this tool versus siblings like caption_span_add, caption_span_rm, or caption_view. The read-only annotation implies it is safe for inspection, but the description does not state selection criteria or mention alternatives.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

caption_span_rmA
Destructive

Remove the caption span at position, as caption_span_ls numbers it.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
positionYesThe span to remove, by its position in caption_span_ls.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A3.9/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare destructiveHint=true and readOnlyHint=false, so the description is not burdened with establishing basic safety. The description adds little beyond restating the destructive action in prose, and it does not note side effects such as irreversibility or impacts on related spans. With annotations in place, this is acceptable but not enriching.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is a single front-loaded sentence with no filler. Every word contributes to identifying the action, the target, and the position source. It is an exemplary concise definition.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a simple destructive removal tool with one required parameter, the description is complete: it names the resource, the parameter, and the source of valid positions. Annotations cover the destructive/read-only safety profile, and the output schema plus fully documented parameters cover call details. No critical information is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so all three parameters are already documented. The description's mention of position reuses the same semantics already present in the schema ('by its position in caption_span_ls') and adds no further meaning. Baseline 3 is appropriate because the schema carries the parameter documentation burden.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description names a specific action (remove) and resource (caption span), and anchors the position parameter to caption_span_ls, making its purpose immediately clear. It also distinguishes itself from the sibling caption_span_add and caption_span_ls tools without needing to open their schemas.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The phrase 'as caption_span_ls numbers it' implies the correct workflow: obtain the position from a listing first. However, it does not explicitly state when to prefer this tool over an alternative, nor does it mention the available plan-based dry-run as a safer path despite destructive annotations. Usage guidance is implied rather than fully articulated.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

caption_styleA
DestructiveIdempotent

Read or change the caption look this project keeps.

The style is project state and the captions are derived from it, so a restyle survives every later cut: regenerating re-reads this. Call it with no arguments to read the current look and learn the field names; any argument sets that field and leaves the others alone. reset drops every override first — reset plus preset starts clean from a preset.

preset is the base look ("clean", "karaoke" for per-word highlight, "reveal" for words landing mid-frame and fading in as spoken, or "boxed"); everything else overrides one of its fields, and only the overrides are stored. reveal ("fade", "blur" or "none") is how each word arrives.

Colours take "#rrggbb", "#rrggbbaa", a name ("yellow", "white", "red", …) or an ASS "&H…" value. text is the word's colour and highlight what it turns as it is spoken, which only shows with karaoke on. position is named: "bottom", "top", "top-right", and so on. Both come back resolved, because ASS quotes colours backwards and alpha-inverted.

plan validates and resolves without writing. Use caption_view to see the result on the actual timeline.

ParametersJSON Schema
NameRequiredDescriptionDefault
boxNoDraw an opaque box behind the words. It buys legibility over light footage — white captions over the film's own light cards measure 1.10:1 without one — and costs clean edges, since libass draws one box per override block.
boldNoDraw bold.
fontNoFamily name to draw with. Whether it actually draws is a different question from whether it is installed — `fonts` measures a render, and libass substitutes silently at exit 0.
holdNoHow long a cue lingers after its last word, in seconds.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
sizeNoType size, against the project's canvas as the reference frame.
textNoThe word's own colour: `#rrggbb`, `#rrggbbaa`, a name, or an ASS `&H…` value. It comes back resolved, because ASS quotes colours backwards and alpha-inverted.
resetNoDrop every override first. `reset` together with `preset` starts clean from that preset.
marginNoDistance from the frame edge, in canvas pixels.
presetNoThe base look: `clean`, `karaoke` (per-word highlight), `reveal` (words land mid-frame, fading in as spoken) or `boxed`. Everything else overrides one of its fields, and only the overrides are stored.
revealNoHow each word arrives as it is spoken: `fade`, `blur` (blurs and fades in; the outline returns at the end), or `none`. The line is laid out whole from the start, so nothing moves.
shadowNoDrop-shadow distance.
karaokeNoFill each word as it is spoken. The fill is left-to-right within a line rather than a per-word step, which is what the grouping fields below shape.
max_gapNoStart a new cue when the silence between two words exceeds this many seconds.
positionNoWhere captions sit, named: `bottom`, `top`, `top-right` and so on.
highlightNoWhat a word turns as it is spoken. It only shows with `karaoke` on.
max_wordsNoMost words in one caption cue. Grouping is part of the look, which is why it is stored with it.
reveal_msNoHow long a word's reveal takes, in milliseconds. Default 150. Needs a reveal.
box_colourNoColour of the box behind the type, when `box` is on.
reveal_blurNoHow blurred a word starts under `reveal=blur` (ASS `\blur`; a gaussian of 0.85 x this in canvas pixels). Default 6.
max_durationNoLongest a single cue stays on screen, in seconds.
outline_widthNoOutline thickness. With no box this is what holds the words apart from the picture.
outline_colourNoColour of the outline around the type.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.3/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations mark destructiveHint=true and readOnlyHint=false, and the description adds meaningful context: `reset` drops overrides, the style persists across cuts, and colors come back resolved due to ASS quirks. It also highlights the non-destructive `plan` path. This goes beyond the annotations without contradicting them.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but highly structured: it leads with the core purpose, then explains argument semantics, presets, colors, and validation/viewing alternatives. Every paragraph serves a clear function and no sentence is redundant. It is efficiently organized for a tool with 24 parameters.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's complexity (24 params) and that an output schema exists, the description covers the essential concepts: read vs. set, reset behavior, preset override model, color resolution, and how to validate/view. It doesn't enumerate every parameter, but the schema already does. The description supplies the conceptual glue an agent needs to use the tool correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3. The description enhances understanding by explaining the preset system (e.g., only overrides stored), how `reset` interacts with presets, and the meaning of color formats and position names. It ties parameters together conceptually (e.g., `reveal` needs a reveal_ms, `highlight` shows only with karaoke), adding value beyond the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a precise verb+resource pair: 'Read or change the caption look this project keeps.' It clearly distinguishes itself from sibling tools like caption_view (which shows the result), caption_style_save/load (persistence), and caption_style_library (storage). An agent can immediately understand the tool's role.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Provides explicit invocation patterns: call with no arguments to read, with arguments to set fields, and describes reset behavior. It also names `plan` for validation without writing and points to caption_view for visual confirmation. However, it does not explicitly exclude use cases for the persistence-related siblings, so it's not a full 5.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

caption_style_libraryB
Read-onlyIdempotent

Every caption look saved to this machine's library, each with what it resolves to.

ParametersJSON Schema
NameRequiredDescriptionDefault

No parameters

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

B3.1/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true, idempotentHint=true, and destructiveHint=false, covering safety. The description adds the context that it is a library of caption looks with resolution behavior ('each with what it resolves to'), which is useful. Since annotations carry the safety profile, a 3 is appropriate; it adds some behavioral detail but not much beyond that.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is a single concise sentence, front-loaded with the resource. It is efficient, but the phrase 'each with what it resolves to' is a bit cryptic and could be clearer, but it doesn't waste words.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness3/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The tool is simple with no params and a rich output schema presumably (has output schema=true). The description doesn't need to explain return values if the output schema covers them. However, given the large sibling set, it could better explain its relationship to related tools and the nature of 'resolution' to be fully complete.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The tool has 0 parameters, so the description carries no param burden. The baseline for 0 params is 4, and the description provides enough context about the content (caption looks with resolutions) without needing param details. No issue here.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose3/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description says it lists caption looks saved to the library, which is a clear resource. But it doesn't explicitly state the action (list/access) beyond the name, and it doesn't differentiate from sibling tools like caption_style_save or caption_style_load. The phrase 'each with what it resolves to' hints at mapping but is ambiguous.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

There is no explicit guidance on when to use this tool versus alternatives like caption_style or caption_style_load. It implies it's for browsing the library, but doesn't state when to choose it over siblings. A user would have to infer its purpose relative to others.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

caption_style_loadB
DestructiveIdempotent

Make a saved caption look this project's, replacing the one it has. Undo reverts it.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameYesThe saved look to use (caption_style_library lists them).
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

B3.2/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already mark the tool as destructive and non-read-only; the description adds useful specifics by stating it replaces the project's current style and that undo can revert the change. This gives an agent a clearer risk picture than the annotations alone.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness3/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is very short and front-loads the key behavior plus undo. However, the first sentence is awkwardly phrased and would be clearer with a noun like 'style' or 'look' explicitly resolving what is replaced.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness3/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The schema and output schema cover parameters and return shape, so the main description does not need to explain those. It is missing a clearer statement of its relationship to caption_style_save and caption_style_library, and the ambiguous purpose wording leaves an agent to infer exact semantics.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the parameters are already well-documented. The main description adds no further parameter-level detail, which is acceptable given the rich schema descriptions for name, path, and plan.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose3/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description implies the tool applies a saved caption look to the project and replaces the current one, but the phrase 'Make a saved caption look this project's' is ungrammatical and obscures the subject/object relationship. It does not distinguish itself from similar sibling tools like caption_style_save beyond the 'replacing' wording.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Usage is implied: use this tool to apply a saved caption look to the project. However, there is no explicit guidance on when to choose this over alternatives, and no exclusions or prerequisites are stated. The 'Prefer plan' note in the schema adds some operational guidance but does not address tool selection.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

caption_style_saveA
DestructiveIdempotent

Save this project's caption look to this machine's library, so any project can load it.

The preset and every override on it are saved, grouping rules included.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameYesWhat to call the look in this machine's library: lowercase letters, digits, - and _.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
replaceNoReplace a saved look of this name. Unset, a taken name is refused.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.3/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The description adds machine-local library scope, the fact that the preset plus every override and grouping rule are saved, and that the result can be loaded by any project. These details go beyond the annotations' write/destructive hints and clarify what a save actually captures.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Two brief sentences with the main action and machine-local scope front-loaded. The second sentence earns its place by specifying exactly what is captured, with no filler or redundancy.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a three-parameter write tool with full schema coverage, rich annotations, and an output schema, the description covers purpose, scope, and saved content. Nothing an agent needs to call it correctly is missing; path/name/replace behaviors are already documented in the schema.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, and the description does not attempt to re-explain name, path, or replace; the schema descriptions already define constraints and defaults. The overrides/grouping-rules note is about save scope, not parameter semantics, so it adds no parameter-level meaning beyond the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific verb ('Save') and resource ('this project's caption look') and clarifies the destination ('this machine's library') and purpose ('so any project can load it'). This clearly distinguishes it from sibling caption-style tools without requiring schema inspection.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description clearly frames when to use the tool: when the current project's caption look should be persisted for reuse across projects. It doesn't explicitly name alternatives or when-not-to-use cases, but the context makes the intended invocation obvious.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

caption_viewA
Read-onlyIdempotent

The captions this timeline would produce, and the style in force.

add_captions without writing a file: the same cues, in timeline seconds, already grouped by the project's own break rules — so this is how to check a restyle, or read back what a caption actually says at some moment, before committing a file to it.

Reports rather than refuses: a project with no transcript, or one whose every word has been cut, comes back with an empty cues and a cues_error saying which. Read-only.

cues is a window of limit from first; cues_total is how many the film has and cues_next, when present, where to continue. Use locate to find the cue at a moment rather than paging to it.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
firstNoIndex of the first cue to return. 0 by default.
limitNoMost cues to return; `cues_next` says where to continue.
clip_idNoShow one transcript's captions rather than every clip's.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true, destructiveHint=false, and idempotentHint=true. The description adds beyond this by explaining that it reports rather than refuses (empty `cues` and a `cues_error` for missing transcripts) and describes the pagination fields (`cues_total`, `cues_next`). It also notes that cues are grouped by the project's break rules. This is useful behavioral context not covered by annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact and each sentence serves a purpose. It front-loads the core purpose, then usage, then error behavior, then pagination. No fluff; every line contributes to accurate tool selection and invocation.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given that an output schema exists, the description still explains the important return fields (cues, cues_error, cues_total, cues_next) and how to navigate them. It addresses edge cases (missing transcript) and recommends an alternative for time-based lookup. For a read-only tool, this is complete.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the baseline is 3. The description adds meaning by explaining the relationship between `first`, `limit`, and `cues_next` (a window of `limit` from `first`), and suggests using `locate` instead of paging. It also clarifies that `cues` is a window, which goes beyond the individual parameter descriptions.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific purpose: it returns the captions a timeline would produce along with the active style, and explicitly contrasts itself with add_captions (which writes a file). This clearly distinguishes it from siblings like caption_style or cue_ls. The phrase 'The captions this timeline would produce, and the style in force' is a precise verb-resource pairing.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It explicitly states when to use this tool: 'this is how to check a restyle, or read back what a caption actually says at some moment, before committing a file to it.' It also names the alternative (add_captions) that writes, and recommends using `locate` for finding a cue at a moment rather than paging. This gives clear when-to and when-not-to guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

card_newA
DestructiveIdempotent

Make a card from a template: fill its slots, write the SVG, render it.

name is the <name> in card:<name> — the key a cue points at. Both the SVG source and the PNG are written under the project's assets/cards/, so the card can be re-edited later and re-rendered with card_render rather than redrawn.

A slot value is text. A newline inside one is a line break wherever the template accepts multiple lines; nothing wraps automatically, because a guessed wrap overflows the frame without saying so. Ratings are numbers out of five, to the nearest half.

Leave width/height unset unless you mean something other than this film. They default to the project's own canvas, which is what stops a card from pillarboxing inside the frame it was made for; naming a size that is not the project's is how a card loses a quarter of its width to black bar. Given at all, both must be.

Refused if a card of this name exists, unless overwrite — a cue may already point at it. Read font_warnings in the result: a template naming a face this machine lacks still renders, in a substitute, with nothing else to say so.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameYesThe `<name>` in `card:<name>` — the key a cue points at. The SVG and the PNG are both written under `assets/cards/`.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
slotsYesThe template's slots filled in, as text. A newline is a line break where the template takes several lines; ratings are numbers out of five, to the nearest half.
widthNoRender width. **Leave it unset unless you mean something other than this film** — it defaults to the project's canvas, which is what stops a card pillarboxing inside the frame it was made for. Given at all, `height` must be too.
heightNoRender height, given together with `width` or not at all.
templateYesWhich template to fill; `card_templates` lists them with their slots. A per-aspect variant file is resolved from the canvas, never named here.
overwriteNoRedraw a card of this name that already exists. Refused without it, since a cue may already point at that card.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already carry readOnlyHint=false, destructiveHint=true, idempotentHint=true. The description adds meaningful behavioral context: the overwrite refusal guard, the side effect of writing SVG+PNG to assets/cards, the non-wrapping newline behavior, and the font-substitution fallback. No contradiction with annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Front-loaded with a one-line summary, then structured paragraphs for storage, slots, size, and error/fallback behavior. Bold warning for width/height. Every sentence earns its place; no filler.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Covers purpose, storage, parameter semantics, destructive-guard behavior, and result-reading (font_warnings). Good cross-references to card_render and card_templates. Given the output schema exists, nothing an agent needs to call it correctly is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the schema already documents all parameters. The description adds marginal nuance (e.g., 'nothing wraps automatically' and the pillarboxing warning for width/height), but these largely duplicate the schema text. Baseline 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific verb+resource: 'Make a card from a template: fill its slots, write the SVG, render it.' Distinguishes from card_render and card_reauthor by naming the rendering pipeline and the storage location, so an agent can tell it apart from siblings.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Explicitly names alternatives: 're-rendered with card_render rather than redrawn' and 'card_templates lists them with their slots.' Gives concrete conditions: leave width/height unset unless you need a different size, and read font_warnings in the result. This is clear when-to-use and when-not-to-use guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

card_reauthorA
DestructiveIdempotent

Draw recorded cards again at the shape this project renders at now.

Reach for this after canvas — a card is the only thing in a project whose shape a canvas change cannot fix on its own, because the aspect is baked into the SVG it was drawn from. Re-rendering the old SVG at the new size would pillarbox the card inside the frame; this fills the template again at the new canvas, from what card_new recorded.

With no name it sweeps every recorded card the canvas has left behind, plus any whose files have gone missing. Named, it redraws that one whatever its canvas.

Read unrecorded in the result. Those are cards with files on disk and no record of what made them — nothing can re-author one, and the way to fix it is card_new with overwrite, which records it on the way past. plan reports what would change and writes nothing.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameNoOne card to redraw, whatever its canvas. Omit it to sweep every recorded card the canvas has left behind, plus any whose files have gone missing.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already mark this as destructive and idempotent; the description adds substantial behavioral detail: it sweeps all recorded cards or missing files, redraws a named card, leaves unrecorded cards untouched, and writes nothing in `plan` mode. No contradiction with the annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is organized into tight paragraphs: purpose, usage context, and result interpretation. Every sentence contributes either a behavioral fact, a routing rule, or an edge case, with no filler.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given full schema coverage, an output schema, and safety annotations, the description covers the trigger context, the sibling distinction, the unrecorded-card failure mode, and the safe planning path. Nothing needed to call the tool correctly is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The input schema already describes all three parameters at 100% coverage, including the sweep-vs-named behavior and the `plan` write-nothing behavior. The description mostly restates this rather than adding new parameter-level meaning, so the baseline 3 applies.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Draw recorded cards again at the shape this project renders at now.' It clearly distinguishes this from siblings like canvas and card_new by explaining exactly what makes card_reauthor necessary.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It explicitly says to reach for this after `canvas`, explains why a canvas change cannot fix cards, and names `card_new` with `overwrite` as the alternative for unrecorded cards. It also recommends `plan` for dry-run behavior, giving an agent clear decision rules.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

card_renderA
DestructiveIdempotent

Rasterise assets/cards/<name>.svg into the PNG card:<name> shows.

Author the SVG under the project's assets/cards/, then render it here; both files are kept, so a card can be re-edited rather than redrawn. The PNG is what a card: cue resolves to, so a card is not usable until this has run.

width/height are given together or not at all and set the render size — the document is drawn at that scale rather than rasterised and resampled — and they fit rather than distort, so a size at a different aspect from the document's comes back smaller on one axis. Omitted, the document renders at its own declared size.

Every call reports the fonts the document names and what fontconfig will actually draw. Read font_warnings: a card naming a face this machine lacks renders pixel-identically to one naming a face it has, so nothing downstream can catch the substitution.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameYesThe card to rasterise: `assets/cards/<name>.svg` becomes the PNG that `card:<name>` resolves to.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
widthNoRender width. The document is *drawn* at this scale rather than resampled, so text stays sharp, and it fits rather than distorts. Given together with `height` or not at all; omitted, the document renders at its own declared size.
heightNoRender height, given together with `width` or not at all.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.6/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations only state idempotent and destructive hints, but the description goes far beyond them: it explains that both source and output are kept, that rendering at a different scale draws rather than resamples, that fit behavior shrinks one axis on aspect mismatch, and critically warns about font substitution producing pixel-identical renders that cannot be caught downstream. This is exactly the kind of behavioral context an agent needs and that annotations do not provide.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is longer than a couple of sentences, but every paragraph earns its place: purpose, workflow, size semantics, and font warnings are each distinct and necessary. It is front-loaded with the core purpose and organized by concern, with no filler or redundancy beyond a minor overlap with schema descriptions.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's moderate complexity, a full output schema, and strong annotations, the description is remarkably complete. It covers the entire lifecycle (author → render → use), explains the size constraints with real behavioral detail, and preempts the hardest-to-detect failure mode (font substitution). An agent can call this tool correctly with no additional knowledge.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100% and the schema already documents width/height pairing and omission behavior. The description adds genuine value by explaining the non-resampling render behavior, the fit-not-distort constraint, and the consequence of aspect ratio mismatch. That extra semantic depth moves it above the baseline of 3.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Rasterise `assets/cards/<name>.svg` into the PNG `card:<name>` shows.' This clearly differentiates it from sibling tools like card_new or card_templates, which create or edit card definitions rather than render them. The purpose is unambiguous and immediately front-loaded.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives clear workflow context: author the SVG under assets/cards, then render it to make it usable; it also explains that the PNG is what a card: cue resolves to. It does not explicitly name alternatives or provide when-not-to-use guidance, but the implied usage is strong and sufficient for an agent to decide when this tool is the right one.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

card_safe_zonesA
Read-onlyIdempotent

Measure a rendered card's ink in and around a platform's reserved band.

Report only — nothing here blocks a render, and there is no default floor: SCENE_THRESHOLD's own history is that a threshold gets pinned by looking at real output, not picked cold, and this check has had exactly one look so far. platform is one of proofcut's own zones (tiktok-organic, tiktok-ads, reels, shorts, worst-case) or one an applied pack's active variant declares — pack_show lists both.

Reads card from its already-rendered PNG, never from the manifest's recorded slots alone, so the ink it measures is the ink actually on disk. Refuses a card with no PNG yet (card_new/card_render it first) or a platform neither source declares.

ParametersJSON Schema
NameRequiredDescriptionDefault
cardYesThe card to measure, read from its already-rendered PNG rather than from the recorded slots — so the ink measured is the ink on disk.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
platformYesWhose reserved band to measure against: one of proofcut's own zones (`tiktok-organic`, `tiktok-ads`, `reels`, `shorts`, `worst-case`) or one an applied pack's active variant declares. `pack_show` lists both.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.4/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint, idempotentHint, and destructiveHint false. The description adds significant behavioral context: it reads from the actual rendered PNG on disk (not manifest slots), it is report-only and does not block renders, it has no default floor for thresholds (with historical justification), and it refuses cards without a PNG. This goes well beyond the annotations and clearly sets expectations for an agent.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is front-loaded with the core purpose in the first sentence. The SCENE_THRESHOLD digression in the second sentence adds context but is tangential to immediate usage. The rest is concise and relevant. Overall it is efficient, though slightly verbose with the historical note.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a read-only, idempotent measurement tool with an output schema (not shown), the description covers all necessary operational details: prerequisites (PNG must exist), valid platform sources, the read-from-disk behavior, and refusal conditions. Nothing essential is missing for an agent to call this correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3. The main description largely repeats what the schema property descriptions already say for 'card' and 'platform' (e.g., reading from PNG, enumerating zones). It adds a minor nuance about SCENE_THRESHOLD history, but that is behavioral, not parameter-specific. No new parameter meaning is introduced beyond the schema, so a 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a clear, specific verb-resource pair: 'Measure a rendered card's ink in and around a platform's reserved band.' It distinguishes itself from siblings by being a pure measurement/report operation, and it names related tools (card_new, card_render, pack_show) that support its prerequisites. This leaves no ambiguity about what the tool does.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explains when the tool refuses to run (no PNG yet, unknown platform) and implies the workflow: render first via card_new/card_render. It also references pack_show to discover valid platforms. However, it does not explicitly contrast itself with alternative measurement tools (e.g., reframe_coverage), so the 'when to use this vs. alternatives' guidance is implicit rather than explicit.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

card_templatesA
Read-onlyIdempotent

The card templates proofcut ships, and the slots each one takes.

Read this before card_new: each slot says what it is for, whether it is required, and what it defaults to. The palette and font stacks are slots too, so a card can be restyled without authoring an SVG by hand.

Call it with no name to choose one, then with name to read only that template's slots — the whole table is long.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameNoOne template to return in full. The others come back as name and description only. Unset, every template in full.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.6/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnly, idempotent, and non-destructive behavior, so the description only needs to add context beyond that. It explains the returned structure (slots with purpose, required, defaults) and hints at response size ('the whole table is long'). This adds value without contradicting annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is moderately sized, front-loads the core purpose, and uses separate sentences for distinct points. It avoids redundancy with the schema, though it could be tightened by merging some sentences. Overall, it's efficient and well-ordered.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The tool has a single optional parameter, a clear schema, rich annotations, and an output schema. The description explains what the tool returns, how to use it, and its relationship to card_new. Nothing an agent needs to invoke it correctly is missing, even without seeing the output schema.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The schema already describes the `name` parameter with 100% coverage, including the default and effect. The description adds a usage pattern—'call it with no name to choose one, then with name to read only that template's slots'—which clarifies the intended sequence and helps the agent decide how to use the parameter.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The first sentence explicitly states the tool's purpose: it returns the card templates and the slots each takes. It differentiates from siblings by positioning itself as a prerequisite to card_new ('Read this before card_new'). This is a specific verb+resource with clear scope.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It gives explicit usage instructions: call with no `name` to choose one, then with `name` to read a specific template's slots. It also tells the agent when to use it relative to card_new ('Read this before card_new'), making the selection obvious.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

changesA
Read-onlyIdempotent

What the last steps mutations did — what undo that many times would roll back.

Read-only. Compares the snapshot every mutation already leaves against the live project. timeline.removed and timeline.added are source spans per clip with the words they carry and where they played, so a cut reads as the words it took out rather than as every later segment moving; a pure reorder is reordered; spans under 50 ms (a frame's edge moving) are only counted, in removed_slivers/added_slivers. manifest.keys lists each changed manifest key: records added/removed, and changed field by field where a record has a name (a cue by its word, a framing window by its in-point, a clip by its id); a word-addressed record echoes its word in brackets with three either side. Lists past 40 entries are cut, with exact _counts beside them. unchanged: true means the snapshot and the project agree. Words come from the transcripts as they stand now.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
stepsNoHow many mutations back to compare against, from 1 (the last one — what a single undo would roll back) up to the undo depth. The reply covers everything since that point, not only the oldest step.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.4/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true, idempotentHint=true, and destructiveHint=false, and the description reinforces this with 'Read-only.' It goes well beyond the annotations by explaining precisely how the comparison is computed, what fields appear ('timeline.removed', 'timeline.added', 'manifest.keys'), how edge cases like reorders and sub-50 ms slivers are represented, and that lists past 40 entries are truncated with `_count`s. This gives an agent a clear model of the tool's behavior and output semantics.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but every sentence contributes meaningful behavioral or output-semantic detail. It is front-loaded with the core purpose and read-only guarantee, then systematically explains output structure with concrete examples. Its length is justified by the complexity of the output, though it could be slightly more scannable with explicit field lists.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's complexity, the detailed input schemas, the annotations, and the presence of an output schema, the description is remarkably complete. It covers what the tool does, how it behaves on edge cases, what the output fields mean, truncation behavior, and the meaning of `unchanged: true`. An agent has enough context to invoke it correctly and interpret its results.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, with both `path` and `steps` already documented in detail. The tool description references `steps` in the opening sentence but adds no parameter semantics beyond what the schema provides naturally, so the baseline of 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a precise statement of what the tool computes: 'What the last `steps` mutations did — what `undo` that many times would roll back.' It then states the concrete mechanism, 'Compares the snapshot every mutation already leaves against the live project,' which clearly identifies the verb and resource. The 'Read-only' tag and the contrast with `undo` distinguish it from the sibling tool that actually performs the rollback.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives clear context for when to use the tool: to inspect what recent mutations changed and to preview what an undo would revert, without actually undoing. It does not explicitly name alternative tools or state exclusion conditions, but the 'what undo would roll back' phrasing and 'Read-only' marker make the use case reasonably unambiguous.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

check_blackA
Read-onlyIdempotent

Scan a render for black stretches, and say whether each is the known kdenlive-export tail frame (picture.KNOWN_TAIL_FRAME) or a genuine defect.

target is required — unlike check_frames, there is no cheap no-target mode; there is nothing to detect black in without a render. A run is only ever explained when it sits at the tail and the frame delta against the timeline matches the known defect exactly; a black run inside the declared picture is always reported as a real defect.

ParametersJSON Schema
NameRequiredDescriptionDefault
fpsNoThe rate the timeline's own frame arithmetic is counted on.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
pix_thNoHow dark a pixel counts as black, 0–1.
targetYesThe render to scan. Required — unlike `check_frames` there is no cheap no-target mode, since there is nothing to detect black in without a render.
min_durationNoShortest black run to report, in seconds.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.5/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Even though annotations already declare readOnly/idempotent/non-destructive, the description adds important behavioral detail: a run is only 'explained' as the known tail defect when it is at the tail AND the frame delta matches exactly; any black run inside the picture is always a real defect. This is substantive decision logic beyond what annotations reveal.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact and front-loaded: the core purpose appears in the first sentence, followed by the key usage constraint and the classification rule. Every sentence adds value and none are wasted.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

With annotations covering safety, an output schema present, and the input schema fully documented, the description supplies the remaining essential context: required target, the invariant classification logic, and the reference to check_frames. An agent has everything needed to decide when and how to call this tool correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the schema already documents every parameter. The description repeats the target-required rationale that already appears in the schema's target property, adding no meaning beyond that. Other parameters are left entirely to the schema, which is acceptable but not enhanced.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Scan a render for black stretches' and states the two possible verdicts (known kdenlive-export tail frame vs genuine defect). It distinguishes itself from sibling check_frames by name and by the absent no-target mode, so an agent can tell them apart without inspecting schemas.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It explicitly says `target` is required and contrasts with check_frames' cheap no-target mode, giving a clear condition for using this tool. It does not enumerate broader when-to-use vs when-not-to-use scenarios, but the target requirement and the classification rule provide solid contextual guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

check_framesA
Read-onlyIdempotent

Check an export's frame count against what the timeline says it should be.

The picture-side counterpart to verify, which covers only the audio. Run this on the exported NLE project before rendering — that is where it is worth the most, because the count settles whether the cut positions are right for the price of reading a document rather than encoding one.

target is an NLE project (.kdenlive/.mlt/.xml, put to melt -consumer xml) or a finished render (counted with ffprobe). Omit it to just report expected_frames, the total the timeline lays down.

Read agrees first, then delta — how many frames the target has that the timeline does not. A non-zero delta on an NLE project means the render will not be the length the edit is, and notes says so when the cause is one proofcut already knows about. agrees is null, not false, for an audio-only render: it has no frames, so nothing was checked.

fps must match the rate the export ran at or the two sides are counting on different grids; it defaults to the rate export would have picked.

ParametersJSON Schema
NameRequiredDescriptionDefault
fpsNoThe rate the export ran at. It has to match, or the two sides are counting on different grids; it defaults to the rate `export` would have picked.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
targetNoAn NLE project (`.kdenlive`/`.mlt`/`.xml`) or a finished render. Omit it to just report `expected_frames`, the total the timeline lays down. Run it on the **exported project before rendering** — that is where it is worth the most.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.9/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Even though annotations already declare the tool read-only and idempotent, the description adds substantial behavioral context: how to read the output (`agrees` first, then `delta`), what a non-zero delta implies, that `agrees` is null rather than false for audio-only renders, and when `notes` will explain a mismatch. This goes beyond what the annotations provide and significantly helps the agent interpret results.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but every sentence earns its place: purpose, positioning relative to `verify`, best timing, target forms, output-field reading order, edge case, and fps caveat. The main purpose is front-loaded, and the length is appropriate for the tool's complexity.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the annotations, full schema coverage, and the presence of an output schema, the description is complete. It covers the key behavioral edge cases an agent needs to call and interpret the tool correctly, and it names the relevant sibling alternative. Nothing essential appears missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the schema already documents all three parameters well. The description adds extra value by explaining the tooling for targets ('put to `melt -consumer xml`', 'counted with ffprobe') and reinforcing the `fps` matching constraint. It does not add much about `path`, but the schema's own description for `path` is already exhaustive.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Check an export's frame count against what the timeline says it should be.' It also distinguishes itself from the sibling `verify` by explicitly positioning itself as the picture-side counterpart. An agent can immediately tell what this tool does and how it differs from nearby tools.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives clear when-to-use guidance: run it before rendering, and explains the target alternatives (NLE project vs finished render) and what omitting `target` does. It names the sibling `verify` as the audio-side alternative and says this tool covers the picture side. These explicit conditions leave little to inference.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

clip_rmA
Destructive

Un-register a clip import_media added, when nothing depends on it yet.

Refused, naming every reason, if the clip is on the timeline, cued, held, the music bed's own clip, marked unspoken, transcribed or described — clear those first (cue_rm/hold_rm/unspoken_rm/music reset=True, or proofcut undo) or use undo back to before the import instead. The media on disk is never touched either way.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
clip_idYesThe clip to un-register. Its media on disk is never touched.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The description explains the refusal behavior in detail: it will refuse when any dependency exists and will 'name every reason'. It also adds an important safety boundary not implied by the raw destructive annotation: 'The media on disk is never touched either way'. This materially improves an agent's understanding of the tool's side effects beyond the annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is front-loaded with the core purpose, then compacts all refusal conditions and alternative tools into a second dense but scannable block. Every clause earns its place: no filler words, no repeated schema information. The code formatting and named alternatives make the long conditional list easy to parse.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a destructive, dependency-sensitive unregistration tool, the description covers the intended use window, every known blocking state, how to clear those blocks, the alternative undo route, and the disk-safety guarantee. Since an output schema exists, return-value documentation is not required from the description. An agent has enough operational information to decide when and how to call this tool correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so `clip_id` and `path` are already fully described in the input schema. The description contributes the operational context that clip_id refers to an import_media-registered clip and that media on disk is never touched, but it does not need to re-document parameter formats. A baseline of 3 is appropriate because the schema carries the parameter documentation burden.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Un-register a clip `import_media` added', which clearly identifies the tool as the inverse of import_media. The scope is narrowed with 'when nothing depends on it yet' and the disk-safety line prevents confusion with media-deleting operations. This distinguishes it from the many sibling removal tools such as cue_rm and hold_rm.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives an explicit when-to-use condition: only when nothing depends on the clip yet. It then lists the dependency states that cause refusal and names the exact alternatives (`cue_rm`, `hold_rm`, `unspoken_rm`, `music reset=True`, `proofcut undo`, or `undo`) to use instead. This is unusually clear routing between the tool and its fallbacks.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

clip_roleA
DestructiveIdempotent

Read or set a clip's import role — voiceover vs footage.

Called with no role and no reset it just reports what is stored; role must be "voiceover" or "footage" (ops.CLIP_ROLES); reset clears it back to undeclared.

This changes nothing about how transcribe/attach_transcript or describe treat the clip. Both already gate on their own evidence — a transcript file, has_video — and neither reads this field, so an undeclared clip is exactly as eligible for both as it always was. It is the assets pane's grouping, purely, and setting one is not a schema bump for that reason: an additive optional field on an existing clip record.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
roleNo`voiceover` or `footage`. Omit it and `reset` to read what is stored. It is the assets pane's grouping and nothing else: neither transcribe/describe nor any render path reads it.
resetNoClear the role back to undeclared.
clip_idYesThe clip to read or set.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.8/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the annotations, the description discloses exactly what reset destroys (the role, back to undeclared), that setting the role is additive and not a schema bump, and that downstream tools are unaffected. This is substantial behavioral context that prevents an agent from mispredicting side effects.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is front-loaded with the core purpose and then organizes modes and side-effect clarifications clearly. It is somewhat repetitive with the role parameter description (e.g., 'assets pane's grouping' appears in both), so it is not maximally concise, but every paragraph earns its place.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a tool with 4 parameters angled semantics, the description covers all invocation modes, the allowed values, the reset behavior, and the key non-effects on sibling tools. The output schema is present, so the lack of explicit return-value detail is acceptable.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100% and the schema already documents each parameter richlyging. The description adds interaction semantics between role and reset, clarifies the read mode, and names the allowed values with the ops.CLIP_ROLES constant, which goes slightly beyond the schema's individual property descriptions.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb-resource pair ('Read or set a clip's import role') and precisely defines the two possible values, voiceover vs footage. It also distinguishes this tool from likely siblings by explicitly stating it has no effect on transcribe/attach_transcript or describe.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Call modes are explicit: no role and no reset reads, role sets, reset clears. The description also gives clear when-not guidance by explaining that transcribe/describe do not read this field and that its purpose is purely the assets pane's grouping.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

contact_sheetA
Read-onlyIdempotent

Look at a clip's own head — the first look, as an image.

The sheet to call before cueing anything to a clip you have not seen. Two shots of the film were cued to a clip's own head and got 4.5s of "BASED ON THE NOVEL BY THOMAS HARRIS" over black, because nobody had looked at its first seconds. Ten seconds at 1.5s spacing by default, each tile labelled with the source second it is.

The frames come from thumbnail()'s cache — no new cache location, no new manifest key, no new web route — and the montage of them comes back here as bytes, since an agent confined to proofcut's tools (the agent panel's --tools ToolSearch) cannot open a path. import_media makes the frames for every clip it registers, so this is usually a cache hit; call it to see them, to look further than ten seconds, or to redraw after a re-import.

An audio-only clip returns frames: [] and no sheet, not a refusal — the same "nothing to look at is not a failure" as check_frames. A box without magick returns the frames and a sheet_error.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
clip_idYesThe clip whose head to look at.
secondsNoHow much of the head to cover, in seconds. Ten by default — long enough to catch credits, black or a slate before anything is cued to the clip.
intervalNoSeconds between tiles.

TDQS

A4.4/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already cover read-only/idempotent safety, but the description adds valuable edge-case behavior: returns bytes rather than a path, audio-only clips yield frames:[] without refusal, and boxes without magick return a sheet_error. It also discloses the cache origin (thumbnail()) and that no new cache/manifest/route is created.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is longer than average but front-loaded with a bolded purpose, and all parts serve a function: the anecdote illustrates the failure mode, and the middle paragraphs explain cache/bytes and edge cases. It could be tightened, but it's structured and not bloated.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Without an output schema, the description must explain return behavior, and it does: montage as bytes, audio-only returns empty frames, and missing magick yields sheet_error. It also covers integration with import_media and thumbnail cache, which is enough for an agent to invoke it correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Input schema covers all four parameters with detailed descriptions, so baseline is 3. The tool description restates defaults ('Ten seconds at 1.5s spacing by default') but adds little meaning beyond that; no parameter is explained more deeply than the schema already does.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Look at a clip's own head — the first look, as an image.' It also brands it as 'The sheet to call before cueing anything to a clip you have not seen,' which clearly differentiates it from sibling tools like thumbnail or check_frames by its role in the workflow.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives explicit when-to-use guidance: 'The sheet to call before cueing anything to a clip you have not seen' and 'call it to see them, to look further than ten seconds, or to redraw after a re-import.' It does not explicitly name alternatives or list when-not-to-use, but the context is clear enough for an agent to decide.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

continuity_acceptA
Idempotent

Acknowledge one continuity finding once — a deliberate rhyme, never re-reported every run.

Addressed the way a cue is (clip_id, word_index), plus kind, since one shot can carry more than one finding. Stores a fingerprint of the finding's own numbers; a later run whose recomputed fingerprint disagrees means the shot moved under the mark, and the finding is reported again rather than trusted blindly. Refuses when no finding of kind currently sits at that cue — continuity_check first, then accept what it found.

ParametersJSON Schema
NameRequiredDescriptionDefault
kindYesWhich finding to acknowledge: `rewind`, `replay`, `short_shot` or `stub`.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
clip_idYesThe cue's own addressing transcript, as `continuity_check` reports it.
word_indexYesThe cue's word. With `clip_id` and `kind` it is the finding's address — one shot can carry more than one finding.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The description goes beyond the annotations. It explains the idempotency behavior in detail: 'a deliberate rhyme, never re-reported every run' and the fingerprint mechanism: 'Stores a fingerprint of the finding's own numbers; a later run whose recomputed fingerprint disagrees means the shot moved under the mark, and the finding is reported again rather than trusted blindly.' This discloses a complex behavioral trait that the idempotentHint annotation only hints at, providing crucial context for the agent to understand side effects and constraints.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is well-structured: it opens with the core purpose in a clear, memorable line, then explains the addressing mechanism and the fingerprint behavior, and ends with usage guidance. It is concise, with no fluff, and each sentence adds value. The key constraint is front-loaded (acknowledge once), which is helpful for the agent's quick understanding.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The description is complete for a tool of this complexity. It has an output schema (not shown but indicated) which likely explains the return value, so that's covered. It addresses the main edge cases: the fingerprint mismatch scenario and the refusal when no finding exists. It also provides the prerequisite of running continuity_check. Given the availability of annotations (idempotentHint, destructiveHint=false) and a rich schema, the description provides all necessary behavioral and usage context an agent needs to invoke it correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The input schema already has 100% coverage with detailed descriptions for each parameter, including what values are valid (e.g., kind enum values). The description adds some context about how these parameters combine to form the finding's address: 'Addressed the way a cue is (`clip_id`, `word_index`), plus `kind`, since one shot can carry more than one finding.' This reinforces the relationship but doesn't add substantial new semantics beyond the schema. So it's a baseline 3, as the schema does the heavy lifting.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool's purpose: to acknowledge one continuity finding exactly once, preventing re-reporting. It specifies the resource (a continuity finding identified by clip_id, word_index, and kind) and the action (acknowledge). This distinguishes it from siblings like continuity_check (which reports findings) and continuity_reject (likely a different disposition), making it clear that this tool is for accepting/handling a specific finding.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description provides explicit guidance on when to use this tool: 'Refuses when no finding of `kind` currently sits at that cue — `continuity_check` first, then accept what it found.' This tells the agent to run continuity_check before accepting, and implies it should not be used if no matching finding exists. It also implies that this is the tool for accepting a finding, as opposed to rejecting (continuity_reject) or listing (continuity_ls). This is clear and actionable.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

continuity_checkA
Read-onlyIdempotent

Rewinds, replays, short shots, and film-internal-cut stubs — reports, never decides.

Rewind: a shot lands behind where its own asset last left off, with under gap seconds of timeline since. Replay: an earlier shot's source range is re-shown, gap seconds or more later — reported, never refused, because a deliberate narrative rhyme and a mistake look identical from the cue table alone. short_shot: under min_shot seconds (stills excluded). stub: a shot ends or begins right where its own footage has a real internal cut — likely a fragment rather than the shot itself.

The stored cold open (head) is walked as a pseudo-shot before the first real one, so a body shot that rewinds into the head's own footage is caught the same way a body-to-body rewind is. Overrun is never a finding: mlt.plan_picture already refuses it structurally, so nothing reaches this walk having overrun its asset.

stubs=True costs a scene-cut decode per distinct asset placed — stubs=False skips it. scene_threshold defaults to the pinned 0.15 but is caller-settable: darker footage from a different film has needed 0.12.

Findings already acknowledged by continuity_accept are dropped unless the shot moved under the mark, in which case they are kept and marked accepted_stale: True rather than silently re-suppressed.

ParametersJSON Schema
NameRequiredDescriptionDefault
gapNoHow much timeline may pass before re-showing an asset reads as a replay rather than a rewind, in seconds.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
stubsNoLook for stubs. On by default, and it costs a scene-cut decode per distinct asset placed — `false` skips that.
min_shotNoShortest a shot may run before it is reported as a short shot, in seconds. Stills are excluded.
stub_toleranceNoHow close a shot edge has to sit to its footage's own internal cut to be called a stub, in seconds.
scene_thresholdNoThe scene-cut threshold for the stub scan. It defaults to the pinned 0.15, but darker footage from a different film has needed 0.12.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond annotations that already declare readOnly/idempotent/non-destructive, the description discloses important behaviors: accepted findings can be marked accepted_stale, the cold open is walked as a pseudo-shot, overruns are structurally impossible, stubs=True has a decode cost, and scene_threshold tuning is sensitive to footage. This is rich, non-obvious behavioral information with no contradiction of the annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is longer than average, but every sentence carries distinct information: definitions, edge cases, cost implications, and acknowledgement-staleness behavior. It is front-loaded with a one-line summary and uses bold labels effectively, making dense content scannable without fluff.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a six-parameter, multi-finding analysis tool, the description covers the full decision surface: findings, parameter effects, edge cases, cost, and interaction with continuity_accept. With an output schema present, the absence of return-value discussion is acceptable; the description answers essentially any question an agent would need before calling.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3, but the description adds semantic value by wiring parameters to finding definitions: gap separates rewind from replay, min_shot defines short_shot, stubs controls the expensive decode, and scene_threshold is given a real-world tuning example. It does not add new meaning to stub_tolerance, but the schema already covers it.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The opening line names the tool's exact role: detecting rewinds, replays, short shots, and stubs, and 'reports, never decides.' Each finding type is defined in enough detail to distinguish for checking from sibling continuity_accept/continuity_reject/continuity_ls, which handle decisions and listing after the fact.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description conveys strong context for when this tool is appropriate: it is a non-deciding reporter, and it explains how acknowledged findings from continuity_accept are handled, implying the accept/reject workflow. It does not explicitly name alternatives or say 'use this instead of X,' but the never-decides framing and the continuity_accept reference make the usage context clear.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

continuity_lsA
Read-onlyIdempotent

Every accepted continuity finding, with whether it is still live and whether it still matches what was accepted (stale).

A finding that has disappeared entirely — the shot was re-cued away, or the issue was fixed — reports still_found: False rather than stale, since there is nothing live left to disagree with the mark.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true, idempotentHint=true, and destructiveHint=false, so the safety profile is covered. The description adds behavioral context about how findings are reported: it explains the difference between stale (still exists but disagrees with the mark) and still_found=False (disappeared entirely). This clarifies the output semantics beyond what annotations convey, though it doesn't discuss edge cases like empty results or sorting.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact and front-loaded: the first sentence states the core purpose, and the second paragraph clarifies a nuanced behavioral distinction. Every sentence earns its place, with no redundancy or filler. The structure efficiently conveys the tool's scope and output semantics.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the output schema exists and the path parameter is fully documented, the description covers the essential semantics of what findings are returned and the status fields. It explains the key distinction between stale and still_found, which is critical for correct interpretation. Minor details like ordering or pagination are not mentioned, but these are likely covered by the output schema. Overall, the description is complete enough for an agent to call it correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The single parameter `path` is 100% covered by the schema, including a detailed description of how it resolves when bound or unbound. The tool description does not repeat parameter details, but with full schema coverage, the baseline is 3. No additional semantic value is needed from the description.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool lists accepted continuity findings and defines the status semantics (live vs stale vs still_found). It specifies the resource (accepted continuity findings) and the verb (list), distinguishing it from continuity_accept, continuity_reject, and continuity_check. The distinction between stale and still_found adds precision, making the purpose unambiguous.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description does not explicitly state when to use this tool versus alternatives. It is implicitly the listing counterpart to continuity_accept and continuity_reject, and it contrasts with continuity_check, but no explicit when-to-use or when-not-to-use guidance is given. The semantics are clear, but the tool does not proactively route the agent away from sibling tools.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

continuity_rejectA
Destructive

Unmark a continuity finding, putting it back into continuity_check.

The inverse of continuity_accept: the acknowledgement is dropped from the manifest, so every later run reports that finding again instead of passing over it. Addressed exactly as it was accepted (clip_id, word_index, kind), and refused when no accepted finding of that kind sits there — so a second call says so rather than quietly doing nothing. Nothing on the timeline moves either way; an acknowledgement is a manifest entry, and undo puts it back.

ParametersJSON Schema
NameRequiredDescriptionDefault
kindYesWhich finding to un-acknowledge: `rewind`, `replay`, `short_shot` or `stub`.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
clip_idYesThe cue's own addressing transcript.
word_indexYesThe cue's word, with `clip_id` and `kind` the address the acknowledgement was stored under.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.3/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the destructiveHint annotation, the description discloses the full behavioral profile: the acknowledgement is dropped from the manifest, later runs report the finding again, a second call is refused rather than silently no-oping, nothing on the timeline moves, and undo reverses it. This is rich, non-redundant context that is fully consistent with the annotations (destructive=true, idempotent=false).

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Three dense sentences, each earning its place: core purpose first, then inverse/refusal behavior, then timeline and undo semantics. It is front-loaded and efficiently structured, though the second sentence is heavy with parentheticals and could be split for readability.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a destructive 4-parameter tool with an output schema present, the description covers the essential ground: what it does, when it is refused, what side effects occur, and how to reverse it. The output schema relieves it of explaining return values. Minor gaps like naming the list alternative are acceptable given the existing coverage.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3. The description adds that clip_id/word_index/kind form the address 'exactly as it was accepted,' reinforcing that they must match the prior accept call. It adds modest value over the schema but does not elaborate on the path parameter or the kind values, which the schema already documents.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

Opens with a specific verb+resource ('Unmark a continuity finding, putting it back into continuity_check') and immediately frames itself as the inverse of continuity_accept. This clearly distinguishes it from the accept/check/ls sibling cluster without ambiguity.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Explicitly names continuity_accept as the counterpart and describes the exact precondition (an accepted finding of that kind must sit there, else it is refused). It also notes that undo re-applies the acknowledgement. It does not explicitly name a sibling for viewing accepted findings (continuity_ls) or state 'use this only after an accept,' but the inverse framing carries the guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

cue_addA
Idempotent

Add a picture cue: from word_index of clip_id onward, show asset.

Or from an event of clip_id, for a recording with no words.

Source-addressed like a word range — asset is an opaque key or path, not checked against disk here; build_shots resolves it, the same way assemble_scream.py's CUES table did by hand. Refused if a cue already sits at that exact word; cue_rm it first to replace it. Echoes the resolved word plus three either side, the same convention every word-indexed tool follows.

Addressed by word_index or phrase (exactly one) — a phrase binds to its first word ("from this word onward"). after/occurrence disambiguate a phrase matching more than once; a resolved phrase is stored alongside the word index, additive metadata cue_reresolve can re-derive after a re-record.

src_start pins where inside asset the shot reads from: seconds in that asset's own source time, which is exactly the number describe_ls reports for a window. This is how a moment you found with describe gets placed — without it the shot reads from wherever the per-asset cursor had got to, which is right for re-using a clip and wrong for showing the thing you searched for.

It is an in-point and never a range: the out-point stays derived from the next cue through the edit, so a later cut still renumbers the shot correctly. The cost is a refusal instead of a rewind — if the shot's length runs past the end of the asset from that in-point, build_shots and the picture lane report it rather than quietly showing the asset's opening seconds instead. Shorten the shot with another cue, or pin earlier. A card takes no src_start; a held frame has no playhead.

dissolve and punch are the cut's effects, as cue_set sets them.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
afterNoA forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start.
assetNoWhat to show from that word onward: a registered clip id, or `card:<name>` for a card. An opaque key here, resolved by `build_shots` rather than checked against disk now.
eventNoStart the picture on this event of clip_id instead of a word: `name`, or `name#k` when the name repeats — a screen recording's logged moments, for a clip with no transcript. Not with word_index or phrase.
punchNoA scale punch from the cut, about the canvas centre: 1.1 zooms in 10%. Not with a dissolve on the same cue.
phraseNoAddress the cue by what is said instead of by index. It binds to the phrase's **first** word — "from this word onward".
clip_idYesThe transcript the cue is addressed against — the VO on a voiceover project, not the footage being shown. `asset` is what gets seen.
dissolveNoCrossfade into this cue over this many seconds: the incoming shot's frames before its in-point fade in, reaching the shot on the cue's word. Where the clip has none (an unpinned first use), the outgoing shot fades out from the word instead.
src_startNoWhere inside `asset` the shot reads from, in that asset's own source seconds — the number `describe_ls` reports for a window. An in-point and never a range: unpinned, the shot reads from wherever the per-asset cursor had got to, which is right for re-using a clip and wrong for showing the thing you searched for. A card takes none.
occurrenceNoDisambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at.
punch_easeNoThe punch's curve. Default ease-out.
punch_modeNo`in` (default) zooms to `punch` and holds for the shot; `settle` starts there and eases back.
word_indexNoThe word the picture starts on, in `clip_id`'s transcript. Give this or `phrase`, not both.
dissolve_easeNoThe crossfade's curve: linear (the default), ease, ease-in or ease-out.
punch_secondsNoHow long the punch moves. Default 0.2.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.9/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

With annotations already indicating read-write (readOnlyHint=false) and idempotent (idempotentHint=true), the description clearly adds critical behavioral context: the refusal behavior when a cue already exists at that exact word, the in-point semantics (never a range, out-point derived from next cue), and the refusal instead of rewind when the shot runs past the asset's end. It also explains the resolution of `asset` by `build_shots` rather than checking disk, and the additive metadata `cue_reresolve` can re-derive. These details go far beyond the annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but every paragraph earns its place, each addressing a distinct aspect: basic usage, alternative addressing, source addressing, in-point semantics, and effects. It is front-loaded with the core purpose and immediately gives the alternative. While dense, it uses structured paragraphs and precise terminology, making it efficient for an agent to parse. There is no fluff or repetition.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a tool with 15 parameters, 100% schema coverage, a clear output schema, and rich annotations, the description fills all major gaps. It covers what the tool does, how to address cues (word, phrase, event), what the parameters mean in context, and critical edge-case behaviors. The description integrates with the ecosystem by referencing sibling tools like `cue_rm`, `build_shots`, and `describe_ls`, and explains the output convention ('Echoes the resolved word plus three either side'). Nothing essential is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The input schema has 100% description coverage with detailed per-parameter descriptions. The tool description adds significant semantic nuance beyond those: it explains the concept of 'from this word onward' for phrase binding, the in-point semantics for src_start, and the interplay between dissolve and punch. However, some parameters like punch_ease, punch_mode, and punch_seconds are only slightly extended in the description; the schema already covers them. The description's extra value is in clarifying the overall addressing model, which the schema only hints at.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a crisp specification: 'Add a picture cue: from `word_index` of `clip_id` onward, show `asset`', and immediately provides a functional alternative for event-based cues. It clearly distinguishes this from sibling tools like cue_set, cue_rm, and cue_ls by naming the specific action and resource. The resource ('picture cue'), the addressing scheme, and the effect are all explicit, leaving no ambiguity about what the tool does.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description provides extensive usage guidance: it explains when to use word_index vs phrase, when to use event (for recordings with no words), how to replace existing cues ('cue_rm it first'), and how to place a searched moment with src_start. It even contrasts with sibling tools like cue_set (which sets effects) and build_shots (which resolves the asset). The when-not conditions (e.g., 'a card takes no src_start') and alternatives (e.g., 'cue_rm it first') are explicit.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

cue_lsA
Read-onlyIdempotent

List the picture cue table, each entry echoed with its resolved word.

Read-only. Omit clip_id to see every clip's cues. Ordered by (clip_id, word_index), not by resolved timeline position — that needs the edit's surviving ranges, which is build_shots's job.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
clip_idNoList one clip's cues. Omit it for the whole table.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.3/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already carry readOnlyHint, idempotentHint, and destructiveHint, so the description's 'Read-only' adds no new safety info. However, it adds genuinely new behavioral context: the result is ordered by (clip_id, word_index) rather than timeline position, which is a non-obvious trait an agent needs to interpret results. No contradiction with annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Three terse sentences with no filler: purpose first, then scope, then the ordering caveat and pointer to build_shots. Every sentence earns its place and the most decision-relevant fact (what it lists) is front-loaded.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a simple read-only listing tool with a rich output schema and full parameter coverage, the description is complete. It covers what is returned, scope control, ordering behavior, and where to go for timeline ordering. Nothing an agent needs to call or interpret this tool is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so both parameters are already fully documented, including path resolution semantics and the clip_id filter. The description adds a small behavioral note about omitting clip_id for the whole table, which slightly extends the schema, but the heavy lifting is done by the schema itself. Baseline 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb+resource ('List the picture cue table') and clarifies that each entry is echoed with its resolved word. It implicitly distinguishes itself from the mutation siblings (cue_add, cue_rm, cue_reresolve) by declaring itself read-only, and explicitly separates itself from build_shots over the ordering question.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It gives clear operational guidance on scope ('Omit clip_id to see every clip's cues') and explicitly routes the timeline-ordering need to build_shots, naming the alternative. It stops short of stating explicit when-not-to-use conditions versus the cue_* mutation siblings, but the read-only framing and ordering caveat give the agent enough to choose correctly.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

cue_reresolveA
DestructiveIdempotent

Re-resolve every phrase-addressed cue, unspoken mark and music-bed boundary against the current transcript, and report what moved.

A re-record replaces a clip's transcript wholesale, and every stored word_index on that clip potentially now addresses the wrong word — already true today of a plain word-index entry, and this does not close that gap for one. What it closes it for is an entry that also carries the phrase it was placed with: re-resolving says where that same wording landed now, without hand re-indexing a whole cue table.

apply=False (default): report only, nothing is written — the same posture as reframe_detect/unspoken_detect. apply=True rewrites word_index in place for every entry whose phrase still resolves to exactly one match; anything ambiguous or unresolved is reported and left untouched, never guessed. An entry with no stored phrase is reported as "action": "unchanged (no phrase to re-resolve)", not silently skipped.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
applyNoRewrite `word_index` wherever the stored phrase still resolves to exactly one match. Off by default: it reports first, and anything ambiguous or unresolved is reported and left untouched either way.
clip_idNoRe-resolve one clip's entries. Omit it for every clip.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.6/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations carry destructiveHint=true, idempotentHint=true, and readOnlyHint=false, and the description fully complements them: it discloses exactly what gets destroyed (word_index rewritten in place), the never-guess policy for ambiguous/unresolved entries, the special 'action': 'unchanged (no phrase to re-resolve)' report, and the apply=False default safety posture. No contradiction with annotations; substantial added context.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Front-loaded with the core purpose and outcome before the 'why', and the paragraphs are organized by concern (motivation, then apply semantics). It is somewhat long, but every sentence carries load — the re-record/word_index background and the no-phrase edge case earn their place. No fluff.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a destructive, state-mutating tool with three parameters and an output schema, the description is complete: it covers apply semantics, ambiguity/unresolved handling, the no-phrase case, and the path-binding behavior is already fully documented in the schema. Nothing an agent needs to invoke it correctly is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100% and each parameter is well-documented, so baseline is 3. The description adds genuine value beyond the schema by explaining the semantic requirement that an entry must carry a stored phrase to be re-resolvable, and how apply interacts with ambiguity — detail not derivable from the schema alone.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description names a specific verb ('re-resolve') and precise resource ('phrase-addressed cues, unspoken marks, music-bed boundaries') and states the outcome ('report what moved'). It is immediately distinguishable from siblings like resolve_phrase (single phrase lookup) and the unspoken_*/reframe_detect report tools because it targets the re-record/word_index-invalidation scenario explicitly.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives a concrete trigger condition (a re-record replacing a clip's transcript, invalidating stored word_index entries) and explains the apply=False vs apply=True decision, explicitly aligning the report-only posture with reframe_detect/unspoken_detect. It does not explicitly name resolve_phrase as the alternative for single-entry lookup, but the scenario framing makes routing reasonably clear.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

cue_rmA
Destructive

Remove one picture cue, addressed the way cue_add placed it.

Give word_index, or phrase to resolve against clip_id's transcript (its first word, cue_add's own binding). Refuses, listing every cue, when none sits at that word — cue_ls shows the table first. Shots re-project from the cues that remain; no other cue moves. Replacing a cue's asset is cue_rm then cue_add, since cue_add refuses an occupied word. undo puts it back.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
afterNoA forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start.
eventNoThe event the cue sits on, spelled as `cue_add` was given it.
phraseNoAddress it by wording instead; it resolves to its first word, the way `cue_add` placed it.
clip_idYesThe transcript the cue was addressed against.
occurrenceNoDisambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at.
word_indexNoThe word the cue sits on. Give this or `phrase`.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.5/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the destructiveHint annotation, the description discloses concrete consequences: refusal with a listing of cues, that no other cue moves, that shots re-project from the remaining cues, and that `undo` restores the cue. This is substantial behavioral context, not a restatement of the annotation.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact and logically ordered: purpose first, then addressing, failure behavior, side effects, replacement workflow, and undo. Every sentence earns its place and there is no filler or repetition.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a destructive mutation with seven parameters, the description covers the addressing contract, refusal and failure behavior, side effects, the replacement workflow, and recovery via `undo`. Remaining parameter details and return information are already fully covered by the 100% input schema and the existence of an output schema.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, and the schema already explains the `word_index`/`phrase` relationship, phrase resolution to first word, occurrence disambiguation, and `path` binding. The description restates the core addressing contract but adds little parameter information beyond what the schema already provides, so baseline 3 applies.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific verb and resource: "Remove one picture cue," and anchors its addressing to `cue_add`. This makes the tool immediately distinguishable from the sibling tools `cue_ls`, `cue_add`, and `cue_reresolve` without needing to inspect schemas.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It gives clear operational context: choose `word_index` or `phrase`, consult `cue_ls` first when no cue sits at the word, and explicitly prescribes `cue_rm` then `cue_add` for replacing a cue's asset. It does not explicitly exclude a sibling like `cue_reresolve`, but removal has no direct alternative tool.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

cue_setA
DestructiveIdempotent

Set or clear a crossfade or a scale punch on one picture cue, or on every cue.

Address one cue as cue_rm does, or pass every for all of them: "a scale punch per cut" is one call. dissolve crossfades into the cue (0 clears); punch scales the shot about the canvas centre from its cut (1 clears). A field not given is left alone. A punch and a crossfade on one cue are refused: the crossfade removes the cut the punch is on.

Checked against the picture plan before writing, and each crossfade is echoed: from: "outgoing" means the incoming clip had nothing before its in-point, so the fade starts on the cue's word rather than ending on it — pin the cue later into its clip (src_start) to move it. The first shot has nothing to cross from and is reported in crossfades_skipped. A vignette is not this: it is an overlay, card_new from the vignette template. plan writes nothing; undo reverses the call.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
afterNoA forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start.
eventNoThe event the cue sits on, spelled as `cue_add` was given it.
everyNoSet every cue (of `clip_id`, if given) in one call: a punch or crossfade per cut.
punchNoA scale punch from the cut, about the canvas centre: 1.1 zooms in 10%. Not with a dissolve on the same cue. 1 clears it.
phraseNoAddress the cue by wording; it resolves to its first word, as `cue_add` placed it.
clip_idNoThe transcript the cue is addressed against. With `every`, narrows to that clip's cues; omitted with `every`, every cue.
dissolveNoCrossfade into this cue over this many seconds: the incoming shot's frames before its in-point fade in, reaching the shot on the cue's word. Where the clip has none (an unpinned first use), the outgoing shot fades out from the word instead. 0 clears it.
occurrenceNoDisambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at.
punch_easeNoThe punch's curve. Default ease-out.
punch_modeNo`in` (default) zooms to `punch` and holds for the shot; `settle` starts there and eases back.
word_indexNoThe word the cue sits on. Give this, `phrase` or `event`, or pass `every`.
dissolve_easeNoThe crossfade's curve: linear (the default), ease, ease-in or ease-out.
punch_secondsNoHow long the punch moves. Default 0.2.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.8/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations mark the tool as destructive and idempotent, but the description adds substantial behavioral detail: the call is checked against the picture plan before writing, punch and crossfade on the same cue are refused, the first shot is reported in `crossfades_skipped`, and `from: "outgoing"` explains fade-direction edge cases. This goes well beyond what annotations alone provide.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but the tool is genuinely complex, and the core operation is front-loaded in the first sentence. It is organized into overview, constraints, and edge cases, though a few details such as '0 clears' and '1 clears' duplicate the schema descriptions.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a 15-parameter mutation tool with an output schema, the description covers the essential failure modes, edge cases, and alternatives. It informs the agent about plan-checking, skipped crossfades, partial updates, the punch/dissolve conflict, and the plan/undo escape hatches, so nothing critical is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100% with detailed per-parameter descriptions, so the baseline is 3. The description adds valuable cross-cutting semantics: 'A field not given is left alone', the relationship to cue_rm-style addressing, and how `every` applies a punch or crossfade per cut. These ties between the 15 optional parameters are not fully captured in the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Set or clear a crossfade or a scale punch on one picture cue, or on every cue.' It also distinguishes itself from related tools by referencing how cue_rm addresses cues and explicitly says a vignette is not this, directing to card_new instead.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives explicit when-to-use and when-not-to-use guidance: address one cue as cue_rm does or pass `every` for all cues, and use card_new for vignettes rather than this tool. It also clarifies that `plan` writes nothing and `undo` reverses the call, giving the agent alternative workflows.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

cut_by_timeA
Destructive

Cut spans of RENDER/TIMELINE time — what a human reports watching an export.

Each span is [start, end) in the seconds the current export plays at (what timeline_status/verify describe), not source time and not word indices. proofcut converts each span to the source interval(s) it plays — the inverse of the mapping captions and playback use — and cuts those through the same Edit.remove path cut_by_transcript uses. The render timestamp is never stored: the conversion happens once, here, at call time.

All spans resolve against the CURRENT timeline before any is applied, so a list of notes from one watch stays valid together even though a real cut would shift every later timestamp. Overlapping spans are refused rather than silently double-applied.

Every piece echoes the source interval it produced (more than one when the span crosses an earlier cut or a clip boundary) and the words it overlaps there, plus three neighbours either side — the human check that the timestamp actually hit the intended flub. pad widens only the OUTER edges of each requested span. plan=True resolves and reports without writing, identically to cut_by_transcript.

Refused the same way cut_by_transcript is if a span overlaps a word with a suspect duration; confirm_suspect=True or plan=True behave the same.

A second call is not the same call. These are render timestamps, and this cut moves everything after it, so the same numbers name different material next time — take them off a fresh watch rather than reusing a list across two calls. That is also why one call takes every span at once.

ParametersJSON Schema
NameRequiredDescriptionDefault
padNoWiden only the outer edges of each requested span, in seconds.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
spansYesHalf-open `[start, end)` spans in the seconds **an export plays at** — what a person reports off a watch, not source time and not word indices. Every span resolves against the current timeline before any is applied, so a list of notes from one watch stays valid together; overlapping spans are refused rather than double-applied.
confirm_suspectNoGo ahead even though a boundary word claims a suspect duration. Read the echoed words first — a suspect duration usually means whisper hid a retake inside that word, so the edge is not where it reads.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.4/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Even with the destructiveHint annotation already true, the description adds substantial behavioral detail: render timestamps are never stored, conversion happens once at call time, all spans resolve before any are applied, overlapping spans are refused, and a second call is not equivalent to the first. This is exactly the contextual disclosure an agent needs for a destructive operation.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but dense and front-loaded with the core concept before diving into details. Some content repeats what the input schema already states, but the extra length is justified by the destructive nature and the non-obvious render-time mapping.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a complex, destructive tool with one required parameter and several interdependent behaviors, the description covers the conversion semantics, resolution order, overlap refusal, output echoes, pad behavior, plan mode, suspect-word refusal, and the critical 'second call is not the same call' warning. Nothing an agent needs to call it correctly appears to be missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, and the schema already explains spans, pad, plan, path, and confirm_suspect in detail. The tool description adds some cross-cutting context about plan/confirm behaving like cut_by_transcript, but it does not substantially extend the parameter-level meaning already present in the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description names a specific verb ('Cut'), a precise resource ('spans of RENDER/TIMELINE time'), and immediately distinguishes it from source time and word indices. It also references cut_by_transcript by name, helping an agent separate the two tools.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives strong usage context: use it for what a human reports watching in an export, resolve all spans against the current timeline, and take spans from a fresh watch rather than reusing them across calls. It names cut_by_transcript as the analogous path and says this tool is not for source time or word indices, though it stops short of explicitly stating 'use cut_by_transcript instead in those cases.'

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

cut_by_transcriptA
Destructive

Cut or keep inclusive word ranges, e.g. cut=[[30, 45], [120, 131]].

Pass exactly one of cut or keep. pad widens each range on both sides in seconds, to land the cut in the silence between words. The timeline is snapshotted first, so this is undoable.

Every range echoes back the words it resolved to, plus the few words either side of it — an index one past the intended phrase reads fine on its own and is only visibly wrong next to its neighbours. pad_reach names any neighbour the padding eats, since padding is in seconds and the echoed text is not.

through_pause=True (cut only) extends each range's trailing edge through the pause after its last word, whenever that gap is wide enough to have drawn a [N.Ns] marker in the transcript pane — so cutting a phrase also removes the dead air after it instead of leaving it playing. A no-op when the trailing gap is too short to have drawn a marker.

plan=True returns that whole payload — including what the timeline would become — without writing anything. Prefer it over cutting and undoing.

Refused if a range's first or last word claims a suspect duration (see attach_transcript/transcribe's suspect_durations) — that word's end/start is what the cut boundary resolves to, and it is usually hiding a retake rather than ending where it claims. Check the word, then retry with confirm_suspect=True if the boundary is actually fine. Under plan=True these are reported as suspect_boundaries instead of refused.

ParametersJSON Schema
NameRequiredDescriptionDefault
cutNoInclusive word ranges to remove, e.g. `[[30, 45], [120, 131]]`. Pass exactly one of `cut` or `keep`.
padNoWiden each range on both sides, in seconds, so the cut lands in the silence between words rather than on them. `pad_reach` names any neighbour the padding eats.
keepNoInclusive word ranges to keep, everything else going. Pass exactly one of `cut` or `keep`.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
clip_idYesThe transcript the word ranges address.
through_pauseNoExtend each cut's trailing edge through the pause after its last word, wherever that gap was wide enough to draw a `[N.Ns]` marker — so cutting a phrase also takes the dead air after it. A no-op when the gap is short.
confirm_suspectNoGo ahead even though a boundary word claims a suspect duration. Read the echoed words first — a suspect duration usually means whisper hid a retake inside that word, so the edge is not where it reads.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A5/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the annotations' destructiveHint, the description discloses crucial behavioral traits: the timeline is snapshotted so the operation is undoable, `plan=True` writes nothing, `pad_reach` and echoed-word feedback explain boundary effects, and suspect durations trigger refusal or `suspect_boundaries` reporting. This is rich, non-obvious behavioral disclosure.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but every sentence carries distinct value: main operation first, then mutually exclusive parameters, then side effects, then safety/refusal behavior. The structure is logical and front-loaded; the length is justified by the tool's complexity.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the destructive nature, eight parameters, and existing output schema, the description is complete: it covers what happens, what not to do, how to preview safely, how to handle suspect boundaries, and how padding interacts with echoes. An agent has enough context to invoke this correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters5/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Even though schema coverage is 100%, the description substantially enriches the parameters: it explains what `pad` does in seconds, what `through_pause` means semantically, how `plan` differs from execution, and what `confirm_suspect` is for. This goes well beyond the baseline schema descriptions.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The opening sentence states a specific verb and resource: 'Cut or keep inclusive word ranges', with a concrete example showing the exact input shape. This clearly distinguishes it from the sibling `cut_by_time`, which operates on time rather than transcript word ranges.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives explicit constraints ('Pass exactly one of `cut` or `keep`'), mode-specific guidance (`through_pause=True` is cut-only, `plan=True` is preferred over acting and undoing), and a detailed refusal-and-retry workflow for suspect boundaries. These are actionable instructions an agent can follow without inferring.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

describeA
DestructiveIdempotent

Describe footage in fixed windows, so b-roll can be found by what is in it.

A description is (clip_id, src_start, src_end, text) in source seconds, which is why cutting the edit can never invalidate one. Omit clip_id to describe every video clip that has not been described yet; name one to do just that clip. Audio-only clips are refused — their words are what transcribe indexes.

This is a job, not a request. Cost is about three seconds per window regardless of how much footage the window spans, so a project's footage is minutes of GPU time. Run it with plan=True first: that resolves the whole work list and the estimate, and reports whether this machine can run the model at all, without loading anything.

Already-described clips are skipped unless force. Do not widen window to save time without a reason — a single pass over a whole clip describes six frames as six people, fluently and with nothing saying it is wrong.

Read errors and truncated in the result. A truncated description stops mid-fact and reads exactly like a complete one, and a window is never evidence of a continuous shot: the model narrates across a cut inside one as though it were a single take.

The descriptions are written into the project, and force replaces the ones a clip already has; without it an already-described clip is skipped, so a repeat costs nothing and changes nothing.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
forceNoDescribe clips that already have descriptions, replacing them. Without it they are skipped.
windowNoSeconds of footage per description. Do not widen it to save time: a single pass over a whole clip describes six frames as six people, fluently, with nothing saying it is wrong.
clip_idNoOne clip to describe. Omit it for every video clip not described yet; audio-only clips are refused, since their words are what `transcribe` indexes.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.8/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations declare destructiveHint=true and idempotentHint=true, and the description enriches both: the GPU cost model (~3s per window, minutes of project footage), that plan=True runs without loading the model and reports machine capability, that force replaces while a plain repeat costs nothing, and the two serious pitfalls — truncated descriptions read exactly like complete ones, and a window is never evidence of a continuous shot. No contradiction with annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Front-loaded with the core purpose and data model before the cost and pitfall discussion, and every sentence earns its place. Mild redundancy: the final paragraph restates the force/skip behavior already covered by 'Already-described clips are skipped unless force' earlier, which is the only trimming opportunity in an otherwise tight definition.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a complex, cost-bearing, GPU-running tool with an output schema present (so return values need not be explained), the description is remarkably complete. It covers cost, machine-capability preflight, idempotency, destructive replacement semantics, and the two failure modes an agent could not guess (truncation that looks complete, narration across cuts). Nothing an agent needs to call it correctly is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100% and the schema descriptions are already rich, so baseline is 3. The tool description adds genuine value on top: the omitting-clip_id semantics (describe all undescribed video clips), the reframe-proof rationale for source seconds, and the concrete 'six frames as six people' example that motivates not widening window. This elevates it above the baseline.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

Opens with a specific verb+resource+purpose ('Describe footage in fixed windows, so b-roll can be found by what is in it'), then pins down the data model (clip_id, src_start, src_end, text). It actively distinguishes itself from transcribe ('their words are what transcribe indexes') and describes_ls is implied by the read-the-result guidance, so an agent can tell it apart from its close siblings without opening schemas.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Explicit when-to-use and when-not: audio-only clips go to transcribe, already-described clips are skipped unless force, and it names plan=True as the preferred first invocation for a cost-bearing job. It even warns against widening window to save time. No alternative or condition is left to inference.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

describe_lsA
Read-onlyIdempotent

Read the footage descriptions, to find b-roll by what is in it.

This is the search. There is no ranking and no similarity score to ask for — you read the descriptions and pick, which is why the prompt behind them asks for concrete nouns. Each entry is (clip_id, src_start, src_end, text) in source seconds, so what you pick stays valid however the edit is cut.

contains filters: whitespace-separated terms, case-insensitive, and every term must appear — "kitchen knife" matches "a knife on the kitchen counter". Reach for it before reading everything on a large project; words says how much text came back.

Two things not to over-read. A window is evidence of what is visible in a span, never of a continuous shot — the model narrates across a cut inside one as though it were a single take. And an entry with truncated true stopped mid-fact and reads exactly like a complete description.

A clip listed under clips with windows: 0 has not been described yet; describe is what indexes it.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
clip_idNoList only this clip's windows.
containsNoKeep only windows whose text holds every whitespace-separated term, case-insensitively — so `"kitchen knife"` matches "a knife on the kitchen counter".

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.4/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already carry readOnlyHint=true, idempotentHint=true, and destructiveHint=false, so safety is covered. The description adds genuinely valuable behavioral nuance beyond that: there is no ranking/similarity score (the agent must read and choose), entries are returned in source seconds so they stay valid across edits, a window is evidence of what is visible in a span and never a continuous shot (the model narrates across cuts), and a `truncated` entry reads like a complete description but stopped mid-fact. These are exactly the kind of pitfalls an agent would otherwise misjudge.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long (several paragraphs), but every section earns its place: purpose, the no-ranking philosophy, output format in source seconds, `contains` semantics, two critical interpretive caveats (window vs. shot, truncated), and the `windows: 0`/`describe` indexing note. It is front-loaded with the purpose and structured with bold lead-ins that make it skimmable. Slightly longer than strictly necessary, but nothing is filler.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a read-only search tool with an output schema present and 3 optional params, this is complete. The output schema relieves the description of explaining return structure, yet the description still supplies the interpretive keys an agent needs: how to read entries, what `truncated` and `windows: 0` mean, and the source-seconds guarantee. No critical calling information is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100% — `path`, `clip_id`, and `contains` all carry detailed schema descriptions, so the baseline is 3. The tool description adds only marginal parameter value beyond the schema: it reinforces the `contains` semantics (already well documented in the schema) and adds the strategic advice to reach for it on large projects. It mentions the `words` output field, but that is output-related rather than parameter meaning. The schema does the heavy lifting here.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The opening line states a specific verb and resource ('Read the footage descriptions, to find b-roll by what is in it') and then boldly declares '**This is the search.**', which sharply distinguishes it from the sibling `describe` (the indexing tool) and other media tools like `transcribe`/`hear`. An agent immediately knows what this does and what it does not do — it does not rank or score, it lists descriptions to pick from.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives clear strategic guidance: 'Reach for it before reading everything on a large project' (use `contains` to filter early) and explicitly notes that a clip with `windows: 0` has not been described yet and that '`describe` is what indexes it' — routing the agent to the correct sibling. It stops short of enumerating explicit when-not-to-use conditions against other search-adjacent tools, but the context is strong enough to be actionable.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

dissolveA
DestructiveIdempotent

Set, change or clear the crossfade at a join follow made.

Addressed by the incoming clip and where it starts there, never a timeline second, so a cut elsewhere moves it. seconds=0 makes the join a cut again. Checked against the timeline before writing; plan=true writes nothing.

ParametersJSON Schema
NameRequiredDescriptionDefault
easeNoThe crossfade's curve: linear (the default), ease, ease-in or ease-out.linear
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
clip_idYesThe incoming clip of a join `follow` made.
secondsYesSeconds of crossfade; 0 clears it back to a cut.
src_startYesWhere clip_id starts at that join, in its own seconds (follow's reply says).

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already mark the operation as destructive and idempotent, and the description adds meaningful behavior beyond that: addressing is tied to the incoming clip's start position so a cut elsewhere moves the dissolve, `seconds=0` restores a cut, and the call is 'checked against the timeline before writing.' This materially helps an agent predict side effects.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact, roughly four sentences, and every sentence earns its place: the operation, the addressing model, the clearing behavior, and the safety/plan behavior. Key information is front-loaded.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a moderately complex mutation with six fully documented parameters and an output schema, the description covers the essential context: how to reference the join, how to clear the crossfade, the validity check, and the plan mode for side-effect-free dry runs. Nothing needed for correct invocation is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3, but the description adds a relationship between `clip_id` and `src_start` that the schema states only separately: the dissolve is addressed by incoming clip and its local start, never a timeline second. The `plan` parameter's dry-run behavior is also reinforced in context.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb phrase, 'Set, change or clear the crossfade at a join `follow` made,' identifying both the resource (a join created by `follow`) and the operation. It distinguishes itself from related timeline tools by explaining that the address is by incoming clip and source position, 'never a timeline second.'

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description clearly frames when to use the tool: to modify a dissolve at a follow-created join, with `seconds=0` to return to a cut and `plan=true` for a dry run. It does not explicitly name sibling alternatives or state when not to use it, but the scope is concrete enough that an agent can select it appropriately.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

doctorA
Read-onlyIdempotent

Probe every external binary proofcut depends on, and name each one's trap.

Takes no project — it answers the question asked before there is one. Report-only: nothing is installed and nothing is written. ok reads the required section alone; the four optional entries each gate one feature (cards, describe, reframe_detect, vo_synth) and everything else works without them.

Every failing entry carries the fix, not just the ✗ — where melt actually lives, why PyPI's auto-editor is the wrong program, what to set on a box with no display.

server says which project this server is bound to and how (ping's own answer), since that decides which path a call may name.

ParametersJSON Schema
NameRequiredDescriptionDefault

No parameters

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.6/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already mark readOnly, idempotent, and non-destructive, and the description adds meaningful detail: 'nothing is installed and nothing is written,' feature-gated optional sections, and failures that include fixes. This goes well beyond the structured hints without contradicting them.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is longer than strictly necessary, but each sentence contributes a distinct fact: scope, side-effect-free behavior, optional feature gates, failure messaging, and server binding. The structure is coherent and front-loads the main purpose.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a zero-parameter diagnostic with an output schema present, the description is complete. It covers what is probed, what is not touched, how output is organized, and how failing entries are reported. Nothing needed for correct invocation is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The tool has zero parameters)Skip and the schema is trivially covered. The description reinforces the only semantic point: it 'takes no project,' which is the key thing a caller needs to know.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific diagnostic action: 'Probe every external binary proofcut depends on, and name each one's trap.' It also clarifies the tool takes no project, clearly distinguishing it from project-scoped sibling tools.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives strong context for when to use it: before a project exists ('answers the question asked before there is one') and as a report-only check. It does not explicitly name an alternative tool to prefer instead, but the no-project framing is enough to route an agent correctly.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

eventsA
DestructiveIdempotent

Named instants in a recording — the anchors a screen recording has instead of words.

An event is (name, seconds into the clip's own recording): sent, typing_started, a keystroke. No clip_id counts every clip's; clip_id alone lists one clip's, each with the address other tools take (name, or name#k when the name repeats, k from 0); event resolves one address and echoes three neighbours either side.

source imports a recorder's JSON and REPLACES the clip's events of the names it brings (other names are kept), so a repeat import is a no-op and a marks file and a keystroke file combine. A recorder usually logs wall-clock stamps: pass origin naming the key that holds the recording's start. A set with any event outside the clip is refused whole, because a wrong clock moves every event by the same amount. name + at adds one event by hand.

Events index the source, so no cut invalidates one; locate with event= says where one plays now, and present: false means it was cut.

ParametersJSON Schema
NameRequiredDescriptionDefault
atNoSeconds into the recording for the one event being added.
nameNoWith `at`, the event to add. With a bare-list `source`, what those times are. One token, no '#'.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
clearNoRemove every event on this clip.
eventNoResolve one address — `name`, or `name#k` when the name repeats — and echo it with its neighbours, writing nothing.
offsetNoSeconds subtracted from every imported time, after `origin`.
originNoA key in the imported object holding the recording's zero, subtracted from every time — a recorder's clock is usually the wall clock.
sourceNoA recorder's event file to import: a JSON object of name → seconds (or → a list of seconds), or a bare list of seconds with `name`. Replaces this clip's events of the names the file brings; other names are kept.
clip_idNoThe clip whose events to read or write. Omit it to count every clip's.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

It clearly discloses destructive behavior (`REPLACES`, `clear` implied, outside-clip sets refused whole), idempotency (repeat import is a no-op), and the indexing guarantee that cuts do not invalidate events. This goes well beyond the annotations, which only flag idempotent and destructive hints, and it contradicts none of them.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense and every sentence carries substantive information, but some phrasing is terse and awkward ('No `clip_id` counts every clip's; `clip_id` alone lists one clip's, each with the `address` other tools take'). It is compact without being bloated.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the 10-parameter schema, output schema, and annotations, the description covers the critical operation modes, import semantics, edge cases, and cut-index behavior. It omits mention of `clear`, `plan`, `path`, and `offset`, but the schema fully documents those, so the overall calling contract is adequately complete for an agent.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3, and the description adds meaningful context beyond the schema: repeat imports no-op and combine named groups, an entire set is refused if one event is outside the clip, and events survive cuts without invalidation. It does not fully elaborate every parameter (e.g., offset and plan are left to the schema), but it enriches the core semantics.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description identifies events as named instants (name + seconds) and enumerates the main operations: count/list, resolve, import, and hand-add. It is clear about the resource, though the first sentence is a metaphor rather than a specific verb phrase, and it never states a single overarching action like 'manage events'.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives concrete usage patterns: omit clip_id to count, use clip_id to list, use event to resolve, use source to import, and use name+at to add. It does not explicitly contrast with sibling tools, only pointing to `locate` for checking where a cut event plays now, leaving some when-to-use guidance implicit.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

exportA
DestructiveIdempotent

Export the timeline as an NLE project, or render it.

The default writes an MLT project Kdenlive opens; export_format=null renders media. The writer is chosen from the project, never from an argument: a single-source timeline goes through auto-editor, and a multi-source one — a cue table, a second clip, a canvas, a bed, a tail — is written as MLT by proofcut and rendered by melt, because auto-editor renders a second source at 720x576 while exiting 0. The reply names the writer, and a melt render reports resolution and frame count measured off the finished file.

preset bundles quality for a render; tiktok-reels checks 9:16 and never sets the shape — use canvas first. loudness masters to a LUFS target and refuses, leaving the render as it was, if it misses by more than 1 LU.

Captions are not burned by this — add_captions is its own step. Then check the file against the timeline with check_frames and verify; a render that exists is not a render that is right.

ParametersJSON Schema
NameRequiredDescriptionDefault
fpsNoThe NLE timeline's frame rate, defaulting to the picture's own (30 for an audio-only project). It sets the render's rate too wherever proofcut owns the profile, and is ignored when auto-editor renders a single-source timeline.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
outputYesWhere to write the project file or the render. A file argument, not a project selector: it writes where you say.
presetNoA named quality bundle — `youtube`, `web`, `tiktok-reels`, or `custom` (which needs `resolution`) — meaningful only with `export_format=null`, since an NLE project file has no bitrate. `tiktok-reels` also **checks** that the project renders 9:16 and refuses otherwise; it never sets the shape. Use `canvas` for that.
loudnessNoMaster the render to this many LUFS integrated: one gain and a true-peak limiter, measured before and after, and refused — leaving the render as it was — if the result misses by more than 1 LU. Render only.
true_peakNoThe dBTP ceiling the loudness pass limits under. -1.0 by default.
resolutionNo`[width, height]`. It **letterboxes** the existing frame on the single-source render path rather than cropping or reframing it, and is refused outright on a melt (multi-source) project.
export_formatNo`kdenlive` (the default) writes an MLT project Kdenlive opens and melt renders. Pass null to render media instead. Other auto-editor targets — shotcut, premiere, resolve, final-cut-pro — pass straight through.kdenlive

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A5/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations mark this as destructive and non-read-only, but the description goes far beyond: it explains that the writer is chosen from the project (never from an argument), details the single-source vs multi-source behavior, the resolution letterboxing vs refusal, the loudness refusal condition, and the safety rule about paths outside the bound project. It also notes that a render that exists is not necessarily correct, implying the need for verification. No contradiction with annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but every sentence earns its place. It is front-loaded with the core purpose, then progresses through writer selection, presets, loudness, and post-export verification. No fluff or repetition. The length is justified by the complexity of the tool (8 parameters, multiple modes, and interactions).

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's complexity, the description is complete. It covers the main modes, writer selection, parameter interactions, destructive behavior, and directs the user to complementary tools. The output schema exists, so return-value details are not required. An agent can correctly invoke this tool without additional documentation.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters5/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3, but the description adds substantial semantic value. It explains parameter interactions: preset is meaningful only with export_format=null, tiktok-reels checks 9:16 and never sets shape, resolution letterboxes on single-source and is refused on multi-source, loudness is render-only, fps is ignored when auto-editor renders single-source, and path resolution rules. These are critical operational details not present in the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb-resource pair ('Export the timeline as an NLE project, or render it') and immediately clarifies the two modes. It distinguishes from siblings by explicitly stating captions are not burned (add_captions) and mentions verification tools. The writer-selection logic based on project composition further sharpens the tool's unique role.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives explicit when-to-use and when-not-to-use guidance. It says captions require add_captions as a separate step, and recommends check_frames and verify after export. It also warns that tiktok-reels preset never sets the shape and directs to use canvas first. This routes the agent to the correct tools for each sub-task.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

film_checkA
DestructiveIdempotent

Compare this project against the export it is supposed to be.

check_frames answers whether an export agrees with this project's own arithmetic; it cannot catch this project being the wrong film to begin with — a project can pass every check it has and still be seeded from a stale stage of an outside edit (HISTORY.md § The VO the project was holding: 73 segments/410.963s sat in a project whose shipped film was 63 segments/336.269s, with the render, verify, the cue table and the shot plan all agreeing with the wrong one). This checks the project's timeline_duration against a reference file's own ffprobe duration — cheap, no frame counting, no melt. Segment count has nothing on the reference side to compare against once a film is encoded, so segments is reported alone and the notes say why.

reference is remembered: passing it stores it on the project (additive, no schema bump), so a later call with no argument re-asks the same question against the same file. reset drops the stored reference; plan resolves without writing. With no reference given or stored, this reports the project's own numbers and says there is nothing to compare them against, rather than raising.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
resetNoDrop the stored reference.
referenceNoThe delivered file this project is supposed to be. It is remembered, so a later call with no argument re-asks the same question against the same file.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.5/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the annotations, the description discloses important stateful behavior: 'reference is remembered: passing it stores it on the project', 'reset drops the stored reference', and 'plan resolves without writing.' It even specifies that the check is 'cheap, no frame counting, no melt' and explains what happens when no reference is present, which adds valuable context the annotations do not provide.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness3/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is front-loaded with purpose but becomes overly long, including an extended HISTORY.md anecdote that is not necessary for selecting or invoking the tool correctly. The paragraph on segment counts and the detailed example add noise, though the structure is logical and organized.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the output schema exists, return values need no explanation, and the description covers all essential behavioral edge cases: no reference, stored reference, reset, plan, and what exactly is compared. Nothing an agent needs to call this tool correctly is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

All parameters already have rich descriptions in the input schema, so baseline is 3. The description primarily repeats what the schema says (e.g., reference is remembered, reset drops it, plan resolves without writing). It adds no new parameter-level meaning beyond the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific verb and resource: 'Compare this project against the export it is supposed to be.' It also explicitly distinguishes itself from the sibling check_frames by explaining what each tool can and cannot catch, so an agent can tell them apart without opening schemas.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explicitly contrasts film_check with check_frames, identifying the key difference: check_frames validates against the project's own arithmetic, while film_check compares against an external reference file. It also describes behavior in the no-reference case ('reports the project's own numbers and says there is nothing to compare them against') and names the plan and reset alternatives for safe operation.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

finish_checkA
Read-onlyIdempotent

Check a delivered file against this project's timeline — verify/check_frames/check_black/film_check for a file an external mix pass produced, not one of proofcut's own renders.

final carries a cold open and/or holds concatenated on outside proofcut, so every position this reports is in final's own absolute seconds. prepend_seconds defaults to this project's stored head length; holds defaults to its stored holds, resolved live and offset the same way — pass either explicitly (an empty holds list included) to check a file against a different set than what is currently stored.

Eight checks, none individually fatal to the others: stream/chapter/ duration agreement against the timeline's own arithmetic; loudness (report only); blackdetect, with a run explained only when it falls inside the prepend or a hold's own span; each hold's own span transcribed and its seam levels measured; a windowed transcription of final diffed against the timeline's expected words, with every heard word inside the prepend or a hold filtered out first; every dropped run re-cut and re-transcribed on its own to catch a windowed-pass false miss at a window stitch (boundary_misses, recovered — a run that still cannot be found stays in missing, a real fault); and a self-repeat scan over the same filtered transcript. faults/ok aggregate all of it, and every run is logged (finishlog) so proofcut review serve can show a WARN badge keyed to the file's own sha256.

ParametersJSON Schema
NameRequiredDescriptionDefault
fpsNoThe frame grid the timeline's arithmetic is counted on. Defaults to the rate `export` would have picked.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
finalYesThe delivered file to check — one an external mix pass produced, not a proofcut render. Every position reported is in this file's own absolute seconds.
holdsNoThe holds to expect in `final`, resolved and offset the same way the stored ones are. Defaults to the project's own; pass a list (an empty one included) to check against a different set.
pix_thNoblackdetect's pixel threshold: how dark a pixel counts as black.
windowNoLength of each transcription window, in seconds.
clip_idNoDiff against one transcript's expected words rather than all of them.
overlapNoHow far each window overlaps the one before, in seconds.
languageNoForce a language code for the transcription.
recheck_padNoHow much to pad a dropped run when re-cutting it for its own transcription — the pass that separates a real miss from a false one at a window stitch.
windowed_modelNoThe whisper model for the windowed transcription of `final`. A deliberately small one is the default, since the windowed pass runs over twice the audio.
prepend_secondsNoHow much runs before the timeline's first frame in `final` — a cold open concatenated on outside proofcut. Defaults to the project's stored head length.
transcript_pathNoAn existing transcription of `final`, to diff again without re-transcribing.
black_min_durationNoShortest black run to report, in seconds.
duration_toleranceNoHow far `final`'s duration may sit from the timeline's own arithmetic before it is a fault, in seconds.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.4/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already establish readOnly/idempotent/non-destructive, and the description adds substantial non-redundant behavioral context: the full inventory of eight checks with their semantics (loudness is 'report only', blackdetect runs are 'explained only when it falls inside the prepend or a hold's own span'), the window-stitch false-miss recovery behavior (`boundary_misses`, recovered), the aggregation into `faults`/`ok`, and the `finishlog` side effect enabling `proofcut review serve` WARN badges keyed to sha256. No contradiction with annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness3/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The core purpose is front-loaded in the opening sentence and nearly every sentence earns its place given the tool's eight-check complexity. However, the body is one dense ~170-word paragraph built from slash-chains and semicolons that is genuinely hard to scan; the eight checks could be enumerated or broken into digestible chunks. The information is justified, but the structure is not.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a 15-parameter tool with an output schema, the description is unusually complete: it covers the coordinate/time-base semantics, the default resolution of `prepend_seconds` and `holds`, the per-check behavior including what is report-only versus fatal-adjacent, recovery mechanics, and the logging/observability contract. The output schema covers return values and the 100%-coverage schema covers parameter mechanics; the only residual gap is that the density of the checks paragraph still demands careful reading, but nothing operationally necessary is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3, but the description clearly exceeds it: it explains the coordinate system binding `final`, `prepend_seconds`, and `holds` together ('every position this reports is in `final`'s own absolute seconds'), clarifies that `prepend_seconds`/`holds` default to stored project values with live offset resolution, and gives purpose to `recheck_pad` ('the pass that separates a real miss from a false one at a window stitch') and `windowed_model` ('runs over twice the audio'). This is genuine semantic value beyond the schema's field-level descriptions.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb+resource pair ('Check a delivered file against this project's timeline') and immediately differentiates from siblings: it is the `verify`/`check_frames`/`check_black`/`film_check` equivalent 'for a file an external mix pass produced, not one of proofcut's own renders.' An agent can unambiguously distinguish this from its four named sibling tools without opening schemas.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The first sentence establishes the selecting condition — external mix pass deliverables versus proofcut's own renders — which implicitly routes proofcut renders to verify/check_frames/film_check. It also gives explicit guidance on when to override defaults: 'pass either explicitly (an empty `holds` list included) to check a file against a different set than what is currently stored.' It stops short of an explicit when-not statement naming the alternative for proofcut renders, so it is clear but not fully explicit.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

finish_reportA
Read-onlyIdempotent

Duration/canvas/caption/picture/marks/seams report for Finish mode, composed only — the truth strip's own numbers.

duration: edit seconds, tail seconds, and their sum. canvas: the stored or footage-fallback canvas, plus each export preset's own ok/refusal-message. captions: whether a style is configured, its resolved font, and whether the last render actually burned it in ("yes"/"no"/"unknown" — unknown when no render log exists). picture: cue count, pinned count, and the picture plan's own refusal message when it has one. marks: unspoken marks applied vs. still stale. seams: the transcript's own overlap count. unused_clips: registered clips on no lane, cued nowhere, held nowhere, not the music bed — a clip imported and forgotten (TRIAL.md § Registered-and-not-on-the-timeline has no report of its own), clearable with clip_rm or by cueing it. flags: the rolled-up warnings behind all of the above, each one naming the mode that fixes it.

framing adds reframe_coverage's stale-framing numbers and their two flags, and is off by default because it decodes placed footage for a scene-cut scan — 5.7s wall and 46s of CPU on the film, uncached, every call. Off, framing is None, which means "not measured" rather than "nothing stale".

holds adds hold_check's own per-hold seam/transcription report against the last render — off by default for the same reason framing is: it decodes and transcribes render spans. None when not asked for, and also None when asked for but nothing has rendered here yet.

continuity adds continuity_check's finding count by kind (rewind, replay, short_shot, stub) and how many are currently accepted — also off by default, its stubs=True half paying the identical scene-cut decode framing does. None when not asked for.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
holdsNoAdd the per-hold seam and transcription report against the last render. Off by default for the same reason: it decodes and transcribes render spans. Null when not asked for, and also null when nothing has rendered here yet.
framingNoAdd stale-framing numbers. Off by default because it decodes placed footage for a scene-cut scan (5.7s wall, 46s of CPU on the film, uncached, every call). Off, `framing` is null, which means *not measured* rather than nothing stale.
continuityNoAdd the continuity finding counts by kind and how many are accepted. Off by default — its stub half pays the same scene-cut decode `framing` does.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true, idempotentHint=true, and destructiveHint=false, so safety is known. The description adds substantial behavioral context beyond that: it explains the cost of optional sections (5.7s wall, 46s CPU for framing), the meaning of None (not measured vs. nothing stale), and the special semantics of unused_clips and its clearable methods. No contradiction with annotations; instead, it enriches the behavioral model.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but exceptionally well-organized: it opens with a one-line summary, then uses a bulleted list for the core sections, and separately details the optional flags with their costs. Every sentence earns its place; nothing is redundant. The front-loading of the main purpose and the structured breakdown make it easy to scan despite its length.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The description thoroughly covers all sections and optional flags, including return semantics (None cases), performance trade-offs, and even how to clear unused clips. Since an output schema exists, the description need not spell out the return structure, and indeed it doesn't. Nothing an agent needs to decide whether to call this tool or how to set its flags is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The input schema covers all four parameters with descriptions (100% coverage), so the baseline is 3. The description adds extra nuance, especially for 'holds' and 'framing', explaining when they return None and reiterating the cost rationale. This goes slightly beyond the schema's one-liners, providing the agent with better context for deciding when to pass true.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific verb and resource: it produces a comprehensive report for Finish mode, listing the exact components (duration, canvas, captions, picture, marks, seams, unused clips, flags). It also differentiates from siblings by emphasizing 'the truth strip's own numbers' and by referencing optional sections that mirror dedicated check tools (framing, holds, continuity), making its aggregating role clear.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explains when to enable each optional section (framing, holds, continuity) and notes the computational cost for each, giving clear context for choosing to include them. It implies this tool is the go-to Finish report rather than calling the individual check tools, but it does not explicitly state 'use this instead of X' or list alternative tools for specific scenarios. Still, the cost warnings effectively guide usage.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

followA
Destructive

Put a second recording on the timeline after the first, cut or dissolved.

The window's recording, then the terminal's: clip_id plays its span spliced in after after, and everything after moves later. Words, events, retime stretches and reframe windows of either clip keep their meaning, so the incoming clip is retimed and framed like any other. dissolve seconds crossfade into it from its own frames before the in-point; the film is no longer for it. The reply gives the join and the dissolve; plan=true writes nothing, and undo takes the splice back.

ParametersJSON Schema
NameRequiredDescriptionDefault
easeNoThe crossfade's curve: linear (the default), ease, ease-in or ease-out.linear
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
afterYesThe clip on the timeline it follows — the first recording.
clip_idYesThe incoming recording, a registered clip with picture.
src_endNoSeconds into clip_id where it ends. Default its end. Not with until_event.
at_eventNoSplice in after this event of `after` (name or name#k). Omitted: after the last of `after` the timeline plays.
dissolveNoSeconds of crossfade into it; 0, the default, is a cut. Drawn from clip_id's own frames before its in-point, so it needs that much of the file before the start, and the film is no longer for it.
src_startNoSeconds into clip_id where it starts. Default its head. Not with from_event.
from_eventNoStart at this event of clip_id instead of src_start.
until_eventNoEnd at this event of clip_id instead of src_end.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A3.9/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already mark destructiveHint=true, and the description goes well beyond that: it says 'everything after moves later,' explains that retime stretches and reframe windows keep their meaning, and warns that a dissolve consumes source frames before the in-point so 'the film is no longer for it.' It also discloses the dry-run behavior and the undo path, giving an agent a clear picture of side effects.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but efficient: the core action is front-loaded, and the second paragraph packs in behavior, reply contents, dry-run, and undo without filler. The phrase 'The window's recording, then the terminal's' is slightly opaque, but overall the structure earns its length.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For an 11-parameter mutating tool with an output schema, this description covers the main side effects, safety options, and outcome semantics. It does not explicitly enumerate every parameter, but the schema does that; the main gap is the absence of an explicit routing distinction from sibling timeline-editing tools.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the baseline is 3. The description adds relational context by tying clip_id and after into the splicing operation and by explaining the dissolve behavior, but it does not substantially augment the per-parameter documentation already present in the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The first sentence states a concrete operation: 'Put a second recording on the timeline after the first, cut or dissolved.' The second paragraph further clarifies that clip_id is spliced in after after and shifts subsequent content later. It is clear and specific, though it does not explicitly name a sibling tool to differentiate from.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description conveys when the tool is used—splicing one recording after another—and even mentions plan=true as a non-writing way to preview. However, it gives no explicit guidance on when to choose follow over sibling timeline tools such as cut_by_time, seed_timeline, or dissolve, so usage context is mostly implied rather than stated.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

fontsA
DestructiveIdempotent

Will the caption font actually draw on this machine?

Reports two answers side by side and does not merge them: fontconfig says whether the family is present, render burns the family and an impossible family and compares the pixels. Identical pixels mean the name is substituting whatever fontconfig claims — the only way to settle which face drew is to measure a render.

path is optional: with a project, this checks the font that project's caption style would burn; without one, proofcut's default. install copies the vendored face where this OS's font system looks (fontconfig, CoreText or DirectWrite) and is off by default, because it writes into the home directory.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoA project directory, or nothing. Omitting it means *no project* here — never the bound one — and reports proofcut's own default caption face; with a project, it reports the face that project's caption style would burn.
installNoCopy the vendored face where this OS's font system looks (fontconfig, CoreText or DirectWrite). Off by default, because it writes into the home directory.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.5/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the annotations, the description discloses important behavioral traits: the tool reports two answers side by side without merging them, uses an impossible-family render comparison to detect substitution, and has an install flag that writes into the home directory. This adds real context about side effects and output semantics that annotations alone do not provide.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Despite its length, every sentence earns its place: the opening question sets intent, the next two explain the core mechanism and non-merging behavior, and the final paragraph covers the two parameters. The structure front-loads the most important behavioral facts.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The description fully covers what the tool does, how it does it, the optional behaviors, and the side-effect risk of install. The output schema is present, so return-value details do not need to be spelled out. Nothing an agent needs to correctly select and invoke this tool is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3. The description restates the path and install semantics already present in the schema and adds some rationale about why the impossible-family comparison matters, but it does not meaningfully extend the schema's parameter documentation.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a concrete diagnostic question and then specifies exactly what the tool reports: fontconfig presence versus an actual render comparison. It clearly identifies the resource (caption font, default or project-specific) and the unique two-answer behavior that distinguishes it from sibling tools.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives clear context for when to use the tool: when you need to know whether a caption font will actually draw on this machine, rather than just whether the family is present. It explains the path semantics and the default behavior, though it does not explicitly name alternatives or say when not to use it.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

footage_sheetA
DestructiveIdempotent

Look at a clip's own footage — one labelled tile per moment, as an image.

The tool to see what is in some footage, as opposed to shot_sheet, which shows an existing edit's picture track. It needs no edit, cues or transcript, so it is the first look at b-roll, recordings and gameplay — material describe can search by text but cannot show. The bytes come back in the reply.

mode picks the instants: auto (described windows if the clip has any, else the interval), interval, describe (each tile beside its window's sentence), or scenes (one per detected cut — opt-in, since a continuous take has none and a scan decodes the whole clip). page walks a long recording. A tile with nothing in it is marked [blank] on the picture, so a black square is never mistaken for a frame that failed to extract.

What you see is a hypothesis, not a check — and this sheet is read to choose footage. synopsis is where a person says what a clip is; a tile shows what the camera saw, which is a different fact.

ParametersJSON Schema
NameRequiredDescriptionDefault
outNoWrite the image to this path as well, replacing whatever file is there. Unset, it goes to the project's own sheet cache and only the bytes come back.
modeNoWhich instants to draw: `auto` (the default) uses the clip's described windows if it has any and the interval otherwise, and never scans; `interval` draws every `interval` seconds; `describe` draws one tile per described window, beside its text; `scenes` draws one per detected cut. Scenes is opt-in because its yield is uncorrelated with anything the caller knows — 0 cuts on a 29s b-roll loop, 17 in 60s of gameplay — and it decodes the whole clip.auto
pageNoWhich page of rows to draw, from 1. Unset, the first.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
clip_idYesThe registered clip to browse. This sheet reads the clip's **own source**, so it needs no edit, no cues and no transcript.
intervalNoSeconds between tiles when drawing by interval (`interval`, or `auto` on a clip with no descriptions). It is `describe`'s own window length, so a tile lines up with a description.
per_pageNoRows per page. `null` draws the whole project in one montage, which returns a path rather than readable bytes — for a person to open, not for an agent to read.

TDQS

A4.5/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations declare destructiveHint=true and idempotentHint=true, but the description adds meaningful behavioral context: it returns bytes in the reply, marks blank tiles as '[blank]' to avoid confusion with failed extraction, and warns that the sheet is 'a hypothesis, not a check' and is read to choose footage. It also discloses that scenes mode decodes the whole clip. This goes beyond the annotations without contradicting them.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but well-organized: a one-sentence summary, a paragraph on positioning, a paragraph on modes, and a paragraph on interpretation. Every sentence earns its place, though the mode paragraph is long and could be tightened. The key contrast with shot_sheet is front-loaded.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a 7-parameter tool with no output schema, the description covers the main behavioral concerns: what the output looks like (image tiles, bytes in reply), how modes interact, and the caveat that it's a hypothesis. It doesn't explicitly describe the full return structure, but the description's emphasis on 'bytes come back' and 'path rather than readable bytes' covers the essential return distinction. The blank-tile behavior and scenes opt-in warning are valuable completeness additions.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3. The description adds value by explaining the relationship between interval and describe windows ('It is describe's own window length, so a tile lines up with a description'), clarifying that per_page=null returns a path rather than bytes, and explaining the path resolution behavior for bound vs unbound servers. These are semantic details beyond the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Look at a clip's own footage — one labelled tile per moment, as an image.' It immediately distinguishes itself from shot_sheet ('shows an existing edit's picture track') and describe ('can search by text but cannot show'). The purpose is unmistakable and differentiated from siblings.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explicitly states when to use this tool: 'the first look at b-roll, recordings and gameplay' and contrasts it with shot_sheet and describe. It also explains mode selection semantics (auto, interval, describe, scenes) and when scenes is appropriate ('opt-in, since a continuous take has none'). This is explicit when/when-not guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

get_transcriptA
Read-onlyIdempotent

Read a clip's transcript.

With search, returns each match as a word range ready to hand to cut_by_transcript — prefer this to reading the whole transcript. With first/last, returns that window of words. Indices are inclusive.

At most limit words come back per call. total_words is the whole transcript, last_word where this reply stopped, and next_first — only present when words were left out — is the first to ask for next.

ParametersJSON Schema
NameRequiredDescriptionDefault
lastNoLast word index to return, inclusive.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
firstNoFirst word index to return, inclusive.
limitNoMost words to return in one call, counted from `first`. The reply's `next_first` says where to continue. Bounded by default because a whole transcript can be past what a client will put in context.
searchNoReturn each match as a word range ready to hand to `cut_by_transcript`, instead of the whole transcript. Prefer it: a transcript is a lot of words to read to find two.
clip_idYesThe clip to read.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.2/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint, idempotentHint, and destructiveHint, so the tool is safe and idempotent. The description adds pagination details (total_words, last_word, next_first) and notes that next_first is only present when words are left out, which is useful behavioral context beyond annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is concise and well-structured. It front-loads the primary use case (search) and then explains pagination in a few clear sentences. No wasted words.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

With an output schema present and complete schema coverage, the description sufficiently covers the key aspects: modes, pagination, and continuation. It could be a bit more explicit about the output schema fields, but overall it's complete for an agent to use effectively.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the schema already describes all parameters. The description clarifies the interplay between first, last, limit, and search, and explains how next_first is used for continuation, but this is largely redundant with schema descriptions. It doesn't add major new semantics.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool reads a clip's transcript and explains the different modes (search, first/last). It distinguishes itself from siblings like cut_by_transcript by showing how search results are meant to feed into it.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It explicitly says to prefer search over reading the whole transcript, and explains first/last semantics. It also mentions pagination with limit and next_first, providing complete guidance on when and how to use the tool.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

graphic_captureA
DestructiveIdempotent

Capture one animated graphic, or every one whose capture is missing or stale.

Needed after a canvas or frame-rate change; graphic_new and graphic_edit capture on their own. Runs a headless browser; doctor says whether this machine has one.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameNoThe graphic to capture. Unset, every graphic whose capture is missing or stale.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
forceNoRecapture even a current one.
pagesNoBrowser pages capturing side by side, 1 to 8. Default 2.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.5/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare idempotentHint and destructiveHint, and the description adds useful non-obvious behavior: it runs a headless browser and can be validated via `doctor`. It does not detail all side effects, but the destructive flag plus the force parameter's schema description cover the main overwrite behavior without contradiction.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Every sentence earns its place: two compact sentences state the scope, the trigger condition, the sibling behavior, and the runtime prerequisite. The most important information is front-loaded in the first sentence.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

With an output schema present, all parameters documented in the input schema, and annotations covering safety and idempotency, the description supplies the missing context: when to invoke, what scope it operates over, and what to check before running. Nothing critical for correct invocation is omitted.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the input schema fully documents name, path, force, and pages. The description's 'one...or every one whose capture is missing or stale' adds a light semantic gloss on `name`, but it does not materially improve on the schema, so the baseline 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Capture one animated graphic, or every one whose capture is missing or stale.' It also distinguishes itself from the sibling tools graphic_new and graphic_edit by stating that those tools capture on their own, so this tool's role is clear against closely related alternatives.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It explicitly states when this tool is needed ('after a canvas or frame-rate change') and when it is not ('graphic_new and graphic_edit capture on their own'). It also points to `doctor` as the way to check the headless-browser prerequisite, giving the agent actionable selection guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

graphic_editA
DestructiveIdempotent

Change an animated graphic — refill its slots, replace its page, or move its phases — and recapture it.

Every overlay placing it follows, since an overlay names the graphic, not its frames. Undo does not revert a graphic's page: it lives beside the project's manifest, like a card's PNG.

ParametersJSON Schema
NameRequiredDescriptionDefault
htmlNoA whole new page. The graphic stops being its template's.
loopNoNew loop length, in seconds, making the hold loop.
nameYesThe graphic to change.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
introNoNew intro length, in seconds.
outroNoNew outro length, in seconds.
pagesNoBrowser pages capturing side by side, 1 to 8. Default 2.
slotsNoSlots to change, merged into the ones it was filled with.
captureNoRecapture now. False leaves the capture stale until graphic_capture.
no_loopNoMake the hold still again.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already mark the tool as destructive, read-write, and idempotent. The description adds genuinely non-obvious behavioral context: overlays follow because they reference the graphic rather than its frames, and undo does not revert a graphic's page because it persists beside the manifest. These claims go beyond the structured hints without contradicting them.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Three sentences, front-loaded with purpose and followed by two high-value caveats. Every sentence earns its place, and the manifest/PNG analogy communicates persistence behavior without padding.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given a rich input schema, an output schema, and annotations that cover the safety profile, the description supplies the missing contextual pieces: propagation to overlays and undo limits. It does not address sibling selection, but that gap is accounted for in usage guidelines; for invocation context it is largely complete.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the baseline of 3 applies. The description's high-level phrases like "refill its slots" and "replace its page" loosely map to slots and html, but they add no syntax, default, or edge-case detail beyond what the schema already provides.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource, "Change an animated graphic," and enumerates concrete operations — refill slots, replace page, move phases, recapture. This distinguishes it from siblings like graphic_new (creation) and graphic_capture (capture alone). The phrase "move its phases" is slightly jargon-y, but the schema parameters clarify it.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The tool's scope is clear, but the description never states when to choose it over graphic_capture, graphic_save/load, or graphic_new, nor when not to use it. The overlay and undo notes provide surrounding context but no explicit alternative routing. Usage is implied rather than spelled out.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

graphic_libraryB
Read-onlyIdempotent

Every animated graphic saved to this machine's library (graphic_save), with its phases.

ParametersJSON Schema
NameRequiredDescriptionDefault

No parameters

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

B3.3/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint, idempotentHint, and destructiveHint, covering the safety profile. The description adds small context beyond annotations: it addresses the full library scope and the inclusion of phases. It does not contradict the annotations and contributes some behavioral information, but not much.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

One short sentence with no filler. It conveys the core content of the tool and the phase detail efficiently, earning a top score for appropriate sizing and front-loading.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

With no parameters, rich annotations, and an existing output schema, the description is nearly sufficient. It communicates the full scope of the result set and a key property (phases). Minor ambiguity about the exact action and what 'phases' means remains, but the low complexity keeps this from being a serious gap.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The tool has zero parameters and schema coverage is 100% trivially. The description has no parameter burden, so the baseline of 4 applies. There is nothing here that the schema fails to document.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose3/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description identifies the resource (animated graphics in the machine library) and adds a relevant detail (includes their phases), but it is a noun phrase without a verb. It doesn't clearly state the operation (list? retrieve? open?), making the purpose somewhat vague, though it is not a tautology.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

No guidance is given on when to use this tool versus siblings like graphic_ls, graphic_sheet, or graphic_load. The only reference to graphic_save suggests provenance, not when to call this tool, and there are no exclusions or alternative-routing hints.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

graphic_loadA
DestructiveIdempotent

Copy a graphic from this machine's library into the project, and capture it at the project's canvas.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameNoIts name in this project. Unset, the same name.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
pagesNoBrowser pages capturing side by side, 1 to 8. Default 2.
savedYesThe library graphic to copy in (graphic_library lists them).
captureNoCapture it now at this project's canvas and rate.
replaceNoReplace a project graphic of that name. Unset, it is refused.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A3.8/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=false and destructiveHint=true, so the safety profile is covered. The description adds that the tool copies from the library and captures at the canvas, which is useful context, but it does not disclose side effects like default refusal on name collision (only in the replace parameter) or the capture/rate behavior. It adds some value beyond annotations but not a rich behavioral picture.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is a single, efficient sentence with the main verb and resource front-loaded. Every word contributes: it states the action, source, destination, and the additional capture effect. There is no filler or repetition.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the rich input schema (100% coverage, detailed path and replace semantics), annotations (readOnlyHint, destructiveHint, idempotentHint), and an output schema, the description is sufficient for an agent to invoke the tool correctly. It could mention the dependency on graphic_library for the saved parameter, but that hint lives in the schema, so the overall context is nearly complete.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, and each parameter already has a detailed description (path semantics, defaults, replace behavior). The tool description mentions 'library graphic' for saved and 'capture' for capture, but these are largely redundant with the schema. The description does not add meaning beyond what the input schema already provides, so the baseline of 3 applies.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description uses specific verbs ('Copy', 'capture') and names both source ('this machine's library') and destination ('the project's canvas'). It clearly distinguishes this tool from siblings like graphic_library (listing), graphic_new (creating), and graphic_capture (capturing an existing graphic), so an agent can select it without ambiguity.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description implies a workflow by mentioning 'library' and 'project', and the saved parameter references graphic_library for listing, but there is no explicit statement of when to prefer this tool over alternatives or when not to use it. It leaves the choice to inference from the surrounding schema and sibling names.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

graphic_lsB
Read-onlyIdempotent

Every animated graphic in the project, whether its capture is current, and which overlays place it.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

B3.2/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already establish readOnly, idempotent, and non-destructive behavior. The description adds useful context about what the listing covers: all animated graphics, their capture currency, and overlay placement. It does not describe ordering, filtering, or result shape, though an output schema exists.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness3/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is very short, but it is a grammatically awkward fragment rather than a clear sentence like 'Lists all animated graphics...'. It has no wasted words, yet the missing verb and unusual phrasing reduce clarity.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a low-complexity listing tool with one optional parameter fully described in the schema, rich annotations, and an output schema, the description covers the essential result content. The main missing piece is usage guidance, which is already accounted for in the usage_guidelines dimension.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100% and the path parameter is documented in detail, including bound-project behavior, relative resolution, and refusal cases. The tool description itself contributes no parameter-level meaning, so the baseline of 3 applies.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description identifies the resource (animated graphics in the project) and the key reported aspects: whether each capture is current and which overlays place it. The verb is only implied by the tool name and the 'Every...' phrasing rather than stated explicitly, and it does not differentiate from sibling tools like graphic_library or graphic_templates.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

There is no explicit guidance on when to use this tool versus alternatives, and no exclusions or sibling comparisons. Among the many graphic-related siblings, an agent gets no help selecting this tool. The path parameter description gives operational context but not usage criteria.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

graphic_newA
DestructiveIdempotent

Make an animated graphic — a web page, captured frame by frame — from a template or your own HTML.

A graphic has three phases, in seconds of the page's own timeline: an intro that plays once from the start of wherever it is placed, a hold that fills whatever the span leaves (the page's last intro frame, or loop seconds repeated), and an outro that plays once to end the span. The span decides the length, never the graphic, so cuts cannot break it. Write the page's outro animations to start where the intro ends (after one loop, if it loops). Nothing on the page may load from the network.

Place it with overlay_add(graphic=name). Then look at it with graphic_sheet. The capture draws at the project's canvas and export rate; changing either makes it stale, and export refuses a stale graphic.

ParametersJSON Schema
NameRequiredDescriptionDefault
htmlNoA whole page, written by hand. CSS animations and transitions are seeked frame by frame; a script animating from its own clock must define window.proofcutSeek(seconds). Fonts load from /_proofcut/fonts/static/Outfit-Regular.ttf and Outfit-Bold.ttf; nothing loads from the network.
loopNoSeconds of the page after the intro to repeat through the hold, for a hold that moves (a blinking caret). Unset, the hold is the page's last intro frame, still; a page still moving there is refused.
nameYesThe graphic's name: lowercase letters, digits, - and _. overlay_add places it by this name.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
introNoSeconds of the page that play once from the start of the span.
outroNoSeconds of the page, from the hold on, that play once to end the span.
pagesNoBrowser pages capturing side by side, 1 to 8. Default 2.
slotsNoThe template's slots, as text. A colour is #rrggbb, a number a number.
captureNoCapture it now. False writes the page and draws nothing.
replaceNoReplace a graphic of this name. Unset, an existing one is refused.
templateNoA template to fill (graphic_templates lists them). One of template or html.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Even with annotations present, the description adds substantial behavioral context: the three-phase timeline, the fact that the span decides length, the network-loading prohibition, the stale-on-canvas-change behavior, and that export refuses stale graphics. This goes well beyond the structured annotations and gives an agent critical non-obvious constraints.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is four dense sentences, front-loaded with purpose, then the phase model, then hard constraints, then lifecycle actions. Every sentence carries necessary information without filler or repetition.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a tool with 11 parameters, an output schema, and annotations, the description covers the conceptual model (phases, span, staleness), hard constraints (no network, no still-moving holds), and integration (overlay_add, graphic_sheet). It also relies on the schema for per-parameter details and the output schema for return values, so nothing essential is left unexplained.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the baseline is 3. The description adds extra meaning around the phased semantics — intro, hold, loop, and outro — and explains the relationship between these durations and the page's timeline, which is not fully captured by the individual parameter descriptions. This lifts it above baseline, though the schema already does most of the per-parameter work.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with 'Make an animated graphic — a web page, captured frame by frame — from a template or your own HTML,' which names a specific verb, resource, and means of creation. This clearly distinguishes graphic_new from siblings like graphic_edit, graphic_capture, and graphic_ls.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives concrete lifecycle guidance: 'Place it with overlay_add(graphic=name)' and 'Then look at it with graphic_sheet,' and points to graphic_templates for available templates. It doesn't explicitly contrast graphic_new with graphic_edit or state when not to use it, but the creation-vs-editing role is strongly implied by the name, description, and sibling set.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

graphic_saveA
DestructiveIdempotent

Save an animated graphic to this machine's library, where every project can load it.

The page and its phases are saved; the frames are not, since another project may have another canvas.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameYesThe project's graphic to save.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
as_nameNoThe name in the library. Unset, the same name.
replaceNoReplace a library graphic of that name. Unset, it is refused.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already signal the tool is destructive and idempotent. The description adds critical behavioral context by specifying that 'the page and its phases are saved; the frames are not,' explaining a non-obvious limitation. It also clarifies the persistence model ('every project can load it'), which is valuable beyond what annotations provide.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is concise and front-loaded: the first sentence states the primary function, and the second adds an important caveat. Every sentence earns its place, with no redundancy or filler. It is well-structured and easy to parse.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's complexity (four parameters, all documented) and the presence of an output schema, the description covers the essential context: what is saved, where, and the key limitation. It does not describe when to use it over siblings, but that is partially covered by the purpose. The description is adequate for an agent to call it correctly without missing critical details.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100% and each parameter has a clear description, so the baseline is 3. The tool description does not add any additional meaning about parameter usage beyond what the schema already documents. It does not, for instance, explain how the 'name' parameter relates to the 'as_name' override or how 'replace' interacts with existing records.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the purpose: 'Save an animated graphic to this machine's library' – a specific verb (save), resource (graphic), and destination (library). It also adds a clarifying detail about what is saved (page and phases) versus what is not (frames), which distinguishes it from other graphic tools and gives a precise scope.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description implies when to use the tool (to persist a graphic for reuse across projects) but does not explicitly contrast it with alternatives or state when not to use it. There is no mention of sibling tools like graphic_new or graphic_load, leaving the agent to infer context. The caveat about frames suggests a use case but lacks explicit routing guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

graphic_sheetA
Read-onlyIdempotent

Look at an animated graphic: one labelled tile per phase boundary, as an image.

The intro's first frame and two more across it, the hold (and the loop's middle), and the outro's middle and last frame, flattened over grey so a transparent graphic reads. What you see is an opinion, not a check.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameYesThe captured graphic to look at.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

TDQS

A3.9/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the readOnly/idempotent/destructive annotations, the description discloses exactly which frames are sampled (intro first plus two more, hold/loop middle, outro middle and last) and that tiles are flattened over grey so transparency reads. This is concrete behavioral detail that helps the agent know what the image will contain, with no contradiction.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Three sentences with the core purpose front-loaded and supporting sampling/compositing details following. The middle sentence is dense, but every clause carries concrete information; there is no filler or repetition.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

With no output schema, the description still communicates that the result is an image, what frames are included, and the background treatment. It assumes some domain familiarity with 'phase boundary' and 'loop,' but for a specialized inspection tool that is reasonable and not a serious gap.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, and the 'name' parameter is already described as 'the captured graphic to look at.' The tool description adds no extra parameter-level meaning, so it remains at the baseline for fully documented schemas.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly identifies the resource (an animated graphic) and the output form (an image with one labelled tile per phase boundary). It does not use a strong imperative like 'render' or 'generate', and it does not explicitly contrast with sibling sheet tools, but the phase-boundary detail is distinctive enough to separate it from similar tools.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The first sentence frames the intended use: visually inspecting an animated graphic's phases as a labelled sheet. The closing caveat, 'What you see is an opinion, not a check,' explicitly warns against treating it as verification, though it does not name an alternative checking tool.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

graphic_templatesA
Read-onlyIdempotent

The animated graphic templates proofcut ships, with their phases and slots.

Read this before graphic_new with a template. Each template says what it draws, its intro, loop and outro in seconds, and every slot with its default. A template is a starting point; a page written as html can do anything CSS can.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameNoOne template to return. Unset, every template with its slots.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.2/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already cover read-only, idempotent, and non-destructive behavior, so the bar is lower. The description adds useful context about what a template contains, what each template specifies, and the limitation that templates are starting points rather than fully custom solutions.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is short and every sentence contributes. The first sentence is slightly awkward with 'proofcut ships,' but the overall structure is efficient and front-loads the core resource before giving usage guidance.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the output schema, full parameter documentation, and rich annotations, nothing essential is missing. The description explains what the tool returns, when to consult it, and how it relates to graphic_new and custom HTML.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100% and the parameter description already explains that name optionally selects one template and that unset returns every template with its slots. The description adds no parameter-level detail beyond that, so a baseline 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description identifies the resource as the animated graphic templates shipped with proofcut, including their phases and slots. It lacks an explicit verb like 'list' or 'inspect,' but the content and the pointer to graphic_new make the tool's role clear.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It explicitly says to read this before graphic_new with a template, which tells the agent when this tool is a prerequisite. It also frames templates as a starting point and notes that an HTML page can do anything CSS can, implying when custom code is preferable.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

hearA
Read-onlyIdempotent

What does clip_id's source audio actually say between start and end?

Use this when the transcript and the audio might disagree — a word with a suspect duration, a hole with no words in it, a stretch that reads clean but sounds wrong. It runs the same short-overlapping-window pass verify(windowed=True) runs, over the clip's own media across the span (source seconds), and comes back with heard_words/heard_text beside the attached transcript's own words over that span (transcript_words). No need to seed, export and verify to hear your source material.

Reports, never attaches — nothing is written and no word index moves. Where the two disagree, cut_by_time addresses what the transcript has no word for. heard_words can be empty: silence is a real answer. One whisper run over the span; end past the clip is refused.

ParametersJSON Schema
NameRequiredDescriptionDefault
endYesWhere to stop, in the same source seconds. Past the end of the clip it is refused rather than clamped.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
modelNoThe whisper model for this windowed pass.small
startYesWhere to start listening, in that clip's own **source** seconds — never timeline seconds and never a word index.
windowNoLength of each window, in seconds.
clip_idYesThe clip whose source audio to listen to.
overlapNoHow far each window overlaps the one before it, in seconds. The overlap is what stops a word straddling a boundary from being lost between two windows.
languageNoForce a language code, e.g. `en`. Unset, whisper detects it.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the read-only/idempotent annotations, it discloses that the call reports and never attaches, writes nothing, moves no word index, may return empty `heard_words` as a valid silence answer, performs one whisper run over the span, and refuses `end` past the clip. This is substantive behavioral context the annotations do not provide.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but every sentence earns its place: purpose, trigger conditions, method, return fields, side effects, alternatives, and edge cases. The opening question front-loads the core purpose, and the bold 'Reports, never attaches' makes the side-effect statement highly scannable.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a read-only listening/verification tool with an output schema and well-documented parameters, this description covers everything an agent needs to call it correctly: when to use it, what it returns, what it does not do, cost/run characteristics, and refusal behavior. Nothing important is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, and the schema already explains source seconds, refusal behavior, defaults, and language handling in detail. The description reinforces the source-seconds framing and mentions windowed passes, but it does not need to compensate because the schema already carries the parameter semantics.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a precise question: what does a clip's source audio actually say over a span, and immediately ties it to comparing audio against the attached transcript. It also distinguishes itself from siblings by explicitly referencing `verify(windowed=True)` and `cut_by_time`, so an agent can disambiguate without opening schemas.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It gives explicit trigger conditions: suspect word durations, holes with no words, or passages that read clean but sound wrong. It also names the relevant alternatives, saying there is no need to seed/export/verify and pointing to `cut_by_time` for disagreements, which is strong when-vs-alternative guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

hold_addA
Destructive

Splice a hold into clip_id after gap_word_index: a real gap opens in the VO (vo_extend's own mechanism, reused) and a picture cue pins asset's own in-point, snapped to whole words with margin and refused, never clamped, when it cannot fit.

Addressed by (clip_id, gap_word_index), unique — a second hold_add at the same address is refused. gap_word_index/cue_word_index/ word_index_first+word_index_last each also accept a phrase alternative: gap_phrase binds its last word (the gap opens right after it), cue_phrase binds its first, and asset_phrase resolves against asset's own transcript and binds its first and last words to word_index_first/word_index_last together.

Everything else is resolved live: elapsed (how long the VO plays between the cue and the gap), src_start (deterministically — phrase_start - elapsed - head_margin), and hold_length (the phrase's own span plus both margins). Refused, with the measured numbers, when there is no room or the asset runs out.

Mix-only fields (head_margin/tail_margin/under/fade_in/ fade_out) are re-settable on an already-spliced hold by calling again with the same address and no change to word_index_first/ word_index_last — those two are one-way once spliced (hold_rm then hold_add again, or proofcut undo, are the only ways to resize one).

plan=True resolves and reports without writing anything.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
afterNoA forward cursor over the matches of `gap_phrase`/`cue_phrase`/`asset_phrase`: any match at or before this word index is skipped. -1, the default, means from the start.
assetNoThe film clip whose own audio plays in the gap, and whose picture the cue pins.
underNoHow far below the VO the held audio sits, in LU. Re-settable.
clip_idYesThe VO track the gap opens in.
fade_inNoSeconds of fade as the held audio comes in. Re-settable.
fade_outNoSeconds of fade as it goes out. Re-settable.
cue_phraseNoAddress the cue by wording; it binds its **first** word.
gap_phraseNoAddress the gap by wording; it binds its **last** word, since the gap opens right after it.
occurrenceNoDisambiguate `gap_phrase`/`cue_phrase`/`asset_phrase` by count, **1-based**. Unset, an ambiguous phrase is refused rather than guessed at.
head_marginNoSeconds kept before the line, so it does not start on the word. Re-settable on an already-spliced hold.
tail_marginNoSeconds kept after the line. Re-settable.
asset_phraseNoThe line to play, resolved against `asset`'s **own** transcript, binding its first and last words together. One phrase is the source of truth for both ends; hand-typed indices drift the moment a transcript changes under them.
cue_word_indexNoThe word the picture cue for `asset` is placed on.
gap_word_indexNoThe word the gap opens right after. With `clip_id` it is the hold's address, and a second `hold_add` at the same address is refused.
word_index_lastNoLast word of that line. With `word_index_first` it is one-way once spliced: resizing means `hold_rm` then `hold_add`, or `undo`.
word_index_firstNoFirst word of the line to play, in **`asset`'s own** transcript — not the VO's.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.8/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the destructiveHint annotation, it discloses exact behavioral edge cases: refusal rather than clamping when there is no room, deterministic live resolution of elapsed/src_start/hold_length, one-way word indices once spliced, and plan=True writing nothing. This is substantial context beyond the structured hints.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The first sentence is an excellent front-loaded summary and the dense paragraphs earn their place for an 18-parameter tool. It is longer than ideal, with some information already present in the schema, but still well organized.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's complexity, a rich output schema, and per-parameter schema descriptions, the description covers mutation constraints, refusal modes, live computation, re-set semantics, and plan mode. An agent has enough to call it correctly without missing core behavior.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

With 100% schema coverage the baseline is 3, but the description adds cross-parameter meaning: (clip_id, gap_word_index) is the unique address, phrase alternatives bind first/last words, and asset_phrase ties word_index_first and word_index_last together. It stops short of describing every optional combination, so not a 5.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

Opens with a specific operation: 'Splice a hold into `clip_id` after `gap_word_index`' and details the two effects (opening a real gap in the VO and pinning a picture cue). The address uniqueness and refusal behavior further distinguish it from siblings like hold_rm/hold_ls.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Explicitly says when a second hold_add is refused, when re-calling is allowed (re-settable mix-only fields), and states that resizing requires hold_rm + hold_add or proofcut undo. plan=True also offers a no-write alternative, so an agent knows to preview before mutating.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

hold_checkA
Read-onlyIdempotent

Transcribe each hold's own span off render and check its seams.

For each stored hold: the required phrase, transcribed off the render at the hold's live-resolved span, plus the level right at each edge against the quiet floor just after it — "still loud" (a word cut off) or a "noise-floor cliff" (a hard drop with nowhere graceful to land). Report, never refuse — a post-hoc listening check on a render that already exists, verify's and film_check's own stance.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
renderYesThe rendered file to listen to. Each hold's span is resolved live against the current edit and transcribed off this file.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.5/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already mark this read-only, idempotent, and non-destructive. The description goes further by explaining the actual check mechanism: comparing level at each edge against the quiet floor just after it, and classifying results as 'still loud' or 'noise-floor cliff.' This adds meaningful behavioral detail beyond the annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but well-structured: a front-loaded headline, a compact explanation of the seam-check logic, and a bolded behavioral stance. Every sentence contributes meaning without redundancy or filler.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a specialized auditing tool, the description explains the domain concepts, the exact input source, what is examined, and the reporting philosophy. An output schema exists, so lack of return-value detail is acceptable, and the schema covers path/resolution behavior.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the schema itself already documents `render` and `path` thoroughly. The description reinforces `render`'s role by mentioning live-resolved spans, but it does not add substantial new parameter meaning beyond the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

Opens with a specific verb and resource: 'Transcribe each hold's own span off render and check its seams.' It clearly identifies this as a checking/verification action for stored holds, distinguishing it from sibling hold_* mutation tools and aligning it with verify/film_check's report stance.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Gives clear context: this is a 'post-hoc listening check on a render that already exists' and should 'report, never refuse.' It does not explicitly list when-not-to-use or name alternative tools as replacements, but the context is strong enough to guide selection.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

hold_lsA
Read-onlyIdempotent

Every stored hold plus its live-resolved plan.

A hold that cannot currently resolve is reported inline (hold_error), never raised. Each item also carries cue_drift — a check between the hold's own owned cue and what it would compute fresh right now, since nothing stops a plain cue_rm/cue_add on that exact word from an unrelated caller.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A3.6/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The annotations already cover read-only, idempotent, and non-destructive behavior. The description adds meaningful behavioral detail beyond that: unresolved holds are surfaced via an inline hold_error field rather than raised exceptions, and cue_drift exposes live recomputation differences caused by unrelated cue mutations. This is valuable context an agent would not otherwise know.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact, front-loaded with the core purpose, and every sentence adds meaningful detail about error behavior or cue_drift. No filler or repetition is present.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

With annotations covering safety, an output schema present, and the path parameter fully documented in the schema, the description supplies the important behavioral nuances that structured fields cannot. It is complete enough for an agent to invoke and interpret the tool correctly, though it could strengthen the case by mentioning when to prefer this over related hold/cue inspection tools.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the single path parameter is already fully documented in the schema. The tool description adds no additional parameter semantics, which matches the baseline expectation when the schema carries the full burden.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description identifies the resource clearly: every stored hold plus its live-resolved plan and related diagnostics. It implies listing behavior through the tool name and content description, but lacks an explicit verb and does not directly distinguish itself from sibling tools such as hold_check or cue_ls.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

No explicit guidance is given about when to use hold_ls versus alternatives like hold_check, cue_ls, or cue_reresolve. The description provides useful context about inline errors and cue_drift, but leaves the selection criteria to the agent's inference.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

hold_rmA
Destructive

Drop a hold's record and its owned cue — the spliced silence stays.

vo_extend's own irreversibility, inherited: there is no clean "un-splice", only proofcut undo. After this the gap reverts to being an ordinary manufactured silence, a coherent pre-existing state rather than a broken one.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
clip_idYesThe VO track the hold was spliced into.
gap_word_indexYesThe hold's address, with `clip_id`. The record and its owned cue go; the spliced silence stays, since there is no clean un-splice — only `undo`.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A3.5/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the destructiveHint annotation, the description adds critical nuance: the operation is irreversible in the sense that there is no clean un-splice, and the gap reverts to a 'coherent pre-existing state' rather than a broken one. It also states what persists (the spliced silence) and what disappears (the record and cue). This is meaningful behavioral disclosure that the annotation alone does not convey.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is concise—two short paragraphs—and front-loads the primary action in the first sentence. The additional explanation about irreversibility and the resulting state is valuable but delivered in slightly poetic language ('spliced silence stays', 'coherent pre-existing state') that, while not verbose, could be more direct. Overall it is well-structured and avoids redundancy.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a destructive tool, the description covers the key operational aspect (what is removed and what remains) and the irreversibility condition. It does not explain domain concepts like 'record' or 'owned cue', but these are likely defined elsewhere or in the sibling tools' context. Given that an output schema exists (not shown here but flagged), the tool's return information is presumably documented there. The description is complete enough for an agent familiar with the domain.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the parameter descriptions already explain each field adequately. The description itself adds minimal parameter semantics, only clarifying that gap_word_index plus clip_id forms the hold's address and that 'the record and its owned cue go'—which slightly enriches the parameter meaning. However, this is marginal beyond what the schema already provides, so the baseline 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool drops a hold's record and its owned cue, with the explicit note that the spliced silence remains. This distinguishes it from sibling tools like hold_under_rm (which likely removes a 'hold under' region) and cue_rm (which would remove a cue without necessarily the hold record). However, the verb 'Drop' is informal and the exact scope of 'record' and 'owned cue' is implicit, requiring domain familiarity.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description does not provide explicit when-to-use guidance relative to alternative hold-removal tools. It mentions that undo is the only way to revert, but never states 'use this when you want to completely remove a hold and its cue, versus hold_under_rm for partial removal' or similar. The context about irreversibility is behavioral, not usage-directional, so an agent is left to infer when this is the right choice among several hold-related sibling tools.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

hold_underA
DestructiveIdempotent

Play a film clip's own audio under a span of the VO, under LU below it (default 13) — no gap, unlike hold_add. The span is VO words (word_index_start/word_index_end, or phrase_start/phrase_end), and the audio reads from wherever the shot showing asset has got to at the span's first word, so asset must be on screen there — cue it first. A second call at the same (clip_id, word_index_start) replaces the entry; the music bed goes out across it. plan resolves without writing. Both boundary words are echoed with neighbours — check them.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
afterNoA forward cursor over the matches of `phrase_start`/`phrase_end`: any match at or before this word index is skipped. -1, the default, means from the start.
assetYesThe film clip whose audio plays under the voice. It has to be on screen across the span — the audio reads from wherever the shot showing it has got to — so cue it first.
underNoHow far below the VO the film audio sits, in LU. 13 by default.
clip_idYesThe VO track whose words the span is measured in.
fade_inNoSeconds of fade as the film audio comes in.
fade_outNoSeconds of fade as it goes out.
occurrenceNoDisambiguate `phrase_start`/`phrase_end` by count, **1-based**. Unset, an ambiguous phrase is refused rather than guessed at.
phrase_endNoSet the span's end by wording instead.
phrase_startNoSet the span's start by wording instead.
word_index_endNoLast VO word of the span.
word_index_startNoFirst VO word of the span. With `clip_id` it is the entry's address; a second call at the same address replaces it.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.3/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already mark the tool as idempotent and destructive, but the description adds concrete behavior: a second call with the same `(clip_id, word_index_start)` replaces the entry, the music bed goes out across it, and `plan` resolves without writing. This goes beyond the structured hints and describes the actual effects an agent would care about.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but every clause earns its place: main action, differentiation, span selection, asset precondition, replacement semantics, dry-run option, and output echo. It is front-loaded with the core purpose. Slightly on the longer side for a single paragraph, but justified for a 13-parameter tool.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a complex tool with 13 parameters and an output schema, the description covers the major operational points: span selection, asset on-screen requirement, replacement, plan behavior, and output echo. It is complete enough for correct invocation; the only minor omission is further elaboration of the music-bed behavior, which is not essential.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3. The description adds extra meaning: `word_index_start` serves as the entry's address, the span can be set via words or phrases, `under` defaults to 13 LU, and `asset` must be on screen. It also notes that boundary words are echoed with neighbours, which helps the agent verify results.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with the specific action — “Play a film clip's own audio *under* a span of the VO” — and immediately distinguishes it from hold_add (“no gap, unlike `hold_add`”). This makes its purpose and uniqueness clear without needing to open the schema.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It provides clear context: when to use (`under` a span, no gap), preconditions (`asset` must be on screen, cue it first), and a safe dry-run option (`plan`). It does not explicitly state when *not* to use it or point to hold_add as the alternative for gapped holds, but the contrast is implicit enough for an agent to infer routing.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

hold_under_rmA
Destructive

Drop the film audio under the VO addressed by (clip_id, word_index_start).

The inverse of hold_under: that span plays the VO alone again, and the music bed — which a hold gates out — comes back across it. Refused when no entry sits at that address, so a second call says so rather than doing nothing quietly. The audio was a manifest entry, not a splice, so no word moves and undo restores it.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
clip_idYesThe VO track the entry was addressed against.
word_index_startYesThe span's first VO word — the entry's address, with `clip_id`.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.4/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare destructiveHint=true, readOnlyHint=false, and idempotentHint=false, covering the basic mutation safety profile. The description adds context beyond that: it explains the effect on the music bed, the refusal on missing entries, and the undo/restore behavior. No contradiction with annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is roughly four sentences, each carrying distinct information: the primary action, the inverse relationship, the error behavior, and the undo effect. It is front-loaded with the core action and avoids fluff, though a slightly tighter phrasing could be imagined.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a destructive operation with a clear output schema (present), the description covers the main effect, the inverse counterpart, the failure mode, and the reversibility. It omits only generic prerequisites like permissions, which are likely project-wide. No material information an agent needs to call it correctly is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so all parameters (path, clip_id, word_index_start) are already described in the schema. The description references the address pair but doesn't add new semantic meaning beyond reinforcing that they form the address. This meets the baseline for high schema coverage.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Drop the film audio under the VO addressed by (clip_id, word_index_start)'. It clearly identifies the tool as the inverse of hold_under, distinguishing it from the sibling tool without ambiguity. The purpose is unambiguous and not a tautology.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explicitly names the inverse relationship to hold_under, telling the agent exactly when to use this tool instead of that one. It also states the refusal behavior when no entry exists, which is a key precondition. This is strong guidance for selection among siblings.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

image_addA
DestructiveIdempotent

Add a still image to the project: a photo, a logo, a cut-out sticker.

It lands upright (a phone photo's EXIF rotation applied) in a format the render and the window both read. Then show it full frame with cue_add(asset="image:"), or place it over the film as a sticker with overlay_add(image=name, x=, y=, width=, rotate=, style="photo").

ParametersJSON Schema
NameRequiredDescriptionDefault
nameNoWhat to call it; `image:<name>` is how a cue names it. Unset, from the filename.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
sourceYesThe image file: PNG, JPEG, WebP, HEIC, GIF (its first frame), AVIF, TIFF or BMP. list_media lists the ones in a folder under `images`.
replaceNoReplace an image of this name. Unset, a taken name is refused.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.5/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already signal destructive/idempotent behavior, so the description's added value is contextual: it discloses that EXIF rotation is applied and that the image lands in a format readable by both render and window. This is genuine behavioral information beyond the structured annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is well-structured and front-loaded, starting with the core action, then adding behavioral detail and downstream usage. Every sentence earns its place; there is no padding or repetition of schema fields.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given full parameter schema coverage, output schema presence, and annotations for safety/idempotency, the description is complete enough for correct invocation. It also includes downstream composition guidance, leaving no critical gap for an agent to act on.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3, but the description adds meaning beyond the schema: it explains that a cue names the asset as image:<name> and gives the overlay_add signature for placing the image over film. This helps an agent compose correct follow-up calls.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description names a specific action and resource: add a still image to the project, with concrete examples (photo, logo, sticker). It is clearly distinct from sibling tools like image_ls, image_rm, and graphic_* by focusing on adding image assets, and it immediately connects to how the image is used downstream.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It provides clear context for when to use the tool (adding a still image) and explicitly shows the next steps with cue_add and overlay_add. It does not name exclusion cases or alternatives like import_media or graphic_new, so it stops short of full when-not guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

image_lsA
Read-onlyIdempotent

Every still in the project, where it came from, its size, and the cues and overlays placing it.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A3.9/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already establish read-only, idempotent, non-destructive behavior. The description adds useful context about what the listing contains (provenance, size, cues/overlays), which goes beyond the annotation flags and helps the agent anticipate the result shape.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

A single sentence that is information-dense and front-loaded with the core purpose. Every phrase contributes: scope, provenance, size, and placement context.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a simple read-only list tool, the combination of a clear one-line description, a fully documented optional parameter, comprehensive annotations, and an output schema covers everything an agent needs to invoke it correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, and the single optional path parameter is thoroughly documented in the schema. The tool description does not add parameter-level meaning, so the baseline of 3 applies.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly identifies the tool as listing every still in the project and enumerates the returned information (source, size, placing cues/overlays). It is distinguishable from image_add/image_rm and graphic_ls, though it does not use an explicit verb like 'List'.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The phrase 'in the project' implies this is for querying project stills, and the schema explains path resolution. However, there is no explicit guidance on when to prefer this over sibling list tools such as graphic_ls, list_media, or cue_ls, and no when-not-to-use conditions.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

image_rmC
Destructive

Remove a still nothing places. A cue or overlay using it is named instead.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameYesThe image to remove. Refused while a cue or overlay places it.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

C2.6/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare `destructiveHint: true`, so the description does not need to restate destructiveness. It does add the conditional behavior of refusing while a cue/overlay uses the image and mentions that the using item is named instead, but this is also largely present in the `name` property description and is obscured by the garbled prose.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness2/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is short, but brevity comes at the cost of clarity. 'Remove a still nothing places' is not a readable sentence, and 'A cue or overlay using it is named instead' is cryptic. The action is front-loaded, but the sentence-level problems prevent this from being effective concise writing.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness2/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The schema and output schema cover path handling and the destructive hint covers the delete side effect, but the description leaves usage guidance and the dependency behavior ambiguous. It never clearly states that the image is removed only when no cue/overlay references it, nor what the agent should do when the removal is refused.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%; both `name` and `path` are fully documented, including binding behavior and refusal semantics. The prose adds no value beyond the schema, so the baseline of 3 applies.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose3/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description begins with 'Remove a still,' which identifies the verb and resource, but the phrase 'nothing places' is ungrammatical and only becomes decipherable after reading the `name` schema: 'The image to remove. Refused while a cue or overlay places it.' It loosely distinguishes from sibling deletion tools by operating on stills rather than cues/overlays, but does not state this clearly.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

There is no explicit when-to-use versus alternatives guidance. The refusal condition is implied by 'A cue or overlay using it is named instead,' but the description never tells the agent what to do when the image is in use or points to related tools such as `cue_rm` or `overlay_rm`.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

import_editA
DestructiveIdempotent

Lay a cut made in Kdenlive down as this project's timeline.

The supported way to bring an outside edit in. seed_timeline lays a clip down and lets auto-editor find the cuts; this takes a .kdenlive (or .mlt) playlist somebody already trimmed by hand and reads its surviving ranges into the timeline. It replaces the whole timeline, and the previous one is snapshotted first, so it is undoable like any other mutation — which is the part the hand-rolled version of this never had (HISTORY.md § The VO the project was holding: 63 ranges were parsed out of a .kdenlive and written straight to Edit, bypassing cut and its history).

Every clip the document references has to be registered already — the resources are matched against registered clips by resolved path, and any that do not match are named rather than imported behind your back. Pass clip_id for a single-source document whose media sits at a path this project does not know.

Ranges that overrun a clip's registered duration are clamped and reported in overshot, never silently dropped: auto-editor's own exports overshoot the tail by one frame, so a clean overshot is worth reading rather than assuming. plan resolves and checks without writing.

Refused by name rather than half-read: a <blank> in the playlist (real runtime an Edit has nowhere to put), and two playlists carrying different cuts (a multi-track picture edit, which proofcut's one linked A/V track has no shape for).

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
clip_idNoThe registered clip to attribute a single-source document to, when its media sits at a path this project does not know.
documentYesThe `.kdenlive` or `.mlt` playlist somebody already trimmed by hand. Every clip it references has to be registered already; ones that do not match a registered clip by resolved path are named rather than imported behind your back.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.8/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare destructiveHint=true and idempotentHint=true, and the description adds substantial behavioral context: it replaces the whole timeline, snapshots the previous one so it is undoable, clamps and reports overshot ranges rather than silently dropping them, refuses by name rather than half-reading, and requires clips to be registered already. This goes well beyond the annotations and gives the agent a clear model of side effects and failure modes.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but every sentence earns its place: it covers purpose, alternatives, side effects, error behavior, and parameter guidance. It is front-loaded with the core purpose and the key distinction from seed_timeline. It is longer than the typical description, but the complexity of the tool (destructive, with registration requirements and edge cases) justifies the length. A small amount of trimming could improve it, but it is well organized.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's complexity (destructive timeline replacement, registered-clip requirements, clamping behavior, refusal cases, plan mode), the description covers everything an agent needs to call it correctly. The output schema exists, so return values need not be explained. The description even includes a historical note that explains why the undoable behavior matters, which helps the agent understand the tool's guarantees.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the baseline is 3. The description adds extra meaning beyond the schema: it explains the path resolution rules (bound project vs unbound, relative paths, refusal of outside paths), the purpose of plan ('Prefer it over doing the thing and undoing it'), and the exact role of clip_id. The document parameter's description is also enriched by the main description's explanation of registered-clip matching and named refusals. This is more than the schema alone provides, though the schema already covers the basics.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Lay a cut made in Kdenlive down as this project's timeline.' It then distinguishes itself from seed_timeline by explaining that this tool imports a hand-trimmed .kdenlive/.mlt playlist, while seed_timeline lays a clip down and lets auto-editor find cuts. This clearly differentiates it from the closest sibling.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explicitly states when to use this tool ('The supported way to bring an outside edit in'), contrasts it with seed_timeline, and gives concrete conditions: use clip_id for a single-source document whose media sits at an unknown path, and use plan to resolve and check without writing. It also names refusal cases (blank in playlist, two playlists with different cuts), which tells the agent when the tool will not work.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

import_mediaA
Idempotent

Register a media file with the project, probing it with ffprobe.

Links the media by default rather than copying it. Returns the clip record, including the clip_id every other tool takes, and audio_streams — how many the container holds, since every other audio field on the record describes only the first.

A container with more than one audio stream is refused rather than registered as if the first were the recording: whisper picks a stream of its own and MLT picks again at render, so the others would be missing from the film with every check clean. mix=True sums them into one track (two mics of one performance); audio_stream=k keeps one, numbered from 0 in ffmpeg's own audio ordering. Either writes a derived copy under cache/mixed/ that every later op reads without knowing it.

A chapter list or the data/text track it rides on — a movie rip's own inherited from its parent film — is stripped unconditionally, with no flag to opt out: there is no legitimate choice to offer, unlike the audio-stream one. strip/stripped on the record say so when it happened; duration is corrected from the real video/audio streams either way it was detected.

sheet=True by default: a contact_sheet of the clip's first ten seconds rides along on the returned record — cached frames from thumbnail(), so the clip's own opening (credits, black, a slate) is seen before it is cued to a shot rather than discovered after. Pass sheet=False to skip it. --no-sheet on the CLI.

ParametersJSON Schema
NameRequiredDescriptionDefault
mixNoSum a container's audio streams into one track, for two mics on one performance. It writes a derived copy every later op reads without knowing it.
copyNoCopy the media into the project instead of referencing it where it sits. Off by default — a reference costs no disk, and it is also the fallback where symlinks are rejected.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
sheetNoDraw a contact sheet of the clip's first ten seconds onto the returned record. On by default, because a first look that has to be asked for is one nobody takes.
sourceYesThe media file to register. A file argument rather than a project selector, so it is deliberately left unconfined — footage usually lives outside the project.
clip_idNoThe id every later tool addresses this clip by. Unset, one is derived from the filename. Keep it short: it becomes part of cache paths, and a stock Windows measures those against 248 characters.
audio_streamNoKeep one of a container's audio streams and drop the rest, numbered from 0 in ffmpeg's own audio ordering — not the container's absolute stream index, which is a different number once there is video.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.4/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations indicate idempotentHint=true, but description explains that it refuses multi-audio-stream containers unless mix or audio_stream is set, which is a critical behavioral detail. It also discloses that it strips chapter lists and data/text tracks unconditionally, with no opt-out flag, which is a significant side effect beyond the schema. While readOnlyHint=false and destructiveHint=false are consistent, the description elaborates on the derived copy creation and the contact sheet behavior, adding valuable context. It does not contradict annotations, and it goes beyond them in explaining refusal conditions and side effects.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but well-structured, with each paragraph covering a distinct topic: basic registration, audio stream handling, stripping, and contact sheet. It front-loads the core purpose and clip_id return, which is the most frequently needed information. However, some redundancy exists with the schema descriptions (e.g., mix, sheet), and it could be slightly more concise without losing essential context. It is not verbose to the point of obscuring key points.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's complexity (7 parameters, multiple edge cases like multi-audio streams and stripping), the description is remarkably complete. It explains the rationale behind default behaviors, refusal conditions, and derived copies. The output schema exists, so it doesn't need to describe return values, but it does mention the clip_id and contact_sheet. The description covers all necessary operational details an agent would need to correctly invoke this tool, including caveats about file paths and cache limits.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the schema already documents all parameters. The description adds some value by explaining the default linking vs copying behavior and the audio stream handling rationale, which goes beyond the schema. However, it doesn't significantly extend the meaning of parameters like 'path' or 'source' that are already well-described in the schema. It does clarify 'mix' and 'audio_stream' usage in context, but overall it's a moderate addition over the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool's verb ('Register'), resource ('a media file with the project'), and method ('probing it with ffprobe'). It distinguishes itself from sibling tools like 'import_edit' and 'list_media' by specifying it creates a clip record and returns a clip_id. The purpose is unambiguous and specific, not a tautology.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explicitly states when to use this tool versus alternatives: it mentions 'every other tool takes' the clip_id, and it explains the default linking behavior. It also provides clear conditions for using optional parameters like 'mix=True' for multiple audio streams and 'audio_stream=k' for keeping one. It implies this is the entry point for adding media, unlike 'list_media' which likely just lists. There is explicit guidance on when to use the tool and when not to (e.g., refusing multi-audio-stream containers unless mix or audio_stream is specified).

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

initA
Idempotent

Create a proofcut project directory at path.

Writes proofcut.json and the empty assets/, cache/, media/ and renders/ directories, and nothing else — no media, no timeline. Refuses a directory that already holds a project rather than resetting it, so it is safe to call when unsure. Next is import_media, then a transcript, then seed_timeline.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameNoA name for the project, recorded in the manifest. Unset, the directory's own name is used.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.9/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already mark it as idempotent and non-destructive, but the description adds crucial context: it writes only specific files and refuses to overwrite an existing project. This directly explains the idempotent behavior and gives the agent confidence about side effects. It also states what it does not do (no media, no timeline), which is valuable for setting expectations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is well-structured: the first sentence states the core action, the second details outputs and safety behavior, and the third gives the workflow sequence. It is concise with no redundant phrases, and the most important information is front-loaded.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's simplicity, the description covers the essential aspects: what it does, what it writes, what it refuses, and how to proceed next. The output schema exists to define the return value, so that is not a gap. The description also handles edge cases (bound vs unbound) clearly. Nothing an agent needs to call it correctly is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so both parameters are described in the schema. However, the description adds substantial meaning for the path parameter: how it resolves when bound to a project, relative path behavior, and refusal of external paths. This goes beyond the schema's basic description. The name parameter is not addressed in the description, but its schema description is adequate, so the added value is focused on the critical parameter.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool creates a proofcut project directory at a given path, specifies exactly what it writes (proofcut.json and four empty directories), and what it does not (media, timeline). It also positions itself as the first step before import_media and seed_timeline, differentiating it from sibling tools like migrate_project.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explicitly states when it is safe to call ('safe to call when unsure') because it refuses to reset an existing project, and provides a clear sequence of next steps: import_media, transcript, seed_timeline. It also gives detailed guidance on the path parameter, including bound-project behavior and refusal of paths outside the project, which helps an agent decide when and how to invoke it.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

inset_addA
Idempotent

Draw a clip into a rectangle of the recording, following its camera — a render inside the app's preview.

rect is where the recording shows what the inset replaces, in the recording's own pixels, and must be the clip's shape. The inset moves and zooms with the recording's reframe windows, so a push into the preview fills the frame with the clip itself, at full sharpness. The span starts at a word, phrase or event of clip_id and ends at one, at a length, or at the clip's end; it plays at 1x and must lie inside one continuous, 1x stretch of the recording (no cut, no retimed span under it).

It fades in and out by default, can dim the recording around it, and plays its own audio with the music bed out underneath (dipped, with a duck) unless mute; level="speech" measures it and sets gain_db. The reply echoes where it plays and dest, where its rect lands in the canvas; plan=true writes nothing. Any inset routes export through the MLT writer, and export's reply gives each inset's rect at its first and last frame.

ParametersJSON Schema
NameRequiredDescriptionDefault
dimNoDarken the recording around the inset, 0 (none, the default) to 1 (black); 0.55 reads well.
muteNoPlay none of the asset's audio (and leave the bed alone).
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
rectYes[x0, y0, x1, y1] in the recording's OWN pixels: where the recording shows the thing the inset replaces (a preview pane). Must be the asset's shape, within 1%.
afterNoA forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start.
assetYesThe clip to draw, by clip_id: the render an agent made, in a launch clip. Needs picture.
enterNoHow it appears: `fade` or `none` (a cut). Default fade.
eventNoStart on this event of clip_id: `name`, or `name#k` when the name repeats. Usually the moment the recording's own preview starts playing, which locks the two.
leaveNoHow it goes: `fade` or `none`. Default fade.
levelNo'speech' measures the span the inset plays, once, and records the gain_db that brings its speech to -18 dBFS RMS, the launch clip's film level. Not with gain_db.
phraseNoStart on this phrase's FIRST word, resolved against clip_id's transcript.
src_inNoSeconds into the asset the inset starts from. Default 0.
clip_idYesThe recording the inset is drawn into — its camera (reframe windows) is what the inset follows, and its words or events address the span.
gain_dbNoThe asset's own audio level in dB. Default 0. The music bed goes out under it, or dips under it when the bed has a duck.
secondsNoEnd this long after the start.
positionNoWhere in the stack it goes: 0 is the bottom, omitted is the top.
enter_easeNoThe fade's curve: linear, ease, ease-in or ease-out. Default ease.
leave_easeNoThe fade's curve: linear, ease, ease-in or ease-out. Default ease.
occurrenceNoDisambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at.
word_indexNoThe word the inset starts on. One of word_index, phrase or event.
until_eventNoEnd on this event of clip_id.
until_phraseNoEnd as this phrase's LAST word ends.
enter_secondsNoHow long the fade in takes. Default 0.4.
leave_secondsNoHow long the fade out takes. Default 0.4.
until_word_indexNoEnd as this word ends. At most one of until_word_index, until_phrase, until_event or seconds; none runs to the asset's end.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.5/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the annotations, it discloses side effects and rendering behavior: it writes unless `plan=true`, fades by default, dims the recording, lowers the music bed or ducks, routes through the MLT writer, and returns rect locations. It also states a hard constraint (must lie inside one continuous 1x stretch). No contradiction with annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but organized into purpose, geometry/span constraints, and effects/plan/export, with the core definition front-loaded. Every sentence carries operational meaning, and the length is proportionate to the tool's 26-parameter complexity.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the rich schema and output schema, the description covers the essential behavioral model: span anchoring, reframe behavior, audio handling, planning mode, and export behavior. An agent has enough context to call this tool correctly without needing to infer hidden side effects.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The schema already documents all 26 parameters, so the baseline is 3. The description adds value by explaining relationships between parameters (`rect` must match the clip's shape and follows reframe windows; `level="speech"` measures and sets `gain_db`; `plan=true` writes nothing), which helps an agent choose combinations correctly.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The opening sentence names a specific action ('Draw a clip into a rectangle of the recording'), identifies the resource (a clip/asset inside a recording), and distinguishes the behavior from list/remove siblings (inset_ls, inset_rm). It also adds the distinguishing 'following its camera' detail that sets insets apart from static overlays.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description implies the tool is for adding a camera-following picture-in-picture inset and states important placement constraints, but it does not explicitly name alternatives or say when not to use it. The only guidance about choosing an approach is internal: prefer `plan=true` over doing the thing and undoing it.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

inset_lsA
Read-onlyIdempotent

Every inset, bottom of the stack first, with where each plays and where its rect lands.

Each carries its position (as inset_rm takes it). Insets that cannot resolve — a cut removed a start word — come back as insets_error beside the stored records, so the one to move or remove can still be found.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.5/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already mark the tool read-only, idempotent, and non-destructive. The description adds genuinely new behavior: stack order ('bottom of the stack first'), the inclusion of `position` in each entry, and the error-container behavior for unresolved insets ('cut removed a start word'). This goes beyond the structured hints.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Three short, information-dense sentences. The main result is stated first, followed by the position convention, then the failure behavior. No filler or repetition of schema content.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a one-optional-parameter read tool with an output schema, the description covers ordering, output content, and error handling; the schema covers path semantics, so an agent has everything needed to invoke it correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The schema already documents the only parameter (`path`) at 100% coverage with a full explanation of bound/unbound behavior. The description adds nothing about parameters, so the appropriate baseline is 3.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The opening line 'Every inset, bottom of the stack first...' specifies the operation (list all insets), the resource (insets), the ordering, and what is reported (play position and rect). It also references inset_rm's position format, separating this read/list tool from its sibling inset_add/inset_rm.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description tells the agent when the listing is useful: to locate stored records and their position for moving/removing via inset_rm, and that unresolved insets are still returned as errors. It does not explicitly state when to avoid the tool or compare it to other list tools, but for a read-only enumeration this context is sufficient.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

inset_rmA
Destructive

Take one inset off the recording, by its position in inset_ls.

The clip stays registered. Positions above the removed one move down by one.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
positionYesThe inset to remove, by its position in inset_ls.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.5/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare destructiveHint=true and readOnlyHint=false, so the safety profile is covered. The description adds useful behavioral context beyond that: the clip stays registered, and positions above the removed one shift down by one. This tells the agent about side effects on other insets, which is valuable and not duplicated by annotations or schema.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is two short sentences with no filler. It front-loads the core action, then gives the essential behavioral caveats. Every sentence earns its place.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a straightforward removal tool, the description covers what it removes, how the target is identified, and the two important side effects. The output schema exists, annotations carry the destructive warning, and generic parameters (path, plan) are fully documented in the schema. Nothing needed for correct invocation is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3. The description adds meaningful semantics for the 'position' parameter by clarifying that positions are stable until a removal and that subsequent positions shift down by one. This goes beyond the schema's simple phrase 'by its position in inset_ls' and helps an agent reason about valid inputs and consequences.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific action ('Take one inset off'), a specific resource ('the recording'), and the selection mechanism ('by its position in inset_ls'). This clearly differentiates it from sibling tools like inset_add, inset_ls, and the other *_rm tools, so an agent can identify it correctly without opening the schema.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives clear context for when to use this tool: it removes an inset identified by its position in inset_ls, implying one should list insets first. It doesn't explicitly exclude alternatives or name when-not conditions, but for a remove-by-index operation the context is sufficient; it does not mislead.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

lexicon_addA
DestructiveIdempotent

Keep a standing spelling correction: captions print canonical wherever whisper wrote heard.

The fix for a caption that shows whisper's spelling ("rough" for "ruff", "Pup BNB" for a brand). Whole words, one or several: a multi-word key merges its words into one caption word. Every occurrence, so narrow one by including a neighbouring word. Display only; the transcript and verify are untouched. The reply counts the caption words it changes now.

Undo does not revert it: the lexicon is a preference kept beside the project, not an edit. Remove an entry with lexicon_rm. kind="say" is vo_synth's pronunciation respelling instead.

ParametersJSON Schema
NameRequiredDescriptionDefault
kindNo`hear` (default): a caption correction, also folded out of `vo_synth`'s WER. `say`: a respelling `vo_synth` gives the voice model.hear
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
heardYesThe words as whisper spelled them, one or several (`rough`, `pup bnb`). Matched as whole words, case and edge punctuation aside, at every occurrence; carry a neighbouring word to narrow it to one place.
canonicalYesWhat to print instead (`hear`) or what the voice model is given (`say`). Written as it should appear: `PupBnB` keeps its capitals.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The description discloses critical behavioral traits beyond the annotations: persistence ('the lexicon is a preference kept beside the project, not an edit'), non-reversibility ('Undo does not revert it'), scope ('Display only; the transcript and `verify` are untouched'), and matching behavior ('Every occurrence'). This complements the destructiveHint and idempotentHint annotations rather than contradicting them, and no contradiction is present.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but every sentence earns its place: core purpose first, then matching rules, undo behavior, removal alternative, and kind distinction. It is well-structured with a clear separation of concerns, and nothing is redundant or filler.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's complexity (five params, two modes, persistence semantics, undo interaction), the description covers all necessary ground: what it does, when to use it, how to remove entries, what is untouched, and how `plan` can be used safely. An output schema exists, so return-value details are not required. Nothing an agent needs to decide on or invoke this tool is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100% with rich descriptions for all five parameters. The description adds some contextual guidance, such as 'Whole words, one or several: a multi-word key merges its words into one caption word' and the narrowing tactic, but this largely repeats what the schema already states. Baseline 3 is appropriate because the schema carries the semantic load.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The opening sentence states a specific verb and resource: 'Keep a standing spelling correction: captions print `canonical` wherever whisper wrote `heard`.' It names the exact mapping behavior and distinguishes itself from siblings by explicitly addressing `lexicon_rm` and the `kind="say"` alternative for `vo_synth`. An agent can tell what this tool does and how it differs from related tools.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives clear when-to-use context: 'The fix for a caption that shows whisper's spelling' — and provides explicit exclusions and alternatives: 'Remove an entry with `lexicon_rm`' and 'kind="say" is `vo_synth`'s pronunciation respelling instead.' It also steers users toward `plan` over executing destructive changes, which is practical guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

lexicon_lsA
Read-onlyIdempotent

The project's standing corrections: hear (captions) and say (vo_synth).

Read-only. hear maps whisper's spelling to what captions print; say maps a scripted word to what the voice model is given. caption_view's corrected shows where the hear rules fired.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A3.5/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already provide readOnlyHint, idempotentHint, and destructiveHint, so the bar is lower. The description adds useful content-level context by explaining what `hear` and `say` map and where `caption_view` shows `hear` rule firings. No contradiction with annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact and front-loads the core concept in the first sentence. The `caption_view` sentence is somewhat tangential, and 'Read-only' is redundant with the annotations, but neither adds meaningful bulk.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a read-only, zero-required-param list tool with an output schema and safety annotations, the description provides adequate context about the lexicon's content. It could be stronger with an explicit 'list' action and a pointer to the add/remove siblings, but no critical operational information is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The only parameter, `path`, is fully documented in the schema with 100% coverage, including its default and binding behavior. The description adds no parameter-specific detail, so the baseline score of 3 applies.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description identifies the resource ('project's standing corrections') and its two categories (`hear` and `say`), so the scope is clear. It stops short of a 5 because it never uses an explicit verb like 'list' and does not directly distinguish the tool from `lexicon_add`/`lexicon_rm`.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

There is no guidance on when to use this tool versus alternatives. It does not point to `lexicon_add` or `lexicon_rm` for modifications, and 'Read-only' only describes safety, not selection conditions.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

lexicon_rmA
Destructive

Remove one lexicon entry; refuses a key the lexicon does not hold.

The caption goes back to whisper's spelling. lexicon_ls lists the entries.

ParametersJSON Schema
NameRequiredDescriptionDefault
kindNo`hear` (default) or `say`: which table the entry is in.hear
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
heardYesThe entry's key, matched the way `lexicon_add` matches it.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

In addition to the destructiveHint annotation, the description discloses that an unknown key is refused and that captions revert to whisper's spelling after removal. These are meaningful side-effect and failure-mode details an agent could not get from annotations alone.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The entire description is two short sentences with no filler: the first states the action and error behavior, and the second gives a necessary side effect plus the listing alternative. It is front-loaded and every clause contributes.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given a rich schema, a destructiveHint annotation, and an output schema, this description covers the core action, the relevant failure case, and the side effect that matters after deletion. The `plan` dry-run option is already explained in the parameter schema, so nothing essential is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

With 100% schema coverage, the baseline is 3, and the schema already explains `kind`, `path`, and `plan` thoroughly. The description earns a 4 by adding the contract for the `heard` key: a key not held by the lexicon is refused.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description names a specific verb and resource — 'Remove one lexicon entry' — and adds a distinguishing behavioral detail: it refuses keys the lexicon does not hold. It also names `lexicon_ls` as the listing counterpart, so it is clearly separable from the sibling list and add tools.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The intended use is stated plainly (remove a single lexicon entry) and the description explicitly points to `lexicon_ls` for inspecting entries, which is the natural pre-removal workflow. It does not enumerate all sibling alternatives or exclusions, so it stops short of a 5.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

list_mediaA
Read-onlyIdempotent

List media files under source_dir that import_media could register.

What hands an unattended agent source paths on a real job, since an agent confined to proofcut's tools (the agent panel's --tools ToolSearch) has no directory listing of its own (HISTORY.md § The seventh queue item, decided and built). A filename filter, not a probe — import_media is still what decides a file is actually usable. Each entry's already_imported is checked against this project's own registered clips, so a repeated call does not keep re-suggesting footage already on the asset list. source_dir names wherever the footage lives and is not confined to the project.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
recursiveNoWalk subdirectories too. On by default.
source_dirYesThe directory to list. It names where footage lives rather than which project, so it is deliberately not confined to the bound project.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already establish read-only, idempotent, non-destructive behavior. The description adds useful context beyond that: `already_imported` is checked against the project's registered clips, repeated calls avoid re-suggesting existing footage, and `source_dir` is not confined to the bound project. No contradiction with annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness3/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The first sentence is strong and front-loaded, but the second paragraph is verbose and includes tangential references to HISTORY.md and panel flags that do not help an agent call the tool. The content is relevant overall, but it could be trimmed without losing usefulness.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the output schema and full parameter documentation, the description provides enough context for correct invocation: what the tool lists, how `already_imported` is determined, and that `source_dir` is intentionally not project-constrained. Nothing critical for selecting or using the tool is missing, though the phrasing could be more direct.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the baseline of 3 applies. The description's note about `source_dir` largely restates what the schema already says; it adds behavioral context but no new per-parameter semantic details beyond the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The first sentence states the exact verb, resource, and scope: "List media files under `source_dir` that `import_media` could register." It also distinguishes this from being a probe, clarifying that it is a filename filter and not the tool that decides usability.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explains the main use case: handing source paths to an unattended agent that has no directory listing of its own. It also gives an important exclusion: this is not a probe, and `import_media` remains the authority on whether a file is usable. It could be tighter by naming sibling alternatives explicitly, but the guidance is clear.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

locateA
Read-onlyIdempotent

Where does a SOURCE word or SOURCE time play in the current render?

cut_by_time's read-only mirror, and the tool to reach for before quoting any timestamp to a human: word indices and transcript times address the original recording, so they are NOT render times and every accumulated cut moves them further apart.

Two clocks, and this reports the Edit's. timeline_start/ timeline_end are 0 = the Edit's own first frame, unchanged whether or not a head (a cold open) is configured. head_seconds rides along (0.0 with none) so a caller that needs the actual render time — this tool's own stated purpose — can add it: render time = Edit time + head_seconds.

Address it one way per call — first/last are inclusive word indices (last defaults to first), source_start/source_end are seconds into the recording (omit source_end to locate an instant), or phrase — a phrase naturally is a range, so it resolves straight to first/last with no edge to pick (after/occurrence disambiguate a phrase matching more than once), or event — a named instant from events.

Read present first. False means the material is not in the render, and beyond_source distinguishes "you cut it" from "the recording never went that far". A partially-cut range is normal: placements lists each surviving piece in playback order with the source coordinates saying which part of the phrase it is, covered how much survives, and contiguous whether the survivors still play back-to-back. Word mode (and phrase mode, which resolves into it) echoes the resolved words plus three either side; time mode echoes the words the interval overlaps, or its nearest neighbours if it landed in silence. Read-only: nothing is written.

ParametersJSON Schema
NameRequiredDescriptionDefault
lastNoLast word index, inclusive. Defaults to `first`.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
afterNoA forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start.
eventNoLocate a named instant from `events`, as `name` or `name#k` (k counts that name's events from 0). Echoed with its neighbours.
firstNoFirst word index, inclusive. Address it one way per call: `first`/`last`, `source_start`/`source_end`, or `phrase`.
phraseNoLocate by wording. A phrase is naturally a range, so it resolves straight to first and last with no edge to pick.
clip_idYesThe transcript, or the recording, the address belongs to.
occurrenceNoDisambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at.
source_endNoEnd of the source interval, in the recording's own seconds.
source_startNoSeconds into the original recording. Omit `source_end` to locate an instant.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A5/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already state readOnlyHint=true and idempotentHint=true; the description reinforces 'Read-only: nothing is written.' Beyond that, it discloses the two-clock nuance (Edit time vs render time with head_seconds), the meaning of 'present', 'beyond_source', 'placements', 'covered', and 'contiguous', and how word/time modes echo results. This is far beyond the annotations and provides a full behavioral contract.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but every sentence carries necessary information. It is structured into logical paragraphs: purpose, clock explanation, addressing modes, output guidance, and a final read-only note. It front-loads the core purpose and uses bold to emphasize key terms, making it scannable despite its length. No fluff or repetition.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The tool is complex with 10 parameters and multiple addressing modes; the description covers every mode (word, time, phrase, event), explains defaults and edge cases (ambiguous phrase, silence, partial cuts), and specifies how to read the output (present, beyond_source, placements, covered, contiguous). It also mentions the output schema exists, so return values are not the description's job. It is complete for an agent to call correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters5/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

With 100% schema coverage, the schema already documents each parameter, but the description adds crucial semantic context: the one-way-per-call rule, how last defaults to first, how phrase resolves to first/last, how after/occurrence disambiguate, and how event is addressed. It explains the output semantics (present, placements, covered, contiguous) that tie parameters to results, which is essential for correct invocation.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a direct question that states exactly what the tool does: locate where SOURCE words or times play in the current render. It identifies itself as the read-only mirror of cut_by_time, which distinguishes it from that sibling and from other tools. The verb 'locate' plus the resource (source material in render) is specific and unambiguous.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explicitly frames when to use it: 'the tool to reach for before quoting any timestamp to a human,' and explains the crucial difference between source and render times, warning that source indices are not render times. It names cut_by_time as the counterpart and implies this is the read-only variant. No exclusionary guidance is needed beyond this, as the purpose is clear.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

migrate_projectA
DestructiveIdempotent

Bring an older project manifest forward to the current schema version.

Every other tool refuses a project written by an older proofcut rather than guessing at a layout it does not recognise; this is what clears that. It is forward-only, and it copies the manifest into cache/history/ before writing. plan=True reports the version and the steps without writing, which is how to ask what a project is before deciding to change it. A project whose manifest is still lucid.json (written before the rename) is renamed to proofcut.json first, reported as the first step.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the annotations (delete/rebuild, idempotent, read-write), the description discloses that it copies the manifest into cache/history before writing, is forward-only, and handles the pre-rename lucid.json case. No contradiction with the annotations exists.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is information-dense with no filler. It front-loads the core purpose, then adds justification, safety behavior, plan usage, and an edge case in logical order. Every sentence contributes useful guidance.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a migration tool with an output schema and rich parameter descriptions, the description covers the what, when, why, safety mechanism, dry-run alternative, and an important edge case. An agent has everything needed to invoke it correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, and both path and plan already carry detailed descriptions in the schema. The tool description adds minor reinforcement about plan=True reporting version and steps, but it does not fundamentally extend what the schema already states.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Bring an older project manifest forward to the current schema version.' It also distinguishes this tool from everything else by noting that 'every other tool refuses' such projects, so the agent can identify exactly when migrate_project applies.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It gives explicit context for use: older project manifests that other tools refuse. It also explains the plan=True mode as the safe way to inspect before changing, which is a clear usage directive. The 'forward-only' statement further sets expectations about directionality.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

musicA
DestructiveIdempotent

Read or change the A2 music bed this project mixes under its edit.

Call with no arguments to read what is in force. The bed stores word indices and an asset, never a length: it starts where word_index_start of clip_id (the VO transcript) lands on the timeline and runs to where word_index_end ends — or to the end of the edit — so a cut before either boundary moves both. Duration is derived at build time. On a recording with no words, event/until_event (and a passage's event) address its logged events instead.

The first set needs asset, clip_id and a start (word_index_start or phrase_start) together; after that each field updates on its own. A field set by phrase stores the phrase beside the index it resolved to, so cue_reresolve can re-derive it; set by plain index, the stored phrase is cleared. Both boundaries are echoed with their resolved words and neighbours — check them.

Beyond one asset from its head: passages (more pieces, each from its own word), rotate (assets in turn), crossfade, src_in; under levels the bed below the voice, or loudness to a LUFS where there is no voice; duck dips it while the voice speaks, keyed off the edit's own audio, audible insets and ducks sounds at export; over_tail plays it on under the end card. export's music field says what the render carried. clear_* and reset undo each; plan validates without writing.

ParametersJSON Schema
NameRequiredDescriptionDefault
duckNoPull the bed this many dB down while the voice is speaking and let it back up in the pauses. It is keyed off the timeline's own audio at export rather than the transcript's word timings, which were measured against a bed recovered from a real render and beaten: 2.72 dB off for the audio gate against a word-span duck's 3.39. It also hears audible insets and sounds placed with `ducks`.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
afterNoA forward cursor over the matches of `phrase_start`/`phrase_end`: any match at or before this word index is skipped. -1, the default, means from the start.
assetNoThe bed's own music, as a registered clip id — never `card:name`, since a held frame has no sound. It plays from its own head; shorter than its span pads with real silence, longer is trimmed.
eventNoStart the bed on this event of clip_id instead of a word: `name`, or `name#k` when the name repeats. Replaces a start word.
resetNoDrop the bed entirely.
underNoLevel the whole bed this many LU below the voice, measured. It is a fixed offset; `duck` is the moving one.
rotateNoFurther assets to play in turn as each one runs out, overlapping by `crossfade`. `[]` clears them.
src_inNoWhere inside the bed's own asset it starts, in seconds.
clip_idNoThe clip whose words (or events) the bed addresses — the VO, not the music.
fade_inNoSeconds of fade at the bed's start. The fades ride the bed's own entry, so a fade-out ends where the music audibly ends.
fade_outNoSeconds of fade at the bed's end. A fade pair the bed cannot hold refuses at build time rather than being clamped.
loudnessNoLevel the whole bed to this many LUFS, measured — for a film with no voice for `under` to sit below, such as a screen recording. Setting it drops `under`, and `under` drops it. The launch clip's approved bed reads -23.3.
passagesNoReplace the list of passages after the bed's own asset: each `{asset, word_index_start | phrase_start | event, src_in?, crossfade?, rotate?}`. `[]` clears them.
clear_endNoDrop the end word, returning the bed to running to the end of the edit.
crossfadeNoSeconds two pieces overlap by. A crossfade edge is equal-power rather than the straight dB line an ordinary fade draws — two straight fades crossing sum to a hole.
over_tailNoTrue runs a bed with no end boundary on under the tail's card, so the card is not silent and `fade_out` ends with it. False ends it with the edit, the default.
clear_duckNoReturn the bed to one level, with no ducking.
occurrenceNoDisambiguate `phrase_start`/`phrase_end` by count, **1-based**. Unset, an ambiguous phrase is refused rather than guessed at.
phrase_endNoSet the out-point by wording instead; it binds the phrase's last word. Each boundary is independent — one can be a phrase and the other an index.
clear_underNoReturn every asset to its own level.
until_eventNoEnd the bed on this event of clip_id. Replaces an end word; `clear_end` drops it.
phrase_startNoSet the in-point by wording instead; it binds the phrase's first word. The resolved phrase is stored beside the index, so `cue_reresolve` can re-derive it after a re-record.
clear_loudnessNoDrop the `loudness` level.
word_index_endNoWhere the bed goes out. Unset means *to the end of the edit*, so a tail holds over silence unless `over_tail`.
word_index_startNoWhere the bed comes in, as a word of `clip_id`. The bed stores words and never a length, so a cut before either boundary moves it automatically.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.8/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The description goes well beyond annotations: it explains that the bed stores words not lengths, cuts move both boundaries, duration is derived at build time, phrase-set boundaries store phrases for cue_reresolve, `under` and `loudness` drop each other, and ambiguous phrases are refused. These behaviors are not visible in the annotations or schema alone.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but front-loaded: the core read/write purpose and no-arg read behavior come first, then dependencies, then optional features. Every sentence contributes a distinct fact, with no filler, and the organization is appropriate for a 27-parameter tool.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a high-complexity tool with an output schema, the description covers the read path, setup prerequisites, edge cases (no words, no voice, ambiguous phrases, cuts), side effects, and validation via `plan`. Nothing needed to invoke it correctly is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters5/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Even though schema coverage is 100%, the description adds crucial cross-parameter meaning: first-set dependencies, boundary independence, event addressing on wordless recordings, phrase storage/clearing behavior, and the effect of `clear_*` and `reset`. It clarifies how parameters interact rather than merely restating types.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Read or change the A2 music bed this project mixes under its edit.' This clearly identifies what the tool operates on and distinguishes it from the many sibling tools by its focus on the music bed.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It explicitly states 'Call with no arguments to read what is in force,' gives the first-set requirement ('needs asset, clip_id and a start together'), and recommends `plan` over executing. It covers when event-based addressing is needed, but it does not name alternative sibling tools or state explicit when-not-to-use conditions.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

overlay_addA
Idempotent

Draw a transparent card, an animated graphic or a still over the film — a lower third, a graphic, a sticker.

Make the card first with card_new from lowerthird (a headline and an optional footnote, bottom left) or scrim (a dark gradient for type to sit on). The span starts at a word, phrase or event of clip_id and ends at a word, phrase, event or length; it is resolved through the timeline on every build and never stored as seconds, so cuts move it, and a cut through its start word makes export refuse until it is moved.

The stack is list order: a later overlay draws over an earlier one it overlaps. Put the scrim first (or position=0), then the lowerthird. A staggered footnote is its own lowerthird with an empty headline, starting later. The reply echoes the words or event each end resolved to and where it plays; plan=true writes nothing. Any overlay routes export through the MLT writer, and export's reply lists the overlays it drew.

ParametersJSON Schema
NameRequiredDescriptionDefault
xNoA sticker's centre across the frame: 0 is the left edge, 1 the right. Default 0.5.
yNoA sticker's centre down the frame: 0 is the top, 1 the bottom. Default 0.5.
cardNoThe overlay card to place: one made by card_new from an overlay template (`lowerthird`, `scrim`), by name or as `card:NAME`. An ordinary card is opaque and is refused. One of card, graphic or image; each takes its own prefix.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
afterNoA forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start.
enterNoHow it appears: `rise` (moves up while fading in), `fade`, `pop` (scales up past full size and settles), `slide-left`/`slide-right`/`slide-top`/`slide-bottom` (in from that edge), or `none` (a cut). Default rise for a card, pop for an image, none for a graphic.
eventNoStart on this event of clip_id: `name`, or `name#k` when the name repeats.
imageNoA still (image_add) to place as a sticker, instead of a card or graphic. It pops in and fades out unless enter/leave say otherwise.
leaveNoHow it goes: `fade`, `rise` (moves down while fading out), `pop`, a `slide-` out to that edge, or `none`. Default fade for a card or image, none for a graphic.
styleNo`plain`, or `photo`: a white border and a soft shadow, a photo card.
widthNoA sticker's width, as a fraction of the frame's width. Default 0.3.
phraseNoStart on this phrase's FIRST word, resolved against clip_id's transcript.
rotateNoDegrees to turn a sticker, clockwise; negative turns it the other way.
clip_idYesThe clip whose words or events address the span — the transcript the word indices index, or the recording the events belong to.
graphicNoAn animated graphic (graphic_new) to place instead of a card. Its intro plays from the start, its outro ends at the end, and its hold fills the span between; a span shorter than intro plus outro is refused. It enters and leaves with no motion of its own unless enter/leave say so.
secondsNoEnd this long after the start. A length, so a cut inside the span does not shorten it.
positionNoWhere in the stack it goes: 0 is the bottom, omitted is the top. A later overlay draws over an earlier one it overlaps, so a scrim goes before its type.
enter_easeNoThe entrance's curve: linear, ease, ease-in or ease-out. Default ease-out.
leave_easeNoThe exit's curve: linear, ease, ease-in or ease-out. Default ease-in.
occurrenceNoDisambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at.
word_indexNoThe word the overlay starts on. One of word_index, phrase or event.
until_eventNoEnd on this event of clip_id.
until_phraseNoEnd as this phrase's LAST word ends.
enter_secondsNoHow long the entrance takes. Default 0.45.
leave_secondsNoHow long the exit takes. Default 0.3.
until_word_indexNoEnd as this word ends. One of until_word_index, until_phrase, until_event or seconds.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A5/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the annotations, the description reveals substantial behavioral details: spans are resolved through the timeline and never stored as seconds, cuts move them, a cut through the start word makes export refuse, the stack order determines draw order, and any overlay routes export through the MLT writer. This is meaningful context the annotations alone do not provide.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but every sentence earns its place: purpose, prerequisites, span semantics, stack ordering, and call consequences. It is front-loaded with the clearest statement of what the tool does and then layers supporting detail logically, which is efficient for a tool with this many parameters.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given 27 parameters, a fully documented input schema, an output schema, and meaningful annotations, the description adds the missing conceptual glue needed to call the tool correctly. Return values are covered by the output schema, and defaults are covered by the schema descriptions, so nothing essential is left unexplained.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters5/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Although schema coverage is 100%, the description supplies the unifying conceptual model: what a span is, how start/end selectors relate, that card/graphic/image are alternative sources, and that position expresses stack order. This helps an agent choose among the many interrelated parameters rather than treating each parameter in isolation.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The opening sentence names a concrete action ('Draw ... over the film') and a precise resource, then enumerates supported content types: a transparent card, an animated graphic, or a still, with examples like lower third and sticker. This clearly differentiates it from overlay_ls/overlay_rm and from the content-creation tools card_new, graphic_new, and image_add.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It gives explicit preconditions ('Make the card first with card_new from lowerthird or scrim'), stacking rules ('Put the scrim first ... then the lowerthird'), and a preview path ('plan=true writes nothing'). It also covers edge cases such as a staggered footnote and warns about timeline-sensitive span behavior, giving an agent clear guidance on how and when to invoke this tool.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

overlay_lsA
Read-onlyIdempotent

Every overlay, bottom of the stack first, with where each plays now.

Each carries its position (as overlay_rm takes it), its lane, and its timeline span. A stack that cannot resolve — a cut removed a start word — comes back as overlays_error beside the stored records, so the one to move or remove can still be found.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.2/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true, idempotentHint=true, destructiveHint=false, so the safety profile is covered. The description adds valuable behavioral context: the ordering (bottom of stack first), the error behavior when a stack cannot resolve (returns overlays_error beside stored records), and the purpose of carrying position/lane/span. This goes beyond annotations and helps the agent understand edge cases.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact and front-loaded: the first sentence states the core function and ordering. The second sentence adds essential detail about error handling and the data carried. Every sentence earns its place, and there is no fluff or repetition of schema content.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The description is complete for a read-only listing tool. It explains ordering, data carried, and error behavior. The output schema exists, so return values don't need to be described. The only minor gap is not explicitly stating when to prefer this over overlay_rm or overlay_add, but the read-only nature and listing purpose are clear from annotations and description.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the schema already fully documents the single optional 'path' parameter. The description doesn't add parameter-specific semantics beyond what the schema provides, but it does explain the context of the returned data (position, lane, span) which indirectly clarifies what the tool operates on. Baseline 3 is appropriate given full schema coverage.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific verb and resource: list every overlay, bottom of the stack first, with where each plays now. It also distinguishes itself from sibling tools like overlay_add and overlay_rm by focusing on listing, and it explains the ordering and the data carried per overlay. This is clear and specific.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description implies when to use this tool: when you need to see all overlays and their positions, lanes, and timeline spans. It doesn't explicitly name alternatives or exclusions, but the context of listing vs. adding/removing is clear from the sibling names and the description's focus on enumeration. It could be stronger with an explicit 'use this instead of overlay_rm when you need to inspect before removing' but the context is sufficient.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

overlay_rmA
Destructive

Take one overlay off the film, by its position in overlay_ls.

The card stays under assets/cards/, so it can be placed again. Positions above the removed one move down by one.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
positionYesThe overlay to remove, by its position in overlay_ls (0 is the bottom).

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already establish this as destructive; the description adds meaningful behavioral detail beyond that: removing the overlay leaves the card under assets/cards/, re-placement is possible, and positions above shift down by one. This helps the agent predict consequences without contradicting the destructive hint.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact: two sentences, with the core action front-loaded and the behavioral consequences stated in the second sentence. Every sentence adds information about what the tool does or what the agent should expect afterward.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a removal tool with a rich schema, an output schema, and clear annotations, the description covers the essential context: how to select the overlay, that the card persists, and that indices shift. It does not spell out invalid-position behavior or prerequisites, but those are not necessary given the schema and sibling overlay_ls.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100% and the schema already documents position as the overlay index in overlay_ls and the semantics of path and plan. The tool description mostly repeats position's meaning and adds no new parameter-level detail, so the schema carries the weight as expected.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific action ('Take one overlay off the film') on a specific resource ('overlay') and identifies the selection mechanism ('by its position in overlay_ls'). This clearly distinguishes overlay_rm from overlay_add and overlay_ls and from other removal tools like inset_rm or cue_rm.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description implies when to use the tool: remove an overlay by referencing its position in overlay_ls. It gives useful context such as the card remaining re-placeable and positions shifting, but it does not explicitly state when not to use it or name alternatives, leaving some routing to inference.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

pack_activateA
DestructiveIdempotent

Switch the active pack variant to one already snapshotted by pack_apply.

No file re-read — refuses an unknown variant by name, naming the ones that are actually available, rather than trying to load it here.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
variantYesWhich already-snapshotted variant to switch to. No file is re-read, and an unknown name is refused by listing the ones that are available.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.2/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already signal destructiveness and idempotency; the description adds concrete behavior beyond that: it refuses unknown variant names by listing available ones, and it never re-reads files. This meaningfully supplements the structured hints without contradicting them.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Two short sentences with the primary action front-loaded and the refusal/no-re-read behavior placed second. No filler or redundant restatement of the schema.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a mutation tool with strong annotations, an output schema, and fully described parameters, the description covers the essential precondition, the no-re-read guarantee, and the error behavior. It leaves the relationship to pack_status/pack_show implicit, but nothing critical is missing for correct invocation.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, and the schema already documents path, plan, and variant in detail. The tool description mainly restates variant's 'already snapshotted' constraint, so it adds little over the parameter schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific action and resource: 'Switch the active pack variant to one already snapshotted by pack_apply.' It also names the relevant sibling, making it easy to distinguish from pack_apply, pack_show, and pack_status.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description clarifies the key precondition: the variant must already be snapshotted by pack_apply, and no file re-read is involved. It gives clear context for when the tool applies, though it does not explicitly exclude alternative tools or state when not to use it.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

pack_applyA
DestructiveIdempotent

Load a channel preset pack, resolve and snapshot every variant, activate one.

pack_path is an external file — never confined to the project, the same way import_media's source is not — because a pack typically lives in a separate branding repo. Every declared variant is resolved and hashed, not only the one variant activates, so pack_activate can switch between them later with no file re-read; nothing after this call ever depends on pack_path staying reachable.

For every font role, fonts.probe asks whether the declared family actually draws on this machine — a family that does not refuses the whole call unless allow_fallback (then its declared CSS fallback is used and recorded, never silent); one that draws but is vendored nowhere proofcut knows about is recorded font_provenance: "unvendored" rather than refused, since the render here is genuinely correct today. install_fonts vendors the pack's own fonts/ directory if it ships one — off by default, since it writes into $HOME.

Writes nothing to caption styling or to any card already on disk; a card picks up the new style only when card_new/card_reauthor next draws it, and captions only via pack_apply_captions. plan resolves and probes without writing.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
variantNoWhich resolved variant to activate. Every declared variant is snapshotted regardless, so `pack_activate` can switch later with no file re-read.default
pack_pathYesThe pack file to load. An external file, never confined to the project — a pack usually lives in a separate branding repo — and nothing after this call depends on it staying reachable.
install_fontsNoVendor the pack's own `fonts/` directory, if it ships one. Off by default, since it writes into `$HOME`.
allow_fallbackNoAccept a declared CSS fallback for a font family that does not actually draw on this machine, recording which was used. Without it, a family that does not draw refuses the whole call.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.9/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Despite the annotations already declaring readOnlyHint=false, idempotentHint=true, and destructiveHint=true, the description adds substantial behavioral detail: it resolves and hashes every variant (not just the activated one), describes font probing with fallback and 'unvendored' provenance, explains that install_fonts writes to $HOME, and clarifies that it writes nothing to existing cards or caption styling. It also mentions the plan mode as non-writing. This goes far beyond the annotations without contradicting them.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is comprehensive yet efficiently structured. It starts with the core purpose, then explains the external file nature, variant snapshotting, font probing behavior, install_fonts caveat, writing limitations, and plan mode—all in a logical flow. Every sentence earns its place; there is no fluff or redundancy. The use of bold for key points (e.g., 'Every declared variant is resolved and hashed') aids scanning.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a tool with 6 parameters, complex side effects, and a destructiveHint=true annotation, the description covers all critical aspects: what it does, what it does not write to, font handling nuances, plan mode, and how it relates to pack_activate and pack_apply_captions. It also addresses error conditions (refusal for non-drawing fonts) and environmental context (path binding). An agent has everything needed to invoke it correctly and safely.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so each parameter already has a thorough description. The tool description reinforces and adds cross-parameter context, such as the interaction between allow_fallback and font probing, and the relationship between variant and pack_activate. While it does not add new per-parameter syntax, it enriches the meaning of the parameters as a whole, making it more than a simple restatement.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific, action-packed sentence: 'Load a channel preset pack, resolve and snapshot every variant, activate one.' This clearly names the resource (pack), the core actions (load, resolve, snapshot, activate), and distinguishes it from siblings like pack_activate (switching later) and pack_apply_captions (captions only). The purpose is unmistakable and differentiated.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explicitly states when to use this tool versus alternatives: it notes that pack_activate can switch variants later, that captions are applied via pack_apply_captions, and that cards only pick up the style on next card_new/card_reauthor. It also mentions plan as a dry-run alternative. These clear usage boundaries and conditional guidance make it easy for an agent to select the right tool.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

pack_apply_captionsA
DestructiveIdempotent

Apply the active pack variant's caption preset, through caption_style.

Concrete resolved fields, never a live pointer: this reads the preset's already-resolved dict off the snapshot and hands it to the ordinary caption_style call, so a later pack swap can never silently overwrite a project's caption look out from under it. Separate from pack_apply on purpose — applying a pack never restyles captions on its own, only this does.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
presetYesWhich caption preset of the active variant to apply, through the ordinary `caption_style` call. This is the only thing that restyles captions from a pack; `pack_apply` never does it on its own.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already indicate destructive and idempotent behavior, and the description adds meaningful behavioral context: it reads already-resolved fields from a snapshot rather than a live pointer, so a later pack swap cannot silently overwrite the project's caption look. This is the kind of implementation-level guarantee that an agent cannot infer from the schema alone.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact and front-loaded: the first sentence states the action, and the second paragraph earns its place by clarifying the snapshot behavior and the relationship to pack_apply. Every sentence adds distinct value.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the rich input schema, output schema, and annotations, the description covers the key contextual facts an agent needs: what gets applied, how it is resolved, why it is separate from pack_apply, and what makes it safe against later pack swaps. Nothing necessary for correct invocation is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, and the tool description does not add parameter-specific meaning beyond what the schema already provides. The description mentions 'caption preset' and 'caption_style', but the preset parameter already says the same thing; the baseline of 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description uses a specific verb ('Apply'), names the exact resource ('the active pack variant's caption preset'), and clarifies the mechanism ('through caption_style'). It explicitly separates itself from pack_apply, so an agent can immediately distinguish this tool from its siblings.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives explicit when-not guidance: 'Separate from pack_apply on purpose — applying a pack never restyles captions on its own, only this does.' This directly tells the agent that pack_apply is not the way to restyle captions and that this tool is the intended route.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

pack_showA
Read-onlyIdempotent

What a pack declares — from its file, a project's snapshot, or both.

pack_path alone reads and resolves the file fresh, needing no project (card_templates's own shape). path alone reports what a project actually has applied, from its stored snapshot — never the file again. Both together compares "what the file says now" against "what the project is still running."

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoA project directory, or nothing. Omitting it means *no project* here — never the bound one — so `pack_path` alone reads the file fresh; given, it reports what that project has applied.
variantNoReport one variant rather than all of them.
pack_pathNoRead and resolve this pack file fresh, needing no project. With `path` as well, it compares what the file says now against what the project is still running.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true, idempotentHint=true, and destructiveHint=false, so the safety profile is covered. The description adds behavioral context beyond annotations: it explains that path alone reads from the stored snapshot and never the file again, and that pack_path alone reads and resolves the file fresh. This clarifies the data source behavior, which is valuable. It doesn't describe output format, but an output schema exists, so that's not required.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact and front-loaded: the first sentence states the core purpose, and the following sentences explain the three modes without redundancy. Every sentence earns its place, and the structure makes the mode distinction immediately clear.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a read-only inspection tool with three optional parameters, an output schema, and full schema description coverage, the description is complete. It explains all three usage modes, the data sources involved, and the comparison semantics. Nothing an agent needs to select and invoke the tool correctly is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the schema already documents all three parameters. The description adds meaning by explaining the interaction between path and pack_path: how they combine to compare file state vs. project state, and that omitting path means no project. This goes beyond the individual parameter descriptions and clarifies the semantic relationship between parameters.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool's purpose: reporting what a pack declares from its file, a project's snapshot, or both. It distinguishes three modes (pack_path alone, path alone, both together) with specific verbs and resources. This differentiates it from siblings like pack_apply, pack_activate, and pack_status.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explicitly explains when to use each mode: pack_path alone for reading a file fresh without a project, path alone for reporting what a project has applied, and both together for comparing file state vs. project state. It also clarifies that omitting path means no project, never the bound one, which prevents a common misuse.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

pack_statusA
Read-onlyIdempotent

Active pack variant, and which cards/captions have drifted from it.

A card is stale when its own recorded pack_hash no longer matches the active variant's current hash — not wrong, since card_new only pre-merges a pack's style and a per-call slot still wins, but worth a card_reauthor to catch up. caption_preset_stale is the same question for whatever pack_apply_captions last wrote.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.1/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint, idempotentHint, and non-destructive behavior. The description adds valuable interpretation beyond those flags: 'stale' does not mean wrong, a per-call slot still wins, and caption_preset_stale tracks the last pack_apply_captions write. This gives the agent accurate expectations about what the status values mean and what action they imply.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is three sentences with the core statement front-loaded and two dense but purposeful sentences explaining the stale semantics. Nothing is redundant, and the technical nuance earns its place.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a read-only status tool with a full output schema and safety annotations, the description is complete: it defines the two drift statuses, explains why stale is not wrong, and points to the relevant follow-up tool. The only implicit notion, 'active pack variant,' is a consistent domain term supported by sibling tools like pack_activate.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The only parameter, path, is fully documented in the input schema with 100% coverage, including its optional behavior when bound to a project. The description contains no parameter-level detail, which is acceptable because the schema already carries that burden.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description names the resource ('active pack variant') and the specific output (which cards/captions have drifted), so an agent can tell what the tool reports. It lacks an explicit verb, but the status framing and concrete drift/stale terminology make the purpose clear and distinguishable from pack_show.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description implies usage context: when a card's recorded pack_hash no longer matches the active variant, a card_reauthor may be worth doing, and caption_preset_stale refers to what pack_apply_captions last wrote. However, it never explicitly states when to call pack_status versus a sibling like pack_show or pack_apply, so the guidance is implied rather than explicit.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

pingA
Read-onlyIdempotent

Check that the proofcut MCP server is alive, and report its version.

project is the project every tool addresses when path is omitted, and bound_by says how it was chosen: -C at startup, or cwd because the server was started inside a project. Both are null when it is unbound.

ParametersJSON Schema
NameRequiredDescriptionDefault

No parameters

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.5/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint, idempotentHint, and destructiveHint=false, so the safety profile is covered. The description adds meaningful context beyond annotations by explaining the project and bound_by fields, which inform the agent about the server's configuration. It does not contradict any annotation and enriches the agent's understanding of the environment.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is split into two concise sentences. The first sentence states the core purpose, and the second adds necessary context about project binding. There is no fluff; every clause earns its place. It is front-loaded with the primary action, making it easy for an agent to scan quickly.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a simple health-check tool with no parameters, an output schema, and annotations covering safety, the description is complete. It explains the server's liveness check, version reporting, and the meaning of project/bound_by, which is all an agent needs to correctly invoke and interpret the tool. Nothing is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

There are zero parameters, so the input schema is trivially fully covered. The description doesn't need to explain parameters, and the baseline for 0 params is 4. It correctly notes that project and bound_by are both null when unbound, which clarifies the server state without being parameter-related.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific verb ('Check') and resource ('proofcut MCP server'), and clearly distinguishes this health-check tool from all sibling tools, none of which perform a liveness check. It also adds the useful detail that it reports the server version, making the purpose unambiguous.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

While it doesn't explicitly say 'use when you need to verify server connectivity', the purpose is self-evident and no sibling tool overlaps. It does provide valuable context about the project binding and how it was chosen, which helps an agent understand the server's current state and when this info is relevant. No exclusions or alternatives are needed.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

propertiesA
Read-onlyIdempotent

Project/clip/cue detail for a properties inspector, composed only.

No arguments: status, canvas and caption_style's own reports. clip_id: adds that clip's assets entry, its reframe window table, and its whole cue_ls. Both clip_id and word_index: adds cue (the matching entry from that cue_ls, or null if the word carries none) and, only when cue is null, context — the word plus three either side, the same echo every word-indexed tool gives (a cue's own entry already carries this, so it is not duplicated). word_index needs clip_id.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
clip_idNoAdd this clip's assets entry, framing windows and cue table to the report.
word_indexNoWith `clip_id`, add the cue at that word — or, when there is none, the word plus three either side. It needs `clip_id`.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A3.7/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already establish readOnlyHint, idempotentHint, and non-destructive behavior, so the bar is lower. The description adds genuinely useful behavioral context beyond annotations: conditional composition of reports, the null-cue fallback to a context window, and the dedup guarantee that a cue's own entry already carries context so it is not repeated.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness3/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact and parameter detail is logically organized, but the opening 'composed only' phrasing and shorthand like 'the same echo every word-indexed tool gives' are jargon-heavy and hinder immediate comprehension. It is appropriately sized but not as clear as it could be given the density.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a read-only composition tool with an output schema present, the description covers the key agent-facing concerns: the no-argument report set, each parameter's incremental contribution, the word_index-to-clip_id dependency, null-cue behavior, and deduplication. The main gap is the absence of explicit sibling routing, but the conditional behavior an agent needs to invoke it correctly is well specified.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, setting a baseline of 3, but the description materially enriches all three parameters: it spells out exactly what clip_id contributes (assets entry, reframe window table, cue_ls) and what word_index yields (the matching cue or the word±3 context fallback). The path parameter's semantics are already well-covered by the schema, so the description's added value is distributed where it matters.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description identifies the resource ('Project/clip/cue detail for a properties inspector') and the composition behavior, which distinguishes it from dedicated sibling tools like cue_ls or assets. However, the phrase 'composed only' is cryptic and does not crisply convey that this aggregates existing reports rather than computing new data, leaving some ambiguity on first read.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description clearly explains the within-tool parameter combinations (no args vs clip_id vs clip_id+word_index) and the dependency that word_index needs clip_id. It does not, however, explicitly guide when to choose this tool over siblings like describe_ls, cue_ls, or assets, leaving alternative routing to inference.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

proxy_transcodeA
Idempotent

Make footage the preview cannot decode playable in the window.

The other half of what the viewer already reports: an unplayable clip names its reason (hev1, 10-bit, an unopenable container, an undecodable audio track) and shows black. This transcodes a downscaled h264/aac/mp4 stand-in into the project's cache so it plays. One ffmpeg pass; a long clip is minutes.

The result is a preview artefact and cannot reach a render: nothing records it in the manifest, so media_path() — what export, verify and check_frames all resolve through — has no way to see it. That containment is structural, not a convention to be careful about.

Skips the work when a current proxy already exists (keyed by the source's size and mtime), so calling it on every unplayable clip in a project is cheap after the first pass. Refuses a clip that already plays, and refuses a file with no decodable streams — that is a broken file, not a codec problem, and it is the one refusal a transcode cannot close. force rebuilds a current proxy but does not override either refusal.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
forceNoRebuild a proxy that is already current. It touches nothing authored: a proxy is a preview artefact the manifest never records, so no render can reach one. It overrides neither refusal.
clip_idYesThe clip the preview cannot decode. A clip that already plays is refused, and so is one with no decodable streams — that is a broken file, not a codec problem.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.5/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The description is unusually transparent: it discloses the side effect (writing a cache proxy), the performance profile (one ffmpeg pass; long clips take minutes), the structural containment from renders, the idempotent caching behavior, both refusal conditions, and what `force` does and does not override. These go well beyond the annotations, which already mark the tool as non-read-only, non-destructive, and idempotent. No contradiction exists between the description and annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is front-loaded with a one-sentence purpose and then expands into distinct, clearly separated concerns: mechanics, render containment, idempotency, and refusals. Every paragraph earns its place given the tool's nuanced non-obvious behavior; there is no filler or redundant repetition.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a tool with this complexity and with rich annotations and schema, the description covers everything needed to invoke it correctly: what it produces, where it writes, how long it takes, when it skips, when it refuses, what `force` does, and why the proxy cannot leak into renders. An output schema exists, so not describing return values is acceptable.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Input schema coverage is 100%, and the schema already explains `path` binding rules, `force` behavior, and `clip_id` refusals in detail. The free-text description adds useful operational context, such as the ffmpeg pass and proxy-cache behavior, but it does not add new per-parameter semantics beyond what the schema already provides. Baseline 3 is appropriate for full schema coverage.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description names the precise verb ('transcodes'), the resource (a downscaled h264/aac/mp4 stand-in in the project cache), and the triggering condition (footage the preview cannot decode). It clearly separates this preview-only proxy behavior from render/export behavior, so it distinguishes itself from siblings.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description clearly says when to call the tool — on unplayable clips — and gives strong exclusions: refuse clips that already play, refuse files with no decodable streams, and skip work when a current proxy exists. It also clarifies that the result cannot reach a render, which sets expectations versus export/verify/check_frames. It does not name a specific sibling alternative, but no obvious sibling competes for this action.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

reelA
Destructive

Derive a new project at dest holding [start, end) of this timeline.

start/end are render seconds naming the span to keep — the opposite direction from every other tool; the head and tail are cut through cut_by_time. Reach for this before setting a vertical canvas on a film: the canvas is project state, so pass the reel's shape here and it lands on the copy only.

Media is linked, not copied. Descriptions and reframes carry over. Cues carry over only where the reel keeps their word — read cues_dropped head-first, since one pruned just outside the kept span opens the reel on no picture. Survivors are pinned to the film's in-points (cues_pinned, or pins_error). Cards are re-authored at the new canvas (cards_unrecorded names any that cannot be); over_platform_cap says if it still runs long for a vertical feed.

Nothing after the film is inherited: tail_dropped and music_dropped name what the film had. An edge on a suspect-duration word — likely a hidden retake — refuses unless confirm_suspect; read suspect_edges. plan=True creates nothing.

ParametersJSON Schema
NameRequiredDescriptionDefault
endYesWhere it ends, in those same render seconds. `start`/`end` name the span to **keep**, the opposite direction from every other tool here.
destYesWhere the derived project is created. It is a project selector too, not a file, so a bound server confines it to the same tree as `path` rather than letting a reel be written anywhere on disk.
nameNoA name for the derived project. Unset, it is derived from `dest`.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
startYesWhere the reel begins, in the seconds **an export plays at** — the same numbers `cut_by_time` takes, read off a watch.
canvasNoThe shape to set on the derived project only, e.g. `1080x1920`. Setting it on the film instead is what deriving exists to avoid — a canvas is project state and would stay.
confirm_suspectNoGo ahead even though a boundary word claims a suspect duration. Read the echoed words first — a suspect duration usually means whisper hid a retake inside that word, so the edge is not where it reads.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations only say destructiveHint=true and readOnlyHint=false; the description carries the full side-effect burden and exceeds it: media is linked not copied, carry-over rules for cues/cards, dropped items (`tail_dropped`, `music_dropped`, `cards_unrecorded`), refusal on suspect-duration edges unless `confirm_suspect`, and `plan=True` dry-run. This is exactly the disclosure a destructive derivation tool needs, with no contradiction to annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Effectively front-loaded with the core operation in the first sentence, then organized into focused paragraphs: parameter semantics, carry-over behavior, non-inherited tail items, edge-case refusal, and dry-run. Despite length, the tool is genuinely complex (8 params, destructive, many carry-over rules), and every sentence carries load-bearing information rather than padding.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a destructive 8-parameter tool with an output schema, the description is complete: it covers what the operation does, when to reach for it, parameter rationale, what carries over, what is dropped, failure/safety behaviors, and the plan dry-run. With an output schema present, it need not explain return values, and it still references all relevant output fields (e.g., `cues_dropped`, `suspect_edges`, `over_platform_cap`) as behavioral context.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100% with rich per-parameter text, so the baseline is 3. The description adds meaning beyond that baseline: it explains the `start`/`end` 'span to keep' semantics in relation to `cut_by_time`, ties `confirm_suspect` to the suspect-edge refusal flow, and frames `canvas` as the reason to derive rather than set state on the film. Some repetition of schema text exists, but genuine workflow-level meaning is added.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

Opens with a specific verb+resource: 'Derive a new project at `dest` holding `[start, end)` of this timeline.' It distinguishes itself from siblings by contrasting its parameter direction with 'every other tool' and by relating its cut mechanics to `cut_by_time`, and from `canvas` by explaining the copy-only landing. An agent can tell what this does and what it is not.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Gives explicit when-to-use guidance: 'Reach for this before setting a vertical `canvas` on a film' with the rationale that canvas is project state. It also names `cut_by_time` as the mechanism that cuts head/tail, which orients the agent toward the sibling. It stops short of an explicit when-not-to-use/alternative selection rule (e.g., 'use cut_by_time instead when cutting in place'), hence not a 5.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

reframeA
DestructiveIdempotent

Read or set which part of each clip survives into the frame.

What makes a swapped canvas fill the frame instead of pillarboxing it. The default is a centre crop, which is wrong whenever the subject is not centred. Call with no clip_id to read the crops in force for every clip; clips[].windows is each clip's whole series.

A rect is a floor rather than a frame: grown to the canvas's shape, never shrunk into it, stored as asked and refit whenever the canvas moves; the reply gives both asked and the crop it became. src_start makes it a per-shot window, addressed on the source's own clock, so every placement of the clip picks it up. pane makes that window a stacked split for a shot one crop cannot hold; interp slides into it rather than stepping, and ease names that slide's curve; event addresses the window by a named instant instead of seconds; fill="blur" draws it whole over a blurred copy of itself instead of cropping, for a shot every crop loses something from.

reset drops overrides (one clip, one window, or all); plan resolves without writing. Nothing here analyses the picture — reframe_detect proposes crops and writes through this tool. Judge a window on reframe_sheet, never on a watch: a wrong one reads as framing in motion.

ParametersJSON Schema
NameRequiredDescriptionDefault
easeNoThe curve of this window's slide: linear, ease (slow at both ends), ease-in or ease-out. Implies `interp`. The slide runs across the whole previous window, so to move between two moments put a window holding the old rect at the first.
fillNo`blur` draws this window **blur-filled**: the whole source contained in the frame, over a blurred, darkened copy of the same moment covering the canvas. For a shot every crop loses something from and no split divides. Takes no `rect`, `pane` or `interp`; set `src_start` for one shot.
paneNoA second rect making this window a **stacked split**: `rect` on top, `pane` below, each about twice the width one 9:16 window gets. For the shot one window cannot frame. Both are grown to the full source height — nothing masks a pane, so a shorter crop scales into the other half at exit 0.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
rectNo`X,Y,W,H` in that clip's **own source pixels** — the region kept. An override is a floor rather than a frame: a rect that is not the canvas's shape is grown to it, so nothing named is pushed off screen, and the reply gives both `asked` and the `crop` it became.
eventNoStart this window at a named instant from `events` (`name` or `name#k`) instead of `src_start`. The seconds it resolves to are stored; the listing says `event_moved` if the event later moves.
resetNoWith `clip_id`, drop that clip's overrides; with `src_start` as well, only the window there. Alone, drop every override.
interpNoSlide into this window from whatever governed before it instead of stepping to it. It needs `src_start` past 0 — there is nothing before the head of the source to slide from — and cannot be combined with `pane`.
clip_idNoThe clip to read or frame. Omit it to read the crops in force for every clip, including how much of each is kept.
src_startNoFrame a **shot** rather than a clip: seconds into that clip's own source, the rect holding from there until the next window. Because the address is the source's own clock, a clip used seven times picks up the right window at each placement. Omitted, it is the window from the head of the file.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.6/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already mark the tool as non-read-only and destructive, and the description adds meaningful behavioral detail: reset drops overrides, plan writes nothing, rect is stored as asked and refit when the canvas moves, and the reply reports both asked and the crop it became. It also warns that a wrong window 'reads as framing in motion' on a watch, which is useful behavior for an agent to know.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long and dense, but the tool has 11 parameters and complex semantics, so most sentences earn their place. It is front-loaded with the core purpose and then groups related concepts, though headings or shorter sentences could make it easier to scan.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the high schema coverage and the presence of an output schema, the description is complete enough: it covers the read/write duality, all window modes, reset and plan behavior, the clips[].windows output shape, and the division of labor with reframe_detect and reframe_sheet. Nothing essential for invoking the tool correctly appears missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The schema has 100% coverage with detailed per-parameter descriptions, so the baseline is already high. The description adds some conceptual glue by framing rect as a 'floor' and linking shot windows, panes, interpolation, and fill modes, but most of its parameter content is a compressed restatement of what the schema already explains. It does not materially out-document the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb-resource pairing: 'Read or set which part of each clip survives into the frame.' It immediately distinguishes the tool from siblings by saying reframe_detect proposes crops and reframe_sheet is for judging windows, so an agent can tell this tool apart from related ones.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives explicit call patterns: use no clip_id to read all crops, use plan to resolve without writing, and use reset to drop overrides. It also routes analysis to reframe_detect, judging to reframe_sheet, and warns that a watch is the wrong place to judge a window. This is clear when-to-use and when-not-to-use guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

reframe_coverageA
Read-onlyIdempotent

Which placed seconds are framed by a window chosen for an earlier shot.

The question reframe_detect cannot answer: that one is about a proposal, this is about the project on disk. A refused proposal writes nothing, so a stretch can sit under a rect chosen for a shot that ended long before — 13.6s of one clip across four camera setups on the film, with the manifest, status and reframe_sheet all clean.

Every placement is walked against its source's scene cuts. A cut with no window boundary within a frame of it opens a stale stretch. Read stale_seconds — an override held across a cut, which looks deliberate — not default_seconds (the centre crop, only the default doing what it always did). Each stretch carries timeline_start; the fix is reframe_sheet to look, then reframe_detect on the clip.

steps is the mirror, and the one a viewer notices: a window boundary with no cut, where the frame slides sideways mid-take and reads as an edit that is not there. Each carries shift and nearest_cut.

Needs no face detector, reads and never writes — but it decodes placed footage, so it is seconds, not free.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
clip_idNoWalk one clip's placements. Omit it for the whole project.
thresholdNoHow strong a scene change has to be to **demand** a window. Boundaries are scored against every detected cut rather than only these, since a cut too weak to demand a window still explains one.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.1/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true and destructiveHint=false; the description reinforces 'reads and never writes' and adds valuable context: 'Needs no face detector, reads and never writes — but it decodes placed footage, so it is seconds, not free' (discloses compute cost). It also discloses output fields ('Each stretch carries `timeline_start`', 'Each carries `shift` and `nearest_cut`'), which goes beyond annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness2/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is verbose and narrative, including an extended anecdote ('13.6s of one clip across four camera setups...') and metaphor ('the mirror, and the one a viewer notices'). While rich, it is not front-loaded and each sentence does not earn its place; an agent must parse a lot of prose to extract the core operational details. The structure could be tightened significantly without losing meaning.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The description covers the tool's purpose, its distinction from `reframe_detect`, the concepts of 'stale stretch' and 'steps', output fields, cost, and the follow-up workflow (`reframe_sheet` then `reframe_detect`). Given the tool's complexity and the presence of an output schema, this is quite complete. It could be more systematic, but it does not leave major gaps.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The input schema has 100% description coverage for all three parameters (path, clip_id, threshold). The description does not add any extra parameter-specific meaning beyond what the schema already provides. Since the schema fully documents the parameters, the baseline of 3 is appropriate; there is no additional value from the description.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The opening sentence states exactly what the tool does: 'Which placed seconds are framed by a window chosen for an earlier shot.' It uses a specific verb ('framed') and names the resource ('placed seconds'), and it immediately differentiates from sibling `reframe_detect` by contrasting proposal vs. on-disk state. The purpose is unambiguous and distinct.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explicitly explains when NOT to use it: 'The question `reframe_detect` cannot answer: that one is about a proposal, this is about the project on disk.' It also prescribes the workflow: 'the fix is `reframe_sheet` to look, then `reframe_detect` on the clip.' This gives clear usage guidance and directs the agent to the right alternative.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

reframe_detectA
Idempotent

Propose a framing window per camera shot, from where the faces are.

Every placement is split at its camera cuts, each window sampled at a few moments and centred on the faces found. Against fifteen hand-framed, approved windows it beats the centre crop on every measure (0.755 mean overlap against 0.568).

It proposes; it does not frame. apply is off by default: the pass is still about a quarter of a window's width out on average, and a wrong window reads as framing in motion. Look at reframe_sheet before applying. Applying writes through reframe and never over an existing override.

A window with no face is refused, never guessed at — expect about one in seven — and nothing is written for it, so read falls_back_to: at a clip's head that is the centre crop, anywhere else the previous shot's framing. Nothing here chooses the subject either.

A window one crop cannot hold comes back as a stacked split (rect and pane). Read subjects (per frame), not faces, which sums detections across samples and calls one face three. Needs PROOFCUT_FACE.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
applyNoWrite the proposals through `reframe`. Off by default — the opposite of `cut --plan` — because the pass runs 24% of a window's width out on average. Call `reframe_sheet` and look first. It never writes over a window that is already an override.
splitNoOffer a stacked split where every sampled frame holds two or three faces one window cannot hold. On by default; `false` turns the offer off.
framesNoHow many moments to sample inside each window before centring it on the faces found there.
clip_idNoPropose windows for one clip. Omit it for every placed clip.
thresholdNoHow strong a scene change has to be to count as a camera cut, 0–1. 0.15 is pinned by judging detections on real footage: every candidate from 0.141 to 0.244 was a real cut, and the first non-cut is 0.137.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.4/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already mark this as non-read-only, idempotent, and non-destructive, and the description adds substantial behavioral detail beyond those: apply is off by default, refused windows produce no output, falls_back_to behavior at clip heads vs elsewhere, stacked splits, and the PROOFCUT_FACE dependency. It also clarifies the non-destructive 'never over an existing override' behavior, which is consistent with destructiveHint=false.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but front-loaded with the core purpose and then organized into behavioral warnings, edge cases, and dependencies. Some benchmark statistics and repeated accuracy caveats are arguably extra, but they earn their place by justifying why apply is off by default and why review is needed.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a complex proposal tool with six optional parameters, an output schema, and several edge cases, this description covers the essential invocation context: what gets proposed, what is refused, what fallback behavior to expect, how splits work, and the required environment variable. The presence of an output schema means return-value documentation is not needed in the description.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the schema already documents all six parameters thoroughly. The description adds useful behavioral context for apply and split, and warns about reading subjects rather than faces, but it does not need to compensate for missing parameter docs. Baseline 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The first sentence states a specific action and resource: 'Propose a framing window per camera shot, from where the faces are.' It further distinguishes itself from the apply step with the explicit contrast 'It proposes; it does not frame,' making its role among siblings like reframe and reframe_sheet clear.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description makes the workflow obvious: proposals are not applied by default, one should 'Look at reframe_sheet before applying,' and applying writes through reframe. It does not explicitly enumerate all sibling alternatives or say 'use reframe_detect when...', but the propose-vs-apply framing and the reference to reframe_sheet give strong contextual guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

reframe_sheetA
DestructiveIdempotent

Draw every placement's framing window on its own source frames.

A framing decision is unreviewable without this. The hand-framed teaser had 2 of its 15 windows wrong and neither was visible in motion — a badly-placed window reads as framing. Drawn on the whole source frame, what the window leaves out sits right beside it.

Every placement the render shows is walked window by window, the window in force drawn in red and labelled with its rect. A row is a window shown, not a placement: each placement is split at the boundaries it crosses, so a window covering a small slice of a long placement still gets a row. window on a row is the source address reframe --src-start takes; windows is how many the whole placement crosses. Stills come back under skipped — a card is re-authored, never cropped.

A tile is evidence about an instant, not an approval of the span. A static rect over a moving subject has a best moment and a sample can land on it; extremes draws where the subject is leftmost, median and rightmost instead, worst first, with worst_offset on the row to sort by.

A page of rows comes back as an image, six windows by default, at a width vision reads verbatim; row keeps its project-wide number on every page. per_page: null is the whole project as a PNG path, for a person.

ParametersJSON Schema
NameRequiredDescriptionDefault
outNoWrite the image to this path as well, replacing whatever file is there. Unset, it goes to the project's own sheet cache and only the bytes come back.
pageNoWhich page of rows to draw, from 1. Unset, the first.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
momentsNoFractions of each window to draw tiles at, e.g. `[0.1, 0.5, 0.9]`. A tile is evidence about one instant while a rect is a claim about a stretch, so where the subject moves these decide what the sheet can see. Refused alongside `extremes`.
extremesNoDraw the subject's own leftmost and rightmost moments, worst first, instead of fixed fractions — the rect does not move inside a stretch, so that is where a static window is worst. Off by default: it costs the face detector and about half a second a probe. Read `worst_offset` beside `multi_face`, never after it.
per_pageNoRows per page. `null` draws the whole project in one montage, which returns a path rather than readable bytes — for a person to open, not for an agent to read.

TDQS

A3.6/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The description adds significant behavioral detail beyond the annotations: the `out` parameter replaces any existing file (destructive), `extremes` costs face-detection time (~half a second a probe), and `per_page: null` returns a path for a person rather than readable bytes. It also clarifies row semantics and skipped stills. This matches the idempotent/destructive annotations and provides operational insights without contradiction.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness2/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is much longer than necessary and uses metaphorical language ('A tile is evidence about an instant, not an approval of the span') that adds literary style but not operational clarity. It is front-loaded with the purpose, but subsequent paragraphs contain rationale and tangential details (e.g., 'A badly-placed window reads as framing.') that do not directly help an agent invoke the tool. It could be condensed and structured more clearly.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a tool with 6 parameters and no output schema, the description covers the key behavioral aspects: how windows are drawn, row splitting across placement boundaries, skipped stills, extremes selection, pagination, and the difference between returning bytes vs. a path. It is thorough enough for an AI agent to understand the tool's behavior, though it omits edge cases like empty projects or error conditions.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

With 100% schema description coverage, the baseline is 3, but the tool description enriches several parameters: `moments` are explained as 'evidence about one instant,' `extremes` draws leftmost/median/rightmost worst-first with `worst_offset`, and `per_page: null` is explicitly for human consumption. These additions go beyond the schema's own descriptions and aid correct parameter selection.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Draw every placement's framing window on its own source frames.' This clearly distinguishes the tool from likely siblings like `reframe` or `reframe_detect`, which probably perform the actual reframe, though it does not explicitly name alternatives. The heavy use of domain jargon ('placement', 'framing window') may require background knowledge but does not obscure the core purpose.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives a strong contextual reason to use the tool ('A framing decision is unreviewable without this') and explains the informational value of the drawn windows. However, it does not explicitly contrast the tool with sibling visualization tools (e.g., `footage_sheet`, `contact_sheet`) or provide conditions for when not to use it. The guidance is contextual but lacks explicit alternatives or exclusions.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

resolve_phraseA
Read-onlyIdempotent

Resolve a phrase to a word range against clip_id's transcript.

What phrase= on cue_add/cue_rm/unspoken_add/unspoken_rm/vo_extend/music/ locate calls internally, exposed on its own so a resolution — including its full ambiguity list — can be inspected without attempting a write. Companion to get_transcript with search=, which lists every match with no cursor/occurrence/fuzzy; this picks exactly one, or explains why it can't.

after skips matches at or before that word index (forward cursor, -1 means from the start). More than one exact match with no occurrence given fails with every candidate's word range and text — pass occurrence (1-based) to pick one, or narrow the phrase. Zero exact matches falls back to a fuzzy match (fuzzy=False to refuse instead) — ratio is set only on a fuzzy hit, never disguised as exact. Read-only.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
afterNoA forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start.
fuzzyNoFall back to a fuzzy match when nothing matches exactly. A fuzzy hit sets `ratio` and is never reported as an exact one; `false` refuses instead.
phraseYesThe words to find, as they were spoken.
clip_idYesThe transcript to resolve against.
occurrenceNoDisambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.6/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the readOnlyHint/idempotentHint/destructiveHint annotations, the description discloses important edge-case behavior: ambiguous matches fail and list candidates, fuzzy fallback sets ratio and is never disguised as exact, and the after cursor skips matches at or before a word index. The explicit 'Read-only' statement is consistent with the annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is front-loaded with the core purpose and is dense with useful information, but it runs to four paragraphs and slightly repeats details already present in the input schema. Still, each paragraph contributes real behavioral or usage context, so it remains tight for the tool's complexity.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a 6-parameter resolver with ambiguity handling, fuzzy fallback, cursor semantics, and a read-only inspection role, the description covers all critical behavior an agent needs to invoke it correctly. An output schema exists, so not detailing return values is acceptable.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, and the parameter descriptions already explain after, occurrence, fuzzy, clip_id, phrase, and path in detail. The tool description mostly restates key semantics rather than adding new parameter-level meaning, so the baseline of 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The opening sentence states a specific verb, resource, and result: 'Resolve a phrase to a word range against clip_id's transcript.' It further distinguishes itself from get_transcript and explains its role as the internal resolver behind phrase= on several mutation tools, so an agent can tell exactly what it does.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explicitly contrasts this tool with get_transcript's search= mode: that tool lists every match, while this one picks exactly one or explains why it cannot. It also says it is exposed for inspecting a resolution without attempting a write, giving a clear when-to-use signal versus the mutation tools that call phrase= internally.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

restoreA
DestructiveIdempotent

Un-cut whichever part of these inclusive word ranges is not currently in the timeline.

Same range shape as cut_by_transcript's cut=/keep=. Each range resolves to source time exactly like a cut does; only the part Edit.gaps says is actually absent comes back — material still present in the request is left alone, a request spanning two separate cuts restores both as separate pieces, a request only touching part of one cut restores only that part. Restoring only ever brings back material the source recording already has (bounded by the clip's own registered duration), so the timeline stays a subset of the source throughout — this is not vo_extend (PLAN.md parks that separately), which would add material the source never had.

pad matches cut_by_transcript's own pad: pass the same value used on the original cut to bring back its padding sliver, not just the words.

Unlike a cut, there is no suspect-duration refusal — a boundary that looks like it swallowed a retake is exactly the kind of thing restore exists to bring back, not a mistake to guard against.

Refused if clip_id has no surviving segment anywhere in the edit (nothing left of it to splice the range next to — undo or re-seed instead), or if its segments are not contiguous in the edit (an interleaved multi-source timeline, which restore does not support yet).

plan=True resolves and reports without writing, identically to cut_by_transcript.

ParametersJSON Schema
NameRequiredDescriptionDefault
padNoPass the same `pad` the original cut used to bring its padding sliver back, not only the words.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
rangesYesInclusive word ranges, the shape `cut_by_transcript` takes. Only the part the edit says is actually absent comes back; material still present is left alone.
clip_idYesThe clip whose cut material to bring back.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.6/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare destructiveHint=true and readOnlyHint=false, but the description adds substantial behavioral detail: it explains partial restoration, multiple-cut handling, padding sliver recovery, the subset-of-source constraint, and the refusal conditions. It explicitly contrasts with vo_extend and notes the plan mode writes nothing. No contradiction with annotations; idempotentHint=true aligns with 'material still present is left alone.'

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but well-structured and front-loaded with the core purpose. It flows logically from the primary function to range behavior, pad handling, differences from cuts, refusal conditions, and plan mode. Every sentence adds meaningful context; it is not bloated with fluff, though it could be tightened slightly for brevity.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a tool of this complexity, the description covers all necessary aspects: what it does, how ranges behave, pad semantics, differences from cut, refusal conditions, and plan mode. It references the output schema exists, and the description does not need to explain return values since an output schema is present. It is complete for an agent to call correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The input schema already provides 100% coverage with detailed descriptions for every parameter, including pad, ranges, and clip_id. The tool description reiterates some of these (e.g., 'pad matches cut_by_transcript's own pad') but adds little beyond what the schema states. It offers helpful context on range resolution, but since the schema already does the heavy lifting, a baseline of 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a clear verb-resource pair: 'Un-cut whichever part of these inclusive word ranges is not currently in the timeline.' It explicitly states the tool's purpose (restoring removed material) and distinguishes it from siblings like cut_by_transcript and vo_extend, leaving no ambiguity about what it does.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives explicit when-to-use and when-not-to-use guidance. It names vo_extend as the alternative for adding material the source never had, notes the absence of suspect-duration refusal that a cut would have, and lists two refusal conditions (no surviving segment or non-contiguous segments) with the fallback actions (undo or re-seed). It also recommends plan=True for preview.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

retime_addA
Idempotent

Play a span of the film faster or slower: "from event sent to event words in 1.0 s".

The span starts at a word, phrase or event of clip_id and ends at one; it is resolved through the timeline on every build, never stored as seconds. Everything outside every stretch plays at 1x, with the speed eased in and out over half a second either side. The film's own audio is muted wherever it plays off speed; music, sounds, overlays and captions keep 1x and land where the retime puts their moment. Stretches may not overlap.

The reply gives the span in Edit seconds and render seconds, its speed, and the render's new length; plan=true writes nothing. Any retime routes export through the MLT writer. A film-audio hold cannot share a project with a retime yet, and the window previews at 1x.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
afterNoA forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start.
eventNoStart on this event of clip_id: `name`, or `name#k` when the name repeats.
phraseNoStart on this phrase's FIRST word, resolved against clip_id's transcript.
clip_idYesThe clip whose words or events address the span — the transcript the word indices index, or the recording the events belong to.
secondsYesHow long the span plays for in the render. Shorter than the span speeds it up (a 31 s wait in 1.0), longer slows it down.
occurrenceNoDisambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at.
word_indexNoThe word the stretch starts on. One of word_index, phrase or event.
until_eventNoEnd on this event of clip_id.
until_phraseNoEnd as this phrase's LAST word ends.
until_word_indexNoEnd as this word ends. One of until_word_index, until_phrase or until_event.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already mark idempotentHint=true and destructiveHint=false, but the description adds substantial behavioral context: spans are resolved through the timeline on every build (not stored as seconds), speed is eased over half a second, film audio is muted off-speed while other audio stays 1x, stretches cannot overlap, plan=true writes nothing, and export routes through the MLT writer. This far exceeds annotation information and gives the agent a clear model of the tool's effects.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but every sentence earns its place: purpose+example, span resolution, global playback behavior, audio behavior, overlap constraint, reply format, plan behavior, export and compatibility notes. It is front-loaded with the core purpose, followed by progressively more specific details. No filler or repetition of schema content.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a 12-parameter tool with an output schema, this description covers all essential behavioral aspects: span addressing, speed easing, audio handling, constraints (no overlap), dry-run via plan, reply contents, export pipeline, and a critical incompatibility with film-audio holds. An agent has enough context to invoke the tool correctly and interpret its effects, with output schema covering return values.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so baseline is 3. The description adds value by explaining the span concept ('starts at a word, phrase or event of clip_id and ends at one') and referencing how parameters like seconds are used ('from event sent to event words in 1.0 s'). It clarifies the relationship between start/end parameters and the timeline, which is not fully spelled out in individual parameter descriptions.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Play a span of the film faster or slower', and illustrates with a concrete example ('from event sent to event words in 1.0 s'). It clearly distinguishes this from siblings like hold_add by focusing on temporal speed adjustment. The purpose is unmistakable.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description provides clear context for when to use this tool: whenever a span needs non-1x playback. It also gives an implicit alternative constraint by noting 'A film-audio hold cannot share a project with a retime yet', which warns against combining with hold tools. It does not explicitly name sibling tools as alternatives, but the context and constraints are sufficient for an agent to select it.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

retime_lsA
Read-onlyIdempotent

Every retime stretch, in the order added, with where each plays now.

Each carries its position (as retime_rm takes it), its Edit and render spans and its speed, beside the render's length. A retime that cannot resolve — a cut removed an end word — comes back as retime_error beside the stored records.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A3.9/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint, idempotentHint, and destructiveHint, so the description correctly avoids repeating these. It adds behavioral detail beyond the schema by explaining the order (as added) and the error handling for unresolved retimes (returned as retime_error). This is valuable context that helps the agent anticipate output variations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is two concise paragraphs that front-load the core purpose and then add detail about fields and error cases. Every sentence contributes meaningful information, and the structure is clear and efficient, with no fluff or repetition.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool has an output schema, the description correctly avoids repeating return value structures. It does provide essential behavioral context (ordering, error representation) that the schema may not convey. The parameter is fully documented in the schema, and the description covers the key non-obvious aspects of the operation, making it sufficiently complete for an agent to invoke correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The only parameter, path, has 100% schema description coverage, which fully explains its semantics and resolution rules. The tool description does not add any parameter-specific information beyond what the schema provides, so a baseline score of 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the tool lists every retime stretch with its current playback position, order, and associated data. It specifies the resource (retimes) and the action (listing), and implicitly distinguishes it from sibling tools like retime_add and retime_rm by focusing on inspection rather than mutation.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description does not explicitly state when to use this tool versus alternatives. It implies a read-only listing operation but does not mention when to prefer it over retime_add or retime_rm, nor does it provide exclusions. The context of 'list' is inferred from the name and sibling structure, but explicit guidance is missing.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

retime_rmA
Destructive

Take one stretch away, by its position in retime_ls; that span plays at 1x again.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
positionYesThe stretch to remove, by its position in retime_ls; that span plays at 1x again.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A3.8/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare destructiveHint=true and the description aligns by saying something is taken away. It adds a clarifying behavioral consequence — the removed span reverts to 1x, meaning footage isn't deleted, only the speed effect is lifted. It doesn't disclose reversibility or error handling, but with the annotation carrying the destructive-safety profile, a 3 is appropriate.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

A single, tightly written sentence with three distinct clauses: the action ('take away'), the addressing scheme (position in retime_ls), and the consequence (plays at 1x again). Every word earns its place and the action is front-loaded.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a destructive single-item removal with an output schema present and fully documented parameters, the description plus schema covers what to remove, how to reference it, and what the outcome is. The only minor gap — indexing base for 'position' — is a schema-level concern rather than a description omission.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so every parameter (path, plan, position) is already fully documented. The description's 'by its position in retime_ls' adds no meaning beyond the position parameter's own schema description, which repeats the same phrase. Baseline 3 applies because the schema does the heavy lifting.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific action ('Take one stretch away' — removal), the resource (a stretch), and how it is identified (by its position in retime_ls), with the consequence that the span plays at 1x again. This is clear and unambiguous, but it doesn't explicitly distinguish itself from sibling retime_add/retime_ls beyond the verb and the positional reference, so it stops short of full sibling differentiation.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description points the agent to the correct addressing scheme — the position comes from retime_ls — which implies listing first and gives clear operational context for how to invoke the removal. It offers no exclusions or alternative-selection guidance, but the target identification guidance is concrete and directly actionable.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

review_addA
Destructive

Register a rendered file, sheet or A/B member for proofcut review serve.

Never copies source — a render already lives in renders/, a sheet in reframe_sheet's own directory — this just points name at it, so a served round has something to stream and a verdict has something to attach to.

Registering a name that already exists replaces that entry, and the verdict recorded against it stays — so re-pointing a name at a different file leaves yesterday's answer attached to today's bytes. Register the new file under a new name unless replacing it is what you mean.

kind is one of render, sheet, ab, control. A control requires baseline, the name of an already-registered item, and the two files' sha256 must match — a mismatch refuses the call. This is the rule the round that went wrong exists to enforce (HISTORY.md § The bumper the teaser never had): a page once served three cuts, one mislabelled "control" when it was a different, later render. Nothing is labelled a control here unless it is byte-identical to what it claims.

ParametersJSON Schema
NameRequiredDescriptionDefault
kindYesOne of `render`, `sheet`, `ab`, `control`.
nameYesWhat to call this item in the served round. Re-using a name replaces that entry while its verdict stays attached.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
aboutNoOne plain line the served page prints under the name, saying what this item is (how it was made, what differs) — a reviewer judges nothing they cannot tell apart.
sourceYesThe file to point at — never copied. A render already lives in `renders/`, a sheet in the sheet directory.
baselineNoRequired for `kind="control"`: the name of the already-registered item this one claims to be identical to. Both files' sha256 must match or the call is refused — nothing is labelled a control here unless it is byte-identical to what it claims.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the destructiveHint annotation, the description discloses crucial behavioral details: source files are never copied, re-registering an existing name replaces the entry while keeping the old verdict attached, and control items require a matching sha256 or the call is refused. These side effects and safety constraints are exactly what an agent needs before invoking a mutating tool.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is front-loaded with the core purpose and immediately follows with the most important behavioral warnings. The historical anecdote about the control rule is somewhat long, but it reinforces a safety-critical constraint and is not filler. It is structured and readable, though slightly longer than strictly necessary.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The description covers the registration semantics, non-copying behavior, replacement effects, verdict persistence, and the control validation rule. Combined with a fully described input schema and an output schema, nothing essential is missing for an agent to call this tool correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters5/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The description adds substantial meaning beyond the input schema: it explains that source is only pointed to and never copied, that name replacement preserves verdicts, that kind accepts specific values, and that baseline is mandatory for control and must match byte-for-byte. Since schema coverage is already 100%, this extra semantic context meaningfully raises the value.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb-resource pair: 'Register a rendered file, sheet or A/B member for proofcut review serve.' It states exactly what the tool does and for what purpose, and it is clearly distinct from siblings like review_verdict and review_list because it focuses on registration for a served review round.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description clearly conveys when to use the tool: when adding an item to a proofcut review round. It also gives practical usage guidance, such as registering under a new name unless replacement is intended, and explains the control/baseline requirement. It does not explicitly name alternative tools or say when not to use it, but the intended context is clear.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

review_listA
Read-onlyIdempotent

List every item registered for this project's review round, and its verdict.

Read-only. Returns items (each review_add registration: name, kind, project-relative path, sha256 and any control baseline) and verdicts (keyed by item name: the verdict, its note and when it was recorded). Items are registered with review_add, judged with review_verdict, and served to a phone by proofcut review serve.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.1/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint, idempotentHint, and destructiveHint, so the safety profile is covered. The description confirms read-only and adds detail on the return structure (items and verdicts). It does not disclose additional behavioral traits beyond the annotations, so a baseline 3 is appropriate.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is two sentences, front-loaded with the core purpose, then the return shape, then workflow context. Every sentence adds value without redundancy. No fluff or unnecessary detail.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The tool is a simple list operation with one well-documented parameter, safety covered by annotations, and an output schema. The description explains the return structure and how it relates to sibling tools, which is complete for an agent to invoke it correctly. Nothing essential is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Only one optional parameter (path) exists, and its schema description covers 100% of its semantics, including default behavior and binding rules. The tool description adds no additional parameter guidance, so it relies on the schema. Baseline 3 is correct given the high schema coverage.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific verb ('List') and resource ('every item registered for this project's review round, and its verdict'). The description distinguishes it from siblings like review_add (registration) and review_verdict (judging) by clearly scoping its function. It leaves no ambiguity about what the tool does.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Provides context on how it fits into the review workflow by mentioning review_add and review_verdict. It implies when to use it (to inspect registrations and verdicts) but does not explicitly state exclusions or alternative conditions. The related-tools note gives enough situational awareness for an agent to select it appropriately.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

review_verdictA
DestructiveIdempotent

Record a verdict against a review item registered by review_add.

verdict is a free string, not an enum — past review rounds answered yes/no, "loop"/"hold", or a specific choice by name, and a fixed vocabulary would misfit whichever question the next round is actually asking.

Refuses a name review_add has not registered. Calling it again for the same item replaces that item's answer rather than appending one, so a round holds one verdict per item, with the time it was recorded.

ParametersJSON Schema
NameRequiredDescriptionDefault
nameYesThe registered item being answered. An unregistered name is refused.
noteNoAnything to record beside the verdict.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
verdictYesThe answer, as free text rather than an enum — past rounds answered yes/no, loop/hold, or a specific choice by name, and a fixed vocabulary would misfit whichever question the next round asks.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.4/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond annotations, the description discloses refusal of unregistered names, replacement rather than appending, one-verdict-per-item semantics, and that the recorded time is part of the state. This gives the agent a clear picture of side effects without relying on inference.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The purpose is front-loaded in the first sentence, and the rest provides important behavioral context. The free-text rationale is slightly repetitive with the verdict parameter description, but all sentences earn their place.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the output schema and complete input schema, the description covers the registration prerequisite, free-text semantics, replacement behavior, refusal case, and timestamp side effect. An agent has enough information to select and invoke the tool correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, and each parameter already has a detailed description, including nuanced path behavior. The description mostly reiterates the verdict free-text rationale from the schema rather than adding new parameter-level meaning, so the baseline 3 applies.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific action ('Record a verdict') against a specific resource ('a review item registered by review_add'). This clearly distinguishes it from sibling tools like review_add (registration) and review_list (listing).

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description makes the prerequisite explicit: the verdict must be against an item already registered by review_add. It gives clear context for when this tool is appropriate, though it does not explicitly name alternatives or when-not-to-use conditions.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

seed_timelineA
DestructiveIdempotent

Lay a clip down as the timeline, silence-cut by auto-editor by default.

A list of clips lays several recordings end to end in that order, each silence-cut the same way — a footage dump seeded once, cleaned once, then split. clips reports each one.

edit_expr passes auto-editor's edit language straight through, e.g. "(or audio:0.03 motion:0.06)".

Writes project.otio and replaces any timeline already there — every cut made since the last seed included. It seeds a project rather than re-cutting one, and a re-seed with the same arguments lands the same timeline. The old one is snapshotted first, so undo puts it back.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
marginNoHow much to leave either side of kept audio, in auto-editor's own notation (e.g. `0.2s`), so an edge lands in the silence rather than on the breath.
clip_idYesThe clip to lay down as the timeline, or a list of recordings laid end to end in that order. Several must all have picture.
edit_exprNoauto-editor's edit language, passed straight through — e.g. `(or audio:0.03 motion:0.06)`. It replaces the threshold-based rule.
thresholdNoauto-editor's audio loudness threshold, 0–1. Lower keeps quieter material.
remove_silencesNoSilence-cut the clip on the way in, through auto-editor. On by default; false lays the whole clip down untouched.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.3/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already indicate destructive and idempotent behavior, but the description adds valuable detail: 'Writes `project.otio` and **replaces any timeline already there** — every cut made since the last seed included.' It also discloses the undo safety net ('The old one is snapshotted first, so `undo` puts it back') and explains the silence-cutting default, which fully transparently expands on the annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is well-structured, front-loading the core purpose in the first sentence. It uses three paragraphs to cover single clips, multiple clips, and the edit expression, then explains the write/destructive behavior. While slightly verbose, every sentence adds relevant context and no filler or redundancy is present. The use of bold for the destructive action improves scannability.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's complexity (6 parameters, 1 required, destructive and idempotent), the description covers most key aspects: the operation, behavior with lists, edit expression passing, parameter defaults (via schema), and the replacement/undo mechanism. It does not explicitly mention expected return values or error scenarios, but an output schema exists, so that burden is partially relieved. A few edge cases like handling of `path` when unbound are already in the schema, so the description is sufficient for an agent to correctly invoke the tool.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so all parameters already have detailed descriptions. The tool description adds marginal context, such as explaining that `edit_expr` passes auto-editor's edit language straight through and that `clip_id` as a list lays recordings end to end. These nuances are already partly present in the schema, so the description adds limited additional meaning beyond what the schema provides.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Lay a clip down as the timeline, silence-cut by auto-editor by default.' It clearly distinguishes from siblings by stating it 'seeds a project rather than re-cutting one' and explicitly references the `split` and `clips` tools. The purpose is unambiguous and behaviorally distinct from the listed siblings like `timeline_status` or `timeline_view`.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explains when this tool is appropriate: it seeds a project rather than re-cutting one, and mentions that a re-seed with the same arguments yields the same timeline. It also references `split` and `clips` as subsequent operations. However, it does not explicitly state when NOT to use it or offer a direct comparison with alternatives like `split` or `undo`. The guidance is clear but not exhaustive.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

shot_sheetA
DestructiveIdempotent

Look at the picture track — one labelled tile per shot, as an image.

This is the tool to call to see what the film looks like — the picture track of the edit as it stands. Its neighbours answer different questions with the same kind of picture: footage_sheet browses one registered clip's own material, contact_sheet looks at a clip's first ten seconds, and reframe_sheet reviews framing windows a page at a time. All four hand the bytes back, because an agent confined to proofcut's tools (the agent panel's --tools ToolSearch) can open no path at all.

One tile per shot, at the exact source second that shot reads from, four across and about two dozen a page — the measured ceiling before vision downscales the sheet and takes the labels with it. Each tile is labelled asset t=<timeline second>s src=<source second>s, and page walks a longer film.

asset on a row is the footage; clip_id is the transcript the cue is addressed against, which on a voiceover project is the VO and not anything you can see. Read asset.

Drawn from the same projection export renders, so a plan that refuses comes back as shots_error with no sheet rather than a picture of a film that will not render.

What you see here is a hypothesis, not a check. Nothing downstream reads a verdict formed off this sheet — confirm one with an op that measures (check_frames, verify, black, reframe_coverage).

out is the one thing here that writes where you say: the montage lands at that path, replacing whatever file is there. Without it a page is written into the project's own sheet cache, which nothing reads back as authored state.

ParametersJSON Schema
NameRequiredDescriptionDefault
outNoWrite the image to this path as well, replacing whatever file is there. Unset, it goes to the project's own sheet cache and only the bytes come back.
pageNoWhich page of rows to draw, from 1. Unset, the first.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
per_pageNoRows per page. `null` draws the whole project in one montage, which returns a path rather than readable bytes — for a person to open, not for an agent to read.

TDQS

A4.9/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations indicate `destructiveHint: true` and `readOnlyHint: false`. The description goes beyond these flags by detailing the destructive case: 'the montage lands at that path, replacing whatever file is there.' It also discloses that all four sibling tools 'hand the bytes back' and that the sheet is a hypothesis ('What you see here is a hypothesis, not a check'), plus explains rendering failure behavior (`shots_error`). No contradiction with annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but well-organized, opening with the core purpose, then differentiating siblings, then diving into tile mechanics, labels, rendering pitfalls, and parameter notes. Every section adds necessary context; it is not padded. It could be slightly tightened (e.g., merging some repeated mentions of 'four' and 'two dozen'), but the structure supports comprehension.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a tool with four parameters, no output schema, and complex behavioral nuances (destructive write, rendering failure, hypothesis status, page navigation, asset-vs-clip distinction), the description covers all critical aspects. It explains what the agent will receive (bytes, or a path if `per_page` is null), how to handle the output, and warns against using it as a verdict. Nothing an agent needs to call it correctly is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters5/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, but the description adds substantial meaning. For `out`, it clarifies it writes and replaces a file; for `page`, it says 'walks a longer film'; for `per_page`, it explains that `null` returns a path for a person, not an agent; for `path`, it covers project binding behavior and refusal cases. This extra context makes the parameters safer and clearer to use.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a clear statement: 'Look at the picture track — one labelled tile per shot, as an image.' It names the resource (picture track of the edit) and the action (look at). It then explicitly differentiates from siblings (`footage_sheet`, `contact_sheet`, `reframe_sheet`) by describing what each neighbor does instead, leaving no ambiguity about this tool's unique role.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It states 'This is the tool to call to see what the film looks like' and contrasts with siblings: 'footage_sheet browses one registered clip's own material, contact_sheet looks at a clip's first ten seconds, and reframe_sheet reviews framing windows a page at a time.' It also warns this is a hypothesis, not a verification, and points to measurement tools (`check_frames`, `verify`, `black`, `reframe_coverage`) for confirmation. This gives explicit when/when-not guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

sound_addA
Idempotent

Play a one-shot sound at a word, an event, or every event of one name.

Import the sound first (import_media), or call sound_generate for a ready UI set: eight key ticks, send, land, strike. every="key" puts a tick on each keystroke event; pass all eight keys as assets so the run does not repeat one sample, and a jitter_db of 2-3 to vary them. Hits land to the millisecond, between frames, and are resolved through the timeline on every build: a cut moves them, an every hit a cut removed is skipped, and a single hit whose word or event is cut makes export refuse until it is moved. The picks and jitter repeat on every build. src_in/src_out trim what plays. The music's duck hears a sound only with ducks. The reply counts the hits and echoes the first few; plan=true writes nothing. Export's reply lists the sounds it placed.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
afterNoA forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start.
ducksNoThe music bed's duck hears this sound as it hears the voice: set it for a narrator take or a line of dialogue placed as a sound, never for clicks. Only matters when the bed has a duck.
eventNoPlay at this event of clip_id: `name`, or `name#k` when the name repeats.
everyNoPlay at every event of clip_id with this name (e.g. every keystroke). Events a cut removed are skipped and counted.
assetsYesThe imported clips to play, by clip_id. With several, each hit draws one, so a typed run does not repeat one sample. sound_generate registers a ready set (sfx-*).
phraseNoPlay as this phrase's FIRST word starts, resolved against clip_id's transcript.
src_inNoSeconds into each asset where the sound starts. With src_out, plays one line of a long take, and the 30 s cap is on the trimmed part.
clip_idYesThe clip whose words or events say where — the transcript the word index indexes, or the recording the events belong to.
gain_dbNoThe level in dB; 0 plays the file as it is. The generated set peaks at -3 dBFS.
min_gapNoWith every: drop a hit closer than this many seconds to the last one kept. Default 0.045.
src_outNoSeconds into each asset where the sound stops. Unset plays to the file's end.
jitter_dbNoVary each hit's level by up to this many dB either way. Default 0.
occurrenceNoDisambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at.
word_indexNoPlay as this word starts. One of word_index, phrase, event or every.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.6/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the annotations, it discloses important build-time behavior: cuts move hits, `every` hits on removed cuts are skipped, a single hit on a removed word/event makes export refuse until moved, and picks/jitter repeat on every build. It also clarifies that `plan=true` writes nothing and that export's reply lists placed sounds. No contradiction with annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense at roughly 180 words but front-loads the core action and packs behavior caveats that matter for correct use. Every sentence carries information, though phrases like 'ready UI set' are slightly awkward and could be tightened.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the 16-parameter complexity, rich schema, annotations, and output schema, the description covers the non-obvious behaviors an agent would otherwise miss: duck interaction, plan mode, export placement listing, and repeated-build resolution. Nothing essential appears missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3, but the description adds real usage guidance: pass all eight keys as `assets` to avoid repeated samples, use `jitter_db` of 2-3 to vary them, and `src_in`/`src_out` trim playback. It supplements rather than restates the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The first sentence names a specific verb ('Play'), a resource ('a one-shot sound'), and placement targets ('at a word, an event, or every event of one name'). This clearly differentiates it from siblings like sound_generate, which creates assets, and sound_rm, which removes them.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives workflow context: import media first or call sound_generate for a ready set, and it explains when `every`, `ducks`, and `plan=true` are relevant. It does not explicitly state when-not-to-use cases or compare against alternatives like overlay_add, but the context is clear enough for most routing decisions.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

sound_generateA
DestructiveIdempotent

Write proofcut's generated UI sounds into the project and import them.

Registers sfx-key_0 … sfx-key_7 (soft key ticks), sfx-send (a click), sfx-land (a thump and chime, for a result arriving) and sfx-strike (a falling swipe), synthesised, under assets/sounds/. Ids already registered are left alone. Use them with sound_add.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.3/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The description adds concrete behavior beyond the annotations: exact sound IDs, their meanings, the output location (assets/sounds/), and the idempotent behavior of leaving already-registered IDs untouched. This complements the idempotentHint and destructiveHint annotations rather than contradicting them, though it could more explicitly state whether files are overwritten.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact and front-loaded: a clear one-sentence purpose, followed by a precise list of generated IDs and behaviors. Every sentence adds useful information, and there is no padding or repetition of schema content.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given that the tool has only one optional parameter (fully explained in the schema) and an output schema exists, the description covers everything an agent needs: exactly what will be created, where, which IDs are affected, and how the results should be used afterward. No critical operational context is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The sole parameter, path, is fully documented in the input schema with a detailed explanation of bound-project resolution, relative paths, and omission behavior. The description itself adds no parameter-specific meaning, so the schema-coverage baseline of 3 applies.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Write proofcut's generated UI sounds into the project and import them.' It then lists exact sound IDs and their semantics, making it unmistakable what the tool does and clearly distinguishing it from siblings like sound_add, sound_ls, and sound_rm.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives clear contextual guidance: existing IDs are left alone, so reruns are safe)Skip, and the generated sounds are meant to be used with sound_add. It does not explicitly compare to alternatives such as sound_add or sound_rm, but the usage context is strong enough for an agent to select and sequence the tool correctly.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

sound_lsA
Read-onlyIdempotent

Every sound record, with how many hits each places now.

Each carries its position (as sound_rm takes it), hit_count, how many occurrences were skipped (cut) and thinned (too close), and its first hits. Records that cannot resolve come back as sounds_error beside the stored records.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A3.6/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already mark it read-only and idempotent. The description adds valuable behavioral context: it mentions that unresolved records come back as `sounds_error` alongside stored records, and details the fields carried (position, hit_count, skipped, thinned). This goes beyond the safety annotations and helps the agent understand error handling.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Two short paragraphs with no filler. The first sentence states the purpose, the second details the output fields and error handling. Every sentence earns its place, and the most important information is front-loaded.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a simple listing tool with an output schema, the description covers the key aspects: what records are returned, what fields they contain, and how errors are represented. It doesn't mention sorting or pagination, but those are likely covered by the output schema. The description is adequate for an agent to call it correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100% for the single `path` parameter, so the schema already documents its meaning and defaults. The tool description adds no further parameter semantics, but per rubric the baseline is 3 when schema coverage is high.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states it lists every sound record with hit counts, distinguishing it from sound_add, sound_rm, etc. It names the resource (sound records) and the action (listing with metrics). However, it could be more explicit about the 'list' verb, though 'every sound record' implies enumeration.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

No explicit guidance on when to use this tool versus alternatives. It doesn't mention sound_add, sound_rm, or sound_generate, nor does it state conditions for selection. The description implies it's the listing counterpart, but an agent would need to infer that from context.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

sound_rmA
Destructive

Take one sound record off the film, by its position in sound_ls.

The clip stays registered. Positions above the removed one move down.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
positionYesThe sound record to remove, by its position in sound_ls.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.2/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations declare destructiveHint=true, and the description adds meaningful behavioral context beyond that: it clarifies that the clip 'stays registered' (not a full deletion) and that 'positions above move down' (re-indexing). This goes beyond the annotation's binary destructiveness and gives the agent a more precise model of the effect.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is exactly two sentences with zero wasted words. The core purpose is front-loaded, and the behavioral nuance (stays registered, positions shift) is stated efficiently. It is a model of concision for a simple removal operation.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a destructive tool with an output schema and well-documented parameters, the description covers the essential behavior. It would benefit from an explicit mention that sound_ls should be used to obtain the position, but this is strongly implied. The description is otherwise complete for an agent to call the tool correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The input schema has 100% description coverage, with detailed explanations for path and plan, and a clear description for position. The tool description adds no new parameter semantics beyond what the schema already provides, so the baseline of 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific verb ('Take'), a clear resource ('one sound record off the film'), and an unambiguous identifier ('by its position in sound_ls'). It also differentiates from sibling removal tools by specifying 'sound' and from sound_add/ls/generate by the removal action. The added detail about positions shifting further clarifies the operation.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description implies the correct workflow by referencing 'position in sound_ls', indicating that sound_ls should be called first. However, it does not explicitly state when to use this tool versus alternatives (e.g., overlay_rm, clip_rm), nor does it mention exclusions or when not to use it. The context is clear enough for an agent to infer the intended use.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

speech_overlapA
Read-onlyIdempotent

Does a proposed placement of clip_id overlap the VO's speech?

The prerequisite check behind "can this clip speak here?" — answer it before designing any ducking. at/clip_in/clip_out describe where clip_id would sit on the timeline (defaults: unplaced at 0, its whole duration) — the clip need not be on the timeline yet, and usually isn't, since the current model is single-track. VO's own words map through the existing edit (Edit.timeline_span); clip_id's map by offsetting into the proposed window instead. Both sides are trimmed with energy.believable first — an inflated word duration can hide a real seam — then merged into speech runs with max_gap tolerance, since a 0.05s gap is not a usable seam.

Read overlaps first: any entry means placing clip_id there would step on VO speech, not empty air — this caught exactly that on Billy/Stu, where the clip's speech nearly fully covered a VO thesis line with no clean seam to duck into. clean_seams (>= min_seam wide) are the windows where clip_id could speak without touching the VO. Read-only — nothing is written, and there is no plan=.

clip_id need not have a transcript. Without one the clip side is its energy envelope — runs of sound, reported as sound rather than speech (a sting or a swell counts too) — and clip_evidence in the result says "energy" so the reading is not mistaken for a word-level one. Pass clip_evidence="transcript" to refuse instead, or "energy" to force the envelope on a clip that has a transcript. The VO always needs its transcript.

ParametersJSON Schema
NameRequiredDescriptionDefault
atNoWhere the clip would sit on the timeline, in seconds.
capNoHow far a word's claimed duration is trusted, as a multiple of the median. Whisper inflates the word after a collapsed retake until it covers the second take, so believing the claim masks exactly the hole being looked for — 3x is the same multiple a suspect duration is flagged at.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
clip_idYesThe clip whose placement is being proposed. It need not be on the timeline yet, and usually is not.
clip_inNoWhere inside the clip the proposed placement starts, in its own source seconds. Unset, its head.
max_gapNoHow short a silence may be and still be swallowed into one speech run, in seconds — a 0.05s gap is not a usable seam.
clip_outNoWhere it ends, in the clip's own source seconds. Unset, its end.
min_seamNoHow wide a gap has to be to be reported as a `clean_seam`, in seconds.
vo_clip_idNoWhich transcript is the VO. Unset, the project's own. The VO always needs a transcript; the placed clip does not.
clip_evidenceNo`auto` (the default) uses the clip's transcript if it has one and its energy envelope otherwise, saying which in the result. `transcript` refuses a clip with none; `energy` forces the envelope even on a clip that has one — sound rather than speech, which counts a sting or a swell too.auto

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.6/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true, idempotentHint=true, and destructiveHint=false, so the safety profile is covered. The description adds valuable behavioral context beyond that: it explains the trimming with `energy.believable`, the merging into speech runs with `max_gap` tolerance, and the read-only nature ('nothing is written, and there is no `plan=`'). It also discloses the fallback behavior when `clip_id` lacks a transcript, which is a meaningful behavioral trait not visible in the schema. Minor gap: it doesn't describe the exact result shape beyond `overlaps`, `clean_seams`, and `clip_evidence`, but the output schema exists.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but every paragraph earns its place: the first paragraph states the core question and the mapping logic, the second explains the output semantics and the real-world catch, the third covers the transcript/energy fallback. It is front-loaded with the purpose and read-only note. It loses one point for density—some sentences are packed with domain jargon ('energy.believable', 'speech runs', 'seam') that could be tightened—but it is not bloated or repetitive.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a complex 10-parameter tool with an output schema, the description is remarkably complete. It explains the default placement semantics, the single-track model assumption, the trimming and merging pipeline, the meaning of `overlaps` and `clean_seams`, the transcript/energy fallback, and the read-only guarantee. The output schema covers return values, so the description doesn't need to enumerate them. An agent has everything needed to decide when to call this tool and how to interpret its result.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the baseline is 3. The description adds meaning beyond the schema by explaining the conceptual role of `at`/`clip_in`/`clip_out` as describing where `clip_id` would sit on the timeline, and how the clip's words map by offsetting into the proposed window. It also explains the rationale behind `max_gap` ('a 0.05s gap is not a usable seam') and `cap` (Whisper inflation), which the schema descriptions only hint at. It doesn't restate every parameter, but it adds interpretive context that helps an agent choose values correctly.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a direct question—'Does a proposed placement of `clip_id` overlap the VO's speech?'—which precisely states the tool's verb, resource, and purpose. It distinguishes itself from siblings by framing it as the prerequisite check behind 'can this clip speak here?' and explicitly notes it is read-only with no `plan=`, separating it from planning or editing tools.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives explicit when-to-use guidance: 'answer it before designing any ducking.' It also explains the clip need not be on the timeline yet and usually isn't, since the current model is single-track. It clarifies when to pass `clip_evidence` values ('Pass `clip_evidence="transcript"` to refuse instead, or `"energy"` to force the envelope'), and notes the VO always needs a transcript. This is strong routing and exclusion guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

splitA
Idempotent

Cut this timeline into shorts, each a new project beside this one.

For a footage dump: seed every recording (seed_timeline takes a list), clean it once (cut_by_transcript, verify), then split. Which shorts there are and where each starts is your reading of the transcripts. Each short is reel over its span, so everything reel reports comes back per short, and each also leaves out the recordings it does not use (clips_dropped).

overlaps (two shorts sharing material) and unassigned (timeline spans no short holds — a take missed stays in the dump) are reported, never refused: read both. This server cannot reach a short once it exists, by design; proofcut web --root <the dump's parent> lists them. plan=True resolves every short and creates nothing.

ParametersJSON Schema
NameRequiredDescriptionDefault
intoNoThe directory the shorts are created in. Unset, the dump's own parent, so they sit beside it. A bound server takes no other.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
canvasNoThe shape to set on every short, e.g. `1080x1920` — one delivery shape for the batch. The dump keeps its own.
shortsYesEvery short, in order: `{name, from, to}` where `from` is its first word and `to` its last, each `{clip_id, word_index}` or `{clip_id, phrase}` (plus `occurrence` for a repeated phrase); or `{name, start, end}` in the render seconds `reel` takes. `name` is one directory name, created beside the dump, and must not exist.
confirm_suspectNoGo ahead even though a boundary word claims a suspect duration. Read the echoed words first — a suspect duration usually means whisper hid a retake inside that word, so the edge is not where it reads.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.9/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The description goes beyond annotations by disclosing that `overlaps` and `unassigned` are reported, never refused, and that 'This server cannot reach a short once it exists, by design.' It also explains the `plan=True` behavior (resolves and creates nothing) and the `proofcut web` listing workaround. Annotations (readOnlyHint=false, destructiveHint=false) are not contradicted; these additional details significantly increase transparency for a mutation tool. No contradiction.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but every sentence carries information. It starts with the core action and then layers workflow, output behavior, and operational caveats. It is longer than typical but not wasteful. The structure effectively front-loads the primary purpose before diving into edge cases.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's complexity (6 params, 1 required, nested objects in `shorts`, and an output schema), the description covers all essential aspects: workflow, parameter semantics, boundary conditions (suspect durations), reporting of overlaps/unassigned, post-split accessibility, and dry-run. An agent has everything needed to invoke it correctly, including fallback listing via `proofcut web`.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters5/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3, but the description adds substantial meaning beyond the schema. It explains the `shorts` format in detail (word indices, phrases, occurrences, render seconds), clarifies `into` behavior (unset -> dump's parent, bound server restriction), and `path` binding semantics. The `plan` and `confirm_suspect` parameters are also contextualized with reasoning. This fully compensates for any ambiguity in the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Cut this timeline into shorts, each a new project beside this one.' It clearly states the tool's function and distinguishes it from siblings by describing the workflow context (footage dump) and mentioning related tools (seed_timeline, cut_by_transcript, verify). The purpose is unambiguous.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives explicit usage conditions: 'For a footage dump: seed every recording... clean it once... then split.' It also clarifies the decision point ('Which shorts there are and where each starts is your reading of the transcripts') and recommends dry-run with `plan=True`. No alternative tools are named, but the workflow context is precise enough for an agent to know when to use this tool.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

spot_framesA
Read-onlyIdempotent

Pull count evenly-spaced frames (plus any explicit times) from a render as PNGs with signalstats luma, ranked darkest-first.

When target's own probed duration still matches the current timeline within a frame (mapping_trusted), each frame also reports which clip/word it lands near via Edit.source_at — refused, not guessed, when the render looks stale.

Like shot_sheet/footage_sheet/contact_sheet, the reply also carries a montage of the sampled frames as an image — frames[].png is a path, and an agent confined to proofcut's tools (the agent panel's --tools ToolSearch) has no Read to open one (TRIAL.md § spot_frames hands back paths the agent cannot open).

ParametersJSON Schema
NameRequiredDescriptionDefault
fpsNoThe rate used to map a frame back to the clip and word it lands near — refused rather than guessed when the render's duration no longer matches the timeline.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
countNoHow many evenly-spaced frames to pull. They come back ranked darkest-first, with a montage of them as an image.
timesNoExplicit seconds to sample as well as the evenly-spaced ones.
targetYesThe render to pull frames from.

TDQS

A4.2/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond the readOnly/idempotent/non-destructive annotations, the description adds crucial behavioral detail: mapping is refused rather than guessed when the render is stale, and the returned PNG paths cannot be opened by an agent limited to proofcut tools. This significantly improves an agent's ability to predict tool behavior.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but each sentence earns its place: core operation, trust/mapping behavior, and output/agent-access limitation. It is longer than minimal, but that length is justified by genuinely useful caveats; the first sentence front-loads the primary action.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

With no output schema, the description compensates by explaining the key return aspects: PNG frames, montage, darkest-first ranking, and per-frame source mapping. It also warns about the agent's inability to open returned paths, which is critical context for a proofcut-bound agent. Inputs, outputs, and edge-case behavior are all covered.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the schema already documents all five parameters thoroughly. The description reuses `count`, `times`, and `target` but does not add much meaning beyond what the parameter descriptions already provide; the baseline of 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific, concrete operation: pull `count` evenly-spaced frames (plus `times`) from a render as PNGs with signalstats luma, ranked darkest-first. This clearly identifies the tool's resource and behavior, and the sibling references (shot_sheet/footage_sheet/contact_sheet) place it in a family without obscuring its distinct purpose.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description signals that it belongs with sheet-like tools by naming shot_sheet/footage_sheet/contact_sheet, but it never states when an agent should choose spot_frames over those siblings. The mapping_trusted caveat describes behavior, not selection criteria, so usage guidance is implied rather than explicit.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

synopsisA
DestructiveIdempotent

Read, set or clear what a clip is — the corpus b-roll gets chosen from.

No clip_id lists every clip's synopsis and which are missing one; clip_id alone reads one; text writes; clear removes.

A synopsis is a different fact from a describe window. A description says what is in front of the camera — rooms, clothing, lighting. A synopsis says what the footage is: the work, the scene, the people, and whatever else decides whether it belongs under a sentence. It is meant to carry what no camera can see, because that is where the signal turned out to be — measured on real footage, the vision index chose the same clip a human did 2 times in 25, and this catalogue read by something that knows the material chose it 13.

Write these yourself. Nothing generates them: a model looking at the pixels cannot, and guessing a title from a filename would produce confident wrong placements rather than an obviously empty catalogue.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
textNoWhat this footage **is** — the work, the scene, the people. A different fact from a `describe` window, which says what is in front of the camera. Write it yourself: nothing generates one, because a model reading the pixels measurably cannot.
clearNoRemove this clip's synopsis.
clip_idNoThe clip to read or write. Omit it to list every clip's synopsis and which are missing one.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.3/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already provide idempotentHint=true and destructiveHint=true (with readOnlyHint=false), and the description adds genuine value on top: omitting clip_id lists all clips' synopses, clip_id alone reads, text writes, clear removes. It also discloses the destructive nature of `clear` in plain terms and explains the expected agent behavior (write synopses, don't guess from filenames). No contradiction with annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is front-loaded: purpose and operational modes come in the first two short paragraphs, followed by the describe distinction and the write-it-yourself directive. The statistical anecdote (2 in 25 vs 13) is slightly tangential but earns partial keep by motivating why careful synopsis writing matters. A bit longer than strictly necessary, but every section serves the agent's decision to invoke and write well.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a four-optional-parameter multi-mode tool, the description covers all operation modes, the key sibling distinction, and the expected authoring behavior. An output schema exists so return values need not be spelled out, and annotations carry the safety profile. Minor omissions like error behavior for unknown clip_ids are acceptable given the annotation and schema richness.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3, but the description adds the mode semantics that the schema does not: how to combine the four optional parameters to get list, read, write, or clear behavior (no clip_id → list; clip_id alone → read; text → write; clear → removes). It also reinforces the meaning of `text` as carrying what no camera can see, beyond the schema's wording.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The first line states a specific set of verbs (read, set, clear) on a specific resource (a clip's synopsis), defined as 'what a clip *is* — the corpus b-roll gets chosen from.' It explicitly differentiates itself from the sibling `describe` tool, telling the agent that a synopsis is a different fact from a describe window. An agent can immediately distinguish this from describe_ls and clip_role.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description clearly draws the when-to-use line against `describe`: descriptions say what is in front of the camera, synopses say what the footage is and whether it belongs under a sentence. It also gives the operational rule 'write these yourself,' warning that nothing generates them. It does not enumerate other sibling alternatives, but the key exclusion (describe) is explicit and central.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

tailA
DestructiveIdempotent

Read or change the finishing pass this project plays after its last frame.

An end card or a bumper, applied by export itself rather than glued on afterward with ffmpeg — the fix for a defect that has already shipped: a finishing pass applied downstream of export is dropped by every derivation at exit 0, silently, because nothing in the project ever knew it existed (HISTORY.md § The bumper the teaser never had, § The end card). Call it with no arguments to read what is in force.

asset must be card:name, never a clip_id — verify diffs a render's own transcription against the timeline's words, and silence adds none of its own, which is exactly what a card behind it guarantees and a media clip would not. seconds is the tail's whole length, card included, not a hold with fade added on top of it (the known trap: xfade finishes exactly at the length it is given). fade dissolves the card in over the film's last frames; 0 cuts to it hard. A music bed's over_tail keeps the music playing under the card.

Setting asset or seconds for the first time needs both together; either alone after that updates just that field, the same partial-update shape caption_style has. reset drops the tail entirely.

The card follows the cues' picture lane, or with none the timeline's own track, so a screen recording takes a tail as it is. A sound-only film with no cues is refused by export, by name. plan resolves and validates without writing.

ParametersJSON Schema
NameRequiredDescriptionDefault
fadeNoSeconds the card dissolves in over the film's last frames, opaque on the tail's first frame — overlapping the film, never added to `seconds`. 0 cuts to the card hard.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
assetNoThe end card or bumper, as `card:name` — never a clip id. `verify` diffs the render's own transcription against the timeline's words, and a card behind silence adds none of its own, which a media clip would.
resetNoDrop the tail entirely. Note a derivation inherits none of it anyway and reports `tail_dropped`.
secondsNoThe tail's **whole** length, card included — not a hold with `fade` added on top of it.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.6/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Beyond annotations, the description explains the mutation semantics in detail: `reset` drops the tail, setting `asset`/`seconds` first requires both, later updates are partial, `plan` writes nothing, and downstream application drops tails silently. It also discloses edge-case behavior such as sound-only films being refused by `export`. No contradiction with the annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but well-organized into themed paragraphs: purpose, parameter pitfalls, update behavior, and edge cases. Each sentence adds substantive detail, though some historical references (HISTORY.md sections) are tangential. Front-loading is strong.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a mutation tool with 6 parameters, an output schema, and annotations, the description covers all essential behavior: reading, updating, resetting, planning, path semantics are delegated to schema, and niche cases like cue lanes and sound-only films are addressed. Nothing critical is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Input schema already has 100% coverage, so the baseline is 3. The description adds meaningful cross-parameter semantics not present in the schema: the first-time set requires both `asset` and `seconds`, the `seconds` vs `fade` known trap, and the `over_tail` music-bed interaction.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

Opens with a specific verb and resource: 'Read or change the finishing pass this project plays after its last frame.' It clearly distinguishes the tail as an end card/bumper applied by `export`, not a downstream ffmpeg overlay, separating it from sibling tools like finish_report or export itself.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Gives clear context for when to use the tool: to fix a shipped defect, to read the current tail with no arguments, or to use `plan` for a dry run. It contrasts with the ffmpeg-glue-on approach and references the `caption_style` partial-update shape. However, it does not explicitly name alternative tools or state hard when-not-to-use conditions.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

thumbnailA
Read-onlyIdempotent

One filmstrip frame for clip_id, at the source time nearest at.

at snaps to a multiple of interval before anything is extracted, and the frame is cached under cache/thumbs/ keyed by the clip's media size and mtime — a repeated ask for a nearby instant is a cache hit. The result is a path, not the image bytes; proofcut web serves those over /api/thumb/<clip_id>?at=. It never enters the manifest, so nothing that renders can reach it (the same wall the preview proxy has).

ParametersJSON Schema
NameRequiredDescriptionDefault
atYesSource seconds to pull the frame at. It snaps to a multiple of `interval` first, so a repeated ask for a nearby instant is a cache hit.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
clip_idYesThe clip to pull a frame from.
intervalNoThe grid `at` snaps to, in seconds.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.4/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already mark the tool read-only and idempotent. The description adds substantial behavior beyond that: `at` snapping, cache keys based on media size and mtime, cache-hit semantics, path output, and isolation from the manifest. There is no contradiction with the annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Purpose is front-loaded and the cache/output caveats are tightly written. The closing simile about the preview proxy is useful context but is the least essential sentence.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a read-only retrieval tool with a rich output schema and fully documented parameters, the description covers the return contract (a path, not bytes), caching behavior, and render isolation. Nothing an agent needs to invoke it correctly is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The input schema already has 100% description coverage for all four parameters, including the `at` snapping and `path` binding behavior. The description repeats the snapping behavior but adds little new parameter-level meaning beyond what the schema already documents.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The opening sentence identifies the exact resource and operation: a filmstrip frame for `clip_id` at source time `at`. It is clearly distinguished from render/manifest tools by stating the result is a path and that it never enters the manifest.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives clear operational context: it returns a cached path, and the actual bytes are served by `proofcut web` via a specific endpoint. It doesn't explicitly name alternative sibling tools, but the manifest exclusion and web-serving note provide a useful boundary for when this tool is appropriate.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

timeline_statusA
Read-onlyIdempotent

Report the current timeline: duration, segment count, undo depth.

head/tail echo the cold open / finishing pass set with the head/ tail tools, or null for either with none. expected_frames/ expected_duration are what export would lay down — timeline_duration alone stays the Edit's own length even with a head or a tail configured, since the Edit never grows to describe either bookend.

This is the tool to call first, to see what state a project is in — a fresh or un-seeded project answers seeded: false with the clip list rather than refusing (TRIAL.md § timeline_status is the first call an agent makes and it refuses on a fresh project).

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.1/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare read-only, idempotent, and non-destructive behavior. The description adds valuable context: head/tail echo semantics, expected_frames/expected_duration versus timeline_duration, and seeded:false behavior. However, the parenthetical 'it refuses on a fresh project' contradicts the earlier 'rather than refusing', creating ambiguity.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The core purpose is front-loaded in the first sentence, and the head/tail and expected_duration details are substantive. The final TRIAL.md parenthetical is tangential and internally confusing, which prevents full marks for conciseness.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

An output schema exists and the description explains subtle return-value semantics and edge cases around head/tail, export, and seeded projects. The contradictory sentence about refusing on a fresh project leaves one behavioral area ambiguous, so completeness is slightly diminished.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The single path parameter is fully documented in the input schema with 100% coverage, including default and binding behavior, so the description does not need to add parameter detail. It also does not repeat parameter semantics, matching the baseline expectation.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific verb 'Report' and resource 'current timeline', and enumerates concrete outputs: duration, segment count, undo depth. The scope is unambiguous and clearly differentiates this from state-mutating siblings like seed_timeline or cut tools.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Explicitly identifies this as 'the tool to call first, to see what state a project is in' and explains the fresh/unseeded project behavior. It does not explicitly compare against alternatives like timeline_view or properties, so exclusions are absent, but the primary usage context is clear.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

timeline_viewA
Read-onlyIdempotent

The whole edit at once: segments, cut seams, and every word's fate.

timeline_status counts things; this says what they are. Each segment carries both coordinate systems (source in, timeline out), each seam is named by the surviving words either side of it rather than by the second it currently sits at, and each word reports whether it survived, how much of it did, and where it now plays.

Survival is an overlap test, so a word a cut split reports present with partial set — that is normal on whisper timings, not a defect. Words with a suspect duration carry the same flag attach_transcript reported.

This is locate asked once for the whole clip instead of once per range, and it is what the proofcut web view draws. Read-only.

shots is the picture lane the cue table projects — null when there are no cues, and null with a shots_error message when the plan refuses (a cue that was cut, or a shot longer than the asset it points at). The refusal is reported here rather than raised, because this is the view a person uses to find the cue to fix. shots_rate is the frame grid it was quantised on, which is export's rate and not timebase.

segments/shots/seams stay Edit-relative even with a head configured — see head's own docstring for the two-clock rule. head_seconds is the offset a render-time reader needs (0.0 with none); head is the stored config plus its resolved frame count.

words is a window of limit from first (words_total, words_next); the lanes are always whole. get_transcript with search= finds a word faster than paging here.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
firstNoIndex into the `words` list to start the window at. 0 by default.
limitNoMost entries of `words` to return; `words_next` says where to continue. The segments, seams and shots are always whole.
clip_idNoThe transcript whose words' fate to report. A clip that is registered but not on the edit still answers — read `off_timeline`, or every word reads `present: false` and looks cut.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.6/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnly/idempotent, and the description adds substantial non-obvious behavior: partial survival is normal on whisper timings, shots refusals are reported not raised, segments/shots/seams stay edit-relative under head, and the shots_rate grid is export's rate not timebase. This goes well beyond the annotation baseline.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long and dense but front-loaded with a one-sentence summary and organized into clear thematic paragraphs. Some phrasing is poetic ('every word's fate', 'the picture lane the cue table projects') but generally every paragraph earns its place given the tool's complexity.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The description covers edge cases thoroughly: partial survival, suspect durations, shots null/refusal behavior, head clock relativity, pagination windowing, and the search alternative. With an output schema present and detailed input schema, an agent has everything needed to call and interpret the tool correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the baseline is 3 even without parameter details in the description. The description adds only modest param-level value — noting words is a window while lanes stay whole and recommending get_transcript for faster single-word search — but does not meaningfully override what the schema already provides.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The opening line — 'The whole edit at once: segments, cut seams, and every word's fate' — states a specific resource and scope. It explicitly contrasts with timeline_status ('counts things; this says what they are') and frames itself as 'locate asked once for the whole clip instead of once per range,' making differentiation from siblings immediate.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description names alternatives explicitly and gives selection conditions: use this instead of timeline_status when item-level detail is needed, use get_transcript with search= for faster single-word lookup, and use locate for per-range queries. This satisfies both 'when' and 'when-not' guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

transcribeA
Destructive

Transcribe a clip's own media with whisper, and attach the result.

attach_transcript's ASR-driven sibling: use that when the recording already has a transcript, this when it needs one made. Takes minutes on a long recording — there is no timeout, so let it run. Reports near_duplicates, suspect_durations, overlaps and repeats the same way attach_transcript does.

It replaces whatever transcript the clip already had, and it is the one mutation undo cannot reach: a transcript is its own file, so this writes neither the manifest nor the timeline and nothing is snapshotted. There is no cache either — a second call spends the same minutes again. get_transcript first if a transcript might already be there.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
modelNoThe whisper model to run, e.g. `small.en`. Larger is slower, and there is no timeout.turbo
clip_idYesThe clip whose own media whisper transcribes.
languageNoForce a language code, e.g. `en`. Unset, whisper detects it, which it gets wrong on short or noisy clips.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The description goes well beyond the annotations by disclosing that the tool replaces any existing transcript, is unreachable by undo, writes neither manifest nor timeline, has no cache, takes minutes, and has no timeout. These are critical behavioral facts that annotations alone would not convey.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is front-loaded with the core purpose, then cleanly covers sibling selection, runtime expectations, destructive behavior, and undo/cache caveats. Every sentence adds distinct value, and the density is appropriate for a tool with this many behavioral implications.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the annotations, output schema, and fully documented parameters, the description covers everything an agent needs to invoke this tool correctly: what it does, when to use it, what it destroys, how long it can take, and what to check beforehand. The mention of diagnostics like near_duplicates and overlaps compensates for not detailing the output, which the output schema already provides.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Input schema description coverage is 100%, and each parameter already has a meaningful description. The tool description adds useful context around behavior and alternatives but does not add new parameter-level semantics, so the baseline of 3 applies.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Transcribe a clip's own media with whisper, and attach the result.' It also distinguishes itself from attach_transcript by naming the sibling and its purpose, so an agent can tell them apart immediately.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It explicitly states when to use this tool versus attach_transcript: 'use that when the recording already has a transcript, this when it needs one made.' It also advises calling get_transcript first if a transcript might already exist, which is concrete pre-use guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

transcript_checksA
Read-onlyIdempotent

Re-check an already-attached transcript against itself.

Returns the same four findings attach_transcript does — near_duplicates, suspect_durations, overlaps, repeats — for a transcript attached earlier, whose findings were reported once and are otherwise gone. Omit clip_id for every clip that has a transcript.

Read overlaps before anything derived from this transcript is drawn on screen. A seam there is whisper reading across a retake splice and interleaving both takes, which invents words nobody said — and they read as ordinary English, so a human proofread finds some and is blind to the rest. repeats catches the other shape a retake takes: one that survived transcription as distinct, cleanly-timed duplicated words rather than as an interleaved seam. Reads only; it never writes.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
clip_idNoOne clip to re-check. Omit it for every clip that has a transcript.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.4/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already carry readOnlyHint=true and destructiveHint=false, and the description reinforces with 'Reads only; it never writes' — consistent. Beyond that, it adds genuinely valuable behavioral context: the warning that an overlaps seam means whisper is inventing words nobody said, and that a human proofread is blind to some of them, plus the ordering directive to read overlaps before drawing on screen. This is substantial context beyond what annotations provide.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The purpose and return findings are front-loaded in the first sentence. The description is long (~130 words), and the deep-dive into overlaps/retakes is verbose, but every sentence carries actionable weight — the invented-words danger and the read-overlaps-first directive justify the length. Slightly over-detailed but not wasteful.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a read-only, idempotent tool with two optional parameters, full schema coverage, and an output schema, the description is complete. It explains the four findings, their significance, the clip_id omission case, and the safety-critical ordering. Nothing an agent needs to call it correctly is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so both parameters are fully documented in the schema. The description's clip_id guidance ('Omit clip_id for every clip that has a transcript') is verbatim identical to the schema's own clip_id description, adding no new meaning. With full coverage, the baseline of 3 applies.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb+resource ('Re-check an already-attached transcript against itself') and lists the exact four findings returned, tying itself to sibling attach_transcript ('Returns the same four findings attach_transcript does'). This clearly distinguishes it from the sibling that performs the original attachment.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The phrase 'already-attached' and 'attached earlier, whose findings were reported once and are otherwise gone' clearly scopes the use case to re-checking prior transcripts. The clip_id omission rule ('Omit clip_id for every clip that has a transcript') gives practical invocation guidance. It does not explicitly name an alternative to prefer for first-time checks, but the relationship to attach_transcript is strongly implied.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

undoA
Destructive

Roll the project back steps mutations (default one) — the timeline, the manifest, or both.

Mutating tools snapshot first (migrate_project keeps its own backup instead), so this undoes cuts, cues, framing, the music bed, caption style and the rest alike. The reply says what came back: timeline_restored, manifest_restored, and timeline_removed when undoing a seed_timeline leaves no timeline at all. Undoing an import un-registers the clip but leaves its media on disk; transcripts are not snapshotted and stay. There is no redo, so an out-of-range steps is refused before anything is restored, and plan shows what it would undo — changes' answer for the same steps — first. status gives undo_depth.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoRoll nothing back; return `changes`' account of what `steps` would undo. There is no redo, so read it before a `steps` above 1.
stepsNoHow many mutations to roll back, from 1 (the last one) up to the undo depth; the same count `changes` takes. All or nothing: a number past the depth is refused, not walked as far as it goes.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.7/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Even though annotations already mark this as destructive, the description supplies crucial behavioral detail: mutations snapshot first, imports unregister clips but leave media on disk, transcripts are not snapshotted, out-of-range `steps` are refused before any restoration, and there is no redo. It also explains reply fields like `timeline_restored`, `manifest_restored`, and `timeline_removed`, giving the agent a clear model of side effects.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is dense but every sentence earns its place: core operation is front-loaded, then scope, side effects, return fields, and safety warnings are organized in logical paragraphs. Code-formatted identifiers and bolded terms keep it scannable despite its length.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a destructive mutation tool with no required parameters, the description covers what is affected, what is preserved, what the response reports, how to preview safely, and how to check undo depth. With annotations and an output schema also present, nothing needed to call the tool correctly is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, and each parameter's schema entry is already detailed (e.g., `steps` documents the depth, all-or-nothing behavior, and refusal past depth). The description reinforces these semantics and adds cross-references to `changes` and `status`, but it does not introduce substantial new parameter meaning beyond what the schema already provides.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The first sentence specifies a precise verb ('roll the project back') with a parameterized resource ('`steps` mutations') and clearly scopes what is affected: 'the timeline, the manifest, or both.' It also names concrete examples of what is undone (cuts, cues, framing, music bed, caption style), making the operation unambiguous and distinct from read-only or preview siblings like `changes` and `plan`.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives explicit guidance on when to use `plan` before undoing, warns that 'There is no redo,' and instructs the agent to preview with `plan` for `steps` above 1. It also tells the user where to find undo depth via `status`, and clarifies that `migrate_project` is handled differently because it keeps its own backup.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

unspoken_addA
Idempotent

Mark a word the transcript holds and the recording never said.

Whisper transcribes straight across a retake splice and emits words from both takes interleaved, so words appear in the index that nobody said. They are in the transcript and nowhere else — not the audio, not the render — so captions draw them and verify expects them.

This writes a mark beside the transcript and never touches the transcript itself: word indices must not renumber, or every cue pointing at one would move. Captions, caption_view and verify all stop expecting the word; no audio, timing or shot changes, because the seconds around it are the take that was kept. Echoes the word it resolved to, plus three either side.

Addressed by word_index or phrase — but unlike cue_add, a phrase resolving to more than one word is refused rather than bound to an edge: unspoken addresses exactly one word, and picking a side of a wider match would silently mark the wrong one half the time. Narrow the phrase, or pass occurrence= if it is disambiguation rather than width.

Prefer unspoken_detect to find them: it is evidence rather than reading, and reading for sense provably misses the grammatical ones.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
afterNoA forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start.
phraseNoAddress it by wording instead — but unlike `cue_add`, a phrase matching more than one word is refused rather than bound to an edge: a mark addresses exactly one word.
clip_idYesThe transcript holding the word.
occurrenceNoDisambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at.
word_indexNoThe word to mark. Give this or `phrase`.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.9/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The description details side effects beyond the annotations: it 'writes a mark beside the transcript and never touches the transcript itself,' ensuring word indices don't renumber, and that captions, caption_view, and verify stop expecting the word. It also clarifies no audio/timing/shot changes occur. Since annotations only state readOnlyHint=false and idempotentHint=true, this adds substantial behavioral context without contradicting any structured hint.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Every sentence earns its place: purpose, cause, side effects, addressing semantics, and guidance are organized logically. It is front-loaded with the core action, then expands into rationale and constraints. Despite its length, there is zero filler—each paragraph serves a distinct purpose.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a tool with six parameters and an output schema, the description covers all essential aspects: how to address a word (index or phrase), disambiguation rules, side effects on downstream systems, and the recommended sibling tool. It also mentions the refusal behavior for ambiguous phrases, which is critical for correct usage. Nothing an agent needs to invoke it correctly is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3. The description adds value by explaining the behavioral difference between word_index and phrase (refusal on multi-word matches), the meaning of occurrence as 1-based disambiguation, and the interaction with `after`. While not strictly necessary given the schema, these clarifications improve selection and invocation confidence.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a precise verb and resource: 'Mark a word the transcript holds and the recording never said.' It immediately explains the root cause (Whisper splicing artifacts) and contrasts with siblings like cue_add and unspoken_detect, making the tool's unique role unmistakable. An agent can instantly distinguish it from similar editing tools.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description explicitly directs users to 'Prefer `unspoken_detect` to find them' and explains why reading is insufficient. It also contrasts with cue_add, stating that ambiguous phrases are refused rather than bound to an edge, and clarifies when to narrow or use occurrence. This gives clear when-to-use and when-not-to-use guidance with concrete alternatives.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

unspoken_detectA
Destructive

Propose the words a render's own transcription says were never spoken.

Candidates come from two mechanisms and one witness decides both. A seam is where whisper read across a splice and invented a word; a fragment is where a cut left a sliver of a real one, which draws as a whole word on screen and is inaudible. The witness is the render: the candidate's word is counted in the timeline over a short window and in the render's own transcription over the same seconds, and it is proposed only where the timeline has more of them than the render heard. Counted rather than looked up because the inventions are function words — asking whether the render says "the" near here answers yes off the real one beside it.

apply=False by default, like reframe_detect: this changes what a caption says, and a wrong mark deletes a real word from every check proofcut has. Read the echoes first.

transcript_path takes an existing transcription of the render, which is what verify leaves in cache/verify/. Pass it explicitly — it is never found automatically, because a re-render under the same filename would otherwise be judged against the previous render's audio.

ParametersJSON Schema
NameRequiredDescriptionDefault
padNoWiden the window each candidate is counted in, in seconds.
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
applyNoMark the proposals. Off by default, like `reframe_detect`: a wrong mark deletes a real word from every check proofcut has, so read the echoes first.
modelNoThe whisper model to transcribe the render with, when no `transcript_path` is given.
renderYesThe rendered file to judge against — the witness. A word is proposed only where the timeline holds more of it over a span than the render's own transcription heard.
clip_idNoLimit the scan to one transcript.
languageNoForce a language code for that transcription.
transcript_pathNoAn existing transcription of `render`, which is what `verify` leaves in `cache/verify/`. It is never found automatically: a re-render under the same filename would otherwise be judged against the previous render's audio.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.4/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already flag `destructiveHint: true`, and the description adds critical context beyond that: a wrong mark "deletes a real word from every check proofcut has" and therefore the agent should read echoes first. It also discloses that `transcript_path` is never found automatically to avoid judging a re-render by previous audio, which is exactly the kind of behavioral nuance annotations cannot convey.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but well structured: purpose first, then mechanism, safety, and the key parameter caution. Every paragraph adds useful context, though the algorithm explanation (seams, fragments, counting rationale) is more elaborate than strictly necessary for invocation. It is not bloated, but it earns a 4 rather than a 5 because of that extra explanatory weight.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a complex 8-parameter tool with an output schema, the description covers purpose, algorithm, safety, prerequisites, and the one parameter behavior that would otherwise cause subtle errors. The output schema handles return-value details, and the schema covers the remaining parameters. Nothing essential is missing for an agent to call this correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3 even without parameter details in the description. The description does reinforce the meaning of `apply`, `transcript_path`, and the counting window, but it mostly restates what the schema already says rather than adding new parameter-level semantics.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: "Propose the words a render's own transcription says were never spoken." It then explains the two detection mechanisms (seam and fragment) and clearly separates proposing from applying by noting `apply=False` by default. This distinguishes it from manual siblings like `unspoken_add`/`unspoken_rm` without needing to inspect them.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives strong operational guidance: pass `transcript_path` explicitly from `verify`'s cache, read the echoes first, and keep `apply=False` unless sure. It names `reframe_detect` as a sibling with the same safety default. It does not explicitly say when to prefer `unspoken_detect` over manual unspoken tools, but the propose-vs-apply distinction implies it.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

unspoken_lsA
Read-onlyIdempotent

Every word marked never-spoken, with what the transcript says now.

Read-only. stale is a mark whose recorded text and current text disagree — the transcript was re-attached under it. A stale mark is never applied, so re-transcribing surfaces as a list to re-check rather than as words disappearing from a caption file.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.1/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already establish read-only/idempotent/non-destructive behavior, so the description adds meaningful value by defining the 'stale' state and its consequence: stale marks are never applied, and re-transcriptions appear as a list to re-check. This goes beyond the structured hints without contradicting them.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is compact and front-loaded: a one-line purpose, followed by a pithy, high-value explanation of stale marks. No filler or repetition of schema content.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a read-only listing tool with an output schema, complete parameter documentation, and annotations covering safety, the description provides the one missing piece of domain behavior — the stale-mark distinction — and is therefore sufficient for correct invocation.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Only one parameter, path, is fully documented in the schema (100% coverage), including bound/unbound server behavior. The description adds no path-specific information, which is fine because the schema carries the full burden.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The opening sentence 'Every word marked never-spoken, with what the transcript says now' states the operation as a listing of a specific resource (unspoken marks) and the key data returned. It is clearly distinct from sibling unspoken_add/rm/detect, which manage or detect marks.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Usage is implied rather than explicitly stated. The stale-mark explanation gives one concrete scenario — after re-transcribing, use this to re-check marks — but the description never says when to prefer it over unspoken_detect or a general transcript tool.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

unspoken_rmA
Destructive

Unmark a word unspoken_add marked, putting it back into captions and verify.

Address it by word_index, or by a phrase resolving to exactly one word. Refuses a word that is not marked. The transcript file is never edited either way — a mark is a manifest entry — so no cue or caption renumbers. unspoken_ls lists the marks; undo restores one.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
afterNoA forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start.
phraseNoAddress it by wording instead; it has to resolve to exactly one word.
clip_idYesThe transcript holding the marked word.
occurrenceNoDisambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at.
word_indexNoThe marked word. Give this or `phrase`.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.1/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations mark this as destructive (destructiveHint=true) and not read-only. The description adds key nuance: the transcript file is never edited, only a manifest entry changes, so no renumbering occurs. It also discloses the refusal behavior for unmarked words. This adds value beyond the annotations and clarifies the actual side effects.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is composed of three sentences, each carrying distinct information: the core action, the addressing method and refusal, and the side-effect transparency plus sibling pointers. It is front-loaded with the primary purpose and avoids fluff. Slightly longer than minimal but well-organized.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a tool with six parameters and an output schema, the description covers the essential behavioral aspects: what it does, how to address, refusal, side effects, and related tools. It doesn't repeat parameter details already in the schema, and the output format is presumably covered by the output schema. It is complete enough for an agent to invoke correctly.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The input schema already describes all six parameters in detail (100% coverage), including word_index, phrase, clip_id, after, occurrence, and path. The description reiterates that addressing is by word_index or a phrase resolving to exactly one word, but this is already in the schema. It does not add new parameter-specific semantics, so the baseline of 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific action ('Unmark a word'), names the resource type (word marked by unspoken_add), and gives the effect (putting it back into captions and verify). It explicitly references the sibling unspoken_add, which differentiates it clearly from other tools like unspoken_ls and undo.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives clear addressing options (word_index or phrase) and notes the refusal of unmarked words. It mentions alternatives: unspoken_ls lists marks and undo restores one, which helps an agent choose between them. However, it doesn't explicitly state conditions like 'use when you want to remove a mark' vs 'use undo to revert a removal', but the context is sufficient.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

verifyA
Read-onlyIdempotent

Transcribe a finished render and diff it against what the timeline says.

Run this after rendering, before calling an edit done. It transcribes the render with whisper and compares that word sequence to the one the timeline should play, which is the only check that catches a retake still in the picture: whisper collapses an immediate repeat into a single utterance, so a doubled phrase can be invisible in the source transcript and still be in the render.

Read repeated first — an entry there is a phrase the render plays more times than the timeline expects, i.e. a surviving retake, with the heard word index to look at. dropped is the opposite: words the timeline expects that the render never says, usually a cut that reached too far.

A clean single-pass result is not proof. This check has a known blind spot: the render's transcript is itself one whisper pass, which collapses a repeat the same way the source transcript did — three retakes survived a correct run of it on a real video. Set windowed=True to transcribe in short overlapping windows instead, which is what found them. It costs one whisper run over 2x the audio and uses a deliberately smaller model, so run the default first and escalate to it before calling an edit finished.

loud_gaps comes back either way and trusts no transcript: it measures the render's own energy and reports holes in the heard word map that hold sound anyway. An entry is a place to listen, not a verdict — a music bed or an attenuated noise can produce one. Read speech_db/threshold_db beside it.

similarity around 0.97 is normal on a clean render — whisper spells its own output differently on a second pass ("whodunit" / "who done it", "4" / "four"). Treat it as triage; diff is the artifact. Transcription takes minutes on a long render, and the result is cached under cache/verify/ and reported as heard_transcript — pass it back as transcript_path to re-diff without re-transcribing.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
modelNoThe whisper model for the single-pass transcription.
renderYesThe finished render to transcribe and diff against the timeline. The expected words include a sound's or an inset's own when its clip has a transcript (`placed_audio`) — a narrator take placed as a sound is the film's voice. A voice sound (`ducks`) with no transcript is listed in `voice_sounds_untranscribed` and not checked: transcribe it first.
windowNoLength of each window in the windowed pass, in seconds.
clip_idNoDiff against one transcript's expected words rather than all of them.
overlapNoHow far each window overlaps the one before, in seconds.
languageNoForce a language code for it.
windowedNoTranscribe in short overlapping windows instead of one pass. **A clean single-pass result is not proof** — one pass collapses an immediate repeat the same way the source transcript did, and three surviving retakes passed a correct single-pass run on a real video. It costs a run over twice the audio and a smaller model.
transcript_pathNoAn existing transcription of `render` — what a previous run cached and reported as `heard_transcript`. Pass it back to re-diff without spending the minutes again.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.5/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations declare readOnlyHint=true and idempotentHint=true, and the description richly complements them: it discloses the caching behavior (cache/verify/, reported as heard_transcript), the cost profile (minutes per run, windowed costs 2x audio with a smaller model), the known blind spot (single-pass collapses repeats, three retakes survived a correct run), and interpretive context (similarity ~0.97 is normal; loud_gaps is a listen-point, not a verdict). This goes well beyond what annotations convey.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness3/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Well-structured with front-loaded purpose, bolded warnings, and clearly separated paragraphs, and nearly every sentence carries behavioral value. However, it is long for an MCP description and carries some redundancy — the windowed blind-spot explanation appears in both the description and the windowed parameter's schema text, and the loud_gaps triage guidance repeats the similarity triage point. Tightening would help.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a 9-parameter, complex workflow tool, the description is essentially complete: it covers the triggering workflow, escalation strategy, output interpretation (repeated, dropped, loud_gaps, similarity, diff), the blind-spot caveat, and the caching/transcript_path round-trip. An output schema exists, so return values need not be spelled out, and the description still explains the key result fields an agent must act on.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so the baseline is 3. The description adds real value on top: it explains the purpose of transcript_path via the caching mechanism, clarifies that render includes placed_audio transcripts and untranscribed voice sounds, and reinforces windowed's escalation semantics. Not every parameter gets prose (model, window, overlap, language are left to the schema), but the schema itself documents them fully.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

Opens with a precise verb+resource+scope statement: 'Transcribe a finished render and diff it against what the timeline says.' It states the exact trigger condition (after rendering, before edit done) and the specific failure it catches (a surviving retake), which clearly distinguishes it from siblings like transcribe and transcript_checks without needing to open their schemas.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Explicitly states when to run it ('Run this after rendering, before calling an edit done') and gives a clear escalation path ('run the default first and escalate to it before calling an edit finished'). It also warns against false confidence from a clean result. It does not name the sibling tools (transcribe, hear, transcript_checks) that an agent might confuse it with, but the workflow positioning is clear enough to route the agent correctly.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

vo_extendA
Destructive

Open a gap in clip_id's track for material the recording never had.

The one tool allowed to grow the edit rather than cut it: a real hold in the VO, e.g. to let a line the footage carries play under it. Not the end card (tail), and not restore, which only brings back cut source.

Addressed by word_index or phrase — the last word before the gap, which must be on the timeline — for seconds. The stretch is a real silent WAV, registered like any clip; a second call at the same seconds reuses it.

Read covered_by. build_shots runs each shot to the next cue, so whatever picture was playing freezes across the hold by default, with shots_error, verify and check_frames all staying clean. It names every shot the gap now overlaps ([] with no cue table at all).

Two consequences are permanent once a hold lands: restore refuses across the seam, and export always goes through the MLT writer. plan=True reports covered_by without writing; its hold_clip_id is a placeholder.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
afterNoA forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start.
phraseNoAddress it by wording instead. A phrase binds to its **last** word here, which is this tool's own meaning: the last word before the gap.
clip_idYesThe track the gap opens in — the VO.
secondsNoHow long the hold runs. An editorial call this makes no attempt to derive.
occurrenceNoDisambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at.
word_indexNoThe last word **before** the gap; the hold opens immediately after that word's own end. It has to be on the timeline: an index naming cut material is refused rather than guessed at.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.8/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already mark destructiveHint=true, but the description adds crucial consequences: `restore` refuses across the seam, export always goes through the MLT writer, a second call at the same `seconds` reuses the WAV, and `build_shots` interaction is explained. This far exceeds what annotations alone provide.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is long but every sentence carries essential information. It front-loads the tool's purpose and exclusions, then uses bolded headings for parameters and consequences, making it scannable despite density.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's complexity and destructive nature, the description covers addressing modes (word_index/phrase), duration, plan mode, permanent effects, and interaction with `build_shots`. An output schema exists, so return values need not be detailed; nothing critical for correct invocation is missing.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters5/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Despite 100% schema coverage, the description enriches parameter meaning: `word_index` is 'the last word before the gap' and must be on the timeline, `phrase` binds to its last word, `occurrence` is 1-based and ambiguous phrases are refused, and `plan=True` reports without writing. This is substantial added value beyond the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

Opens with a specific verb and resource: 'Open a gap in `clip_id`'s track' for material the recording never had. It also explicitly differentiates itself from `tail` and `restore`, making the tool's unique role clear.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description states clear exclusions ('Not the end card (`tail`), and not `restore`') and gives context ('real hold' in the VO to let footage play under). It doesn't explicitly list every alternative among the `hold_*` siblings, but it provides enough direction for an agent to distinguish this tool.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

vo_synthA
Destructive

Say text in a cloned voice — render several seeds, rank them, read the winner back.

Zero-shot Qwen3-TTS from a ≈19s reference clip (voice); there is no built-in voice. Seeds seed .. seed+candidates-1 render in one process, each with sim (speaker-embedding likeness to the reference — a real take ≈0.99, a 3-semitone shift ≈0.96) and spread (voiced pitch movement). chosen is the best sim less a flatness penalty, since likeness alone keeps the flattest read. A render that hit max_seconds is capped and never wins while an uncapped one exists.

The winner is read back through whisper and heard/wer reported — a clone that sounds right and says the wrong words is the failure nothing else sees. A report, never a gate.

Renders are cached under cache/synth/, so a repeat spends no GPU. The splice is not cached: with clip_id + word_index the winner is registered and spliced in after that word through vo_extend's mechanism (melt routing, restore refusing across the seam, a covered_by report), and calling again splices a second time — check the timeline or undo rather than re-calling. plan=True reports the ranking and splice preview from cached renders only, and says rendered: False rather than spending the GPU.

ParametersJSON Schema
NameRequiredDescriptionDefault
pathNoThe project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing.
planNoResolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it.
seedNoFirst seed of the range; seeds `seed .. seed+candidates-1` render in one process. A new range renders only what the cache lacks.
textYesWhat the voice says. It is respelled first through the project's `lexicon.json` `say` folds, if one exists — the fix for a mispronounced name.
voiceNoA directory holding `ref.wav` + `ref.txt`, the ≈19s reference the clone is zero-shot from. Unset, `$PROOFCUT_TTS_VOICE`. There is no built-in voice, and none ships in the repo: a voice is somebody's recorded speech.
clip_idNoWith `word_index`, the track to splice the winner into. Omitted, nothing is spliced and the renders are just ranked.
lexiconNoA `{"say": {…}, "hear": {…}}` file: `say` respells what the model is given, `hear` folds whisper's spelling back to the script's before the WER is scored. Defaults to the project's own `lexicon.json` if it has one.
readbackNoTranscribe the winner with whisper and report `heard`/`wer`. On by default: a clone that sounds right and says the wrong words is the failure nothing else sees. The numbers are a report, never a gate.
candidatesNoHow many seeds to render and rank. Seed moves a render more than the reference does, which is why this ranks rather than renders once.
flat_floorNoBelow this much voiced pitch movement (semitones) a render starts paying the flatness penalty. Likeness alone keeps the flattest read, because sims in one pool differ by thousandths while spread differs by semitones.
word_indexNoThe word to splice the winner in right after, through `vo_extend`'s own mechanism — so the same one-way consequences follow (melt routing, `restore` refusing across the seam).
flat_weightNoHow much likeness to subtract per semitone of flatness under the floor. 0 restores likeness-only ranking.
max_secondsNoLength cap per render. One that hits it is reported `capped` and never wins while an uncapped one exists — a 21s reference once ran every render to 655s.

Output Schema

ParametersJSON Schema
NameRequiredDescription

No output parameters

TDQS

A4.5/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare destructiveHint=true, and the description richly confirms and extends this: it discloses the non-cached splice with double-splice risk, the caching under `cache/synth/` that avoids GPU on repeat, the ranking rule ('best `sim` less a flatness penalty'), the `capped`-never-wins rule, and the readback as 'a report, never a gate.' It even explains the failure mode a clone that sounds right but says the wrong words. This is far beyond what annotations provide and contradicts nothing.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness3/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is front-loaded with the core purpose in the first sentence and organized into logical paragraphs (ranking logic, readback, caching/splice warning, plan behavior). However, it is quite long and dense for a description, requiring sustained reading. For a 13-parameter tool much of the length is earned, but it could be tightened without losing essential behavioral disclosure.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

An output schema exists, so return values need not be explained. For a destructive, 13-parameter tool with splicing side effects, the description covers everything an agent needs: caching, splice non-idempotency, ranking rules, capped renders, readback semantics, and the `plan` path. The one reliance on `vo_extend`'s documented mechanism is a reasonable pointer rather than a gap. Complete for the tool's complexity.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 100%, so baseline is 3. The description goes well beyond the schema by explaining the meaning of core outputs and ranking terms (`sim`, `spread`, `chosen`, `capped`) and the rationale behind `flat_floor`/`flat_weight` ('likeness alone keeps the flattest read, because sims in one pool differ by thousandths while spread differs by semitones'). It also clarifies `max_seconds` with a concrete anecdote. This adds real value over the schema's per-parameter descriptions.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The first sentence is a specific verb+resource: 'Say `text` in a cloned voice — render several seeds, rank them, read the winner back.' This states exactly what the tool does and clearly separates it from its sibling `vo_extend` (splicing/extension) and `transcribe`/`hear` (readback-only). An agent can tell what this tool is for immediately.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives strong workflow guidance: it explains when to use `plan=True` (report from cached renders, spend no GPU), and explicitly warns against re-calling the splice ('calling again splices a second time — check the timeline or `undo` rather than re-calling'). It references `vo_extend`'s mechanism as an alternative pathway for splicing. It lacks an explicit when-not-to-use statement versus a specific sibling, but the workflow context is clear.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

Tool Schema Changelog

Recent tool additions, removals, and schema changes observed during successful MCP inspections.

  1. 27 tool updatesv0.43.0
    • Addedcaption_span_add
    • Addedcaption_span_ls
    • Addedcaption_span_rm
    • Changedcaption_style4 fields changed
      • changedInput schema / properties / preset / description
        Previous value: -"The base look: `clean`, `karaoke` (per-word highlight) or `boxed`. Everything else overrides one of its fields, and only the overrides are stored."New value: +"The base look: `clean`, `karaoke` (per-word highlight), `reveal` (words land mid-frame, fading in as spoken) or `boxed`. Everything else overrides one of its fields, and only the overrides are stored."
      • addedInput schema / properties / reveal
        Added value: +{
        +  "default": null,
        +  "description": "How each word arrives as it is spoken: `fade`, `blur` (blurs and fades in; the outline returns at the end), or `none`. The line is laid out whole from the start, so nothing moves.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
      • addedInput schema / properties / reveal_blur
        Added value: +{
        +  "default": null,
        +  "description": "How blurred a word starts under `reveal=blur` (ASS `\\blur`; a gaussian of 0.85 x this in canvas pixels). Default 6.",
        +  "type": [
        +    "number",
        +    "null"
        +  ]
        +}
      • addedInput schema / properties / reveal_ms
        Added value: +{
        +  "default": null,
        +  "description": "How long a word's reveal takes, in milliseconds. Default 150. Needs a reveal.",
        +  "type": [
        +    "integer",
        +    "null"
        +  ]
        +}
    • Addedcaption_style_library
    • Addedcaption_style_load
    • Addedcaption_style_save
    • Changedcue_add6 fields changed
      • addedInput schema / properties / dissolve
        Added value: +{
        +  "default": null,
        +  "description": "Crossfade into this cue over this many seconds: the incoming shot's frames before its in-point fade in, reaching the shot on the cue's word. Where the clip has none (an unpinned first use), the outgoing shot fades out from the word instead. ",
        +  "type": [
        +    "number",
        +    "null"
        +  ]
        +}
      • addedInput schema / properties / dissolve_ease
        Added value: +{
        +  "default": null,
        +  "description": "The crossfade's curve: linear (the default), ease, ease-in or ease-out.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
      • addedInput schema / properties / punch
        Added value: +{
        +  "default": null,
        +  "description": "A scale punch from the cut, about the canvas centre: 1.1 zooms in 10%. Not with a dissolve on the same cue. ",
        +  "type": [
        +    "number",
        +    "null"
        +  ]
        +}
      • addedInput schema / properties / punch_ease
        Added value: +{
        +  "default": null,
        +  "description": "The punch's curve. Default ease-out.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
      • addedInput schema / properties / punch_mode
        Added value: +{
        +  "default": null,
        +  "description": "`in` (default) zooms to `punch` and holds for the shot; `settle` starts there and eases back.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
      • addedInput schema / properties / punch_seconds
        Added value: +{
        +  "default": null,
        +  "description": "How long the punch moves. Default 0.2.",
        +  "type": [
        +    "number",
        +    "null"
        +  ]
        +}
    • Addedcue_set
    • Addedgraphic_capture
    • Addedgraphic_edit
    • Addedgraphic_library
    • Addedgraphic_load
    • Addedgraphic_ls
    • Addedgraphic_new
    • Addedgraphic_save
    • Addedgraphic_sheet
    • Addedgraphic_templates
    • Addedimage_add
    • Addedimage_ls
    • Addedimage_rm
    • Addedlexicon_add
    • Addedlexicon_ls
    • Addedlexicon_rm
    • Changedoverlay_add13 fields changed
      • addedInput schema / properties / card / default
        Added value: +null
      • changedInput schema / properties / card / description
        Previous value: -"The overlay card to place: one made by card_new from an overlay template (`lowerthird`, `scrim`). An ordinary card is opaque and is refused."New value: +"The overlay card to place: one made by card_new from an overlay template (`lowerthird`, `scrim`), by name or as `card:NAME`. An ordinary card is opaque and is refused. One of card, graphic or image; each takes its own prefix."
      • changedInput schema / properties / card / type
        Previous value: -"string"New value: +[
        +  "string",
        +  "null"
        +]
      • changedInput schema / properties / enter / description
        Previous value: -"How it appears: `rise` (moves up while fading in), `fade`, or `none` (a cut). Default rise."New value: +"How it appears: `rise` (moves up while fading in), `fade`, `pop` (scales up past full size and settles), `slide-left`/`slide-right`/`slide-top`/`slide-bottom` (in from that edge), or `none` (a cut). Default rise for a card, pop for an image, none for a graphic."
      • addedInput schema / properties / graphic
        Added value: +{
        +  "default": null,
        +  "description": "An animated graphic (graphic_new) to place instead of a card. Its intro plays from the start, its outro ends at the end, and its hold fills the span between; a span shorter than intro plus outro is refused. It enters and leaves with no motion of its own unless enter/leave say so.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
      • addedInput schema / properties / image
        Added value: +{
        +  "default": null,
        +  "description": "A still (image_add) to place as a sticker, instead of a card or graphic. It pops in and fades out unless enter/leave say otherwise.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
      • changedInput schema / properties / leave / description
        Previous value: -"How it goes: `fade`, `rise` (moves down while fading out), or `none`. Default fade."New value: +"How it goes: `fade`, `rise` (moves down while fading out), `pop`, a `slide-` out to that edge, or `none`. Default fade for a card or image, none for a graphic."
      • addedInput schema / properties / rotate
        Added value: +{
        +  "default": null,
        +  "description": "Degrees to turn a sticker, clockwise; negative turns it the other way.",
        +  "type": [
        +    "number",
        +    "null"
        +  ]
        +}
      • addedInput schema / properties / style
        Added value: +{
        +  "default": null,
        +  "description": "`plain`, or `photo`: a white border and a soft shadow, a photo card.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
      • addedInput schema / properties / width
        Added value: +{
        +  "default": null,
        +  "description": "A sticker's width, as a fraction of the frame's width. Default 0.3.",
        +  "type": [
        +    "number",
        +    "null"
        +  ]
        +}
      • addedInput schema / properties / x
        Added value: +{
        +  "default": null,
        +  "description": "A sticker's centre across the frame: 0 is the left edge, 1 the right. Default 0.5.",
        +  "type": [
        +    "number",
        +    "null"
        +  ]
        +}
      • addedInput schema / properties / y
        Added value: +{
        +  "default": null,
        +  "description": "A sticker's centre down the frame: 0 is the top, 1 the bottom. Default 0.5.",
        +  "type": [
        +    "number",
        +    "null"
        +  ]
        +}
      • changedInput schema / required
        Previous value: -[
        -  "card",
        -  "clip_id"
        -]New value: +[
        +  "clip_id"
        +]
    • Changedseed_timeline3 fields changed
      • addedInput schema / properties / clip_id / anyOf
        Added value: +[
        +  {
        +    "type": "string"
        +  },
        +  {
        +    "items": {
        +      "type": "string"
        +    },
        +    "type": "array"
        +  }
        +]
      • changedInput schema / properties / clip_id / description
        Previous value: -"The clip to lay down as the timeline."New value: +"The clip to lay down as the timeline, or a list of recordings laid end to end in that order. Several must all have picture."
      • removedInput schema / properties / clip_id / type
        Removed value: -"string"
    • Addedsplit
  2. 1 tool updatev0.38.0
    • Changedverify1 field changed
      • changedInput schema / properties / render / description
        Previous value: -"The finished render to transcribe and diff against the timeline."New value: +"The finished render to transcribe and diff against the timeline. The expected words include a sound's or an inset's own when its clip has a transcript (`placed_audio`) — a narrator take placed as a sound is the film's voice. A voice sound (`ducks`) with no transcript is listed in `voice_sounds_untranscribed` and not checked: transcribe it first."
  3. 11 tool updatesv0.37.0
    • Changedadd_captions3 fields changed
      • changedInput schema / properties / burn / description
        Previous value: -"Burn the captions into this video with ffmpeg instead of writing a sidecar. It must be a render of **this** timeline — against any other video the timings will not line up. `export --render` does not burn captions, and nothing else reports a render that was made without them."New value: +"Also burn the captions into this video with ffmpeg; the sidecar is still written to `output`. It must be a render of **this** timeline — against any other video the timings will not line up. `export --render` does not burn captions, and nothing else reports a render that was made without them."
      • changedInput schema / properties / burn_output / description
        Previous value: -"Where the burned video goes. Unset, it is derived from `burn`'s own name."New value: +"Where the burned video goes, when `burn` is set. Unset, it is derived from `burn`'s own name in the project's renders folder."
      • changedInput schema / properties / output / description
        Previous value: -"Where to write the `.ass` sidecar, or the burned video under `burn`."New value: +"Where to write the `.ass` sidecar — always, burning or not. Never a video path: a media suffix is refused. The burned video goes to `burn_output`."
    • Changedcue_add1 field changed
      • addedInput schema / properties / event
        Added value: +{
        +  "default": null,
        +  "description": "Start the picture on this event of clip_id instead of a word: `name`, or `name#k` when the name repeats — a screen recording's logged moments, for a clip with no transcript. Not with word_index or phrase.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
    • Changedcue_rm1 field changed
      • addedInput schema / properties / event
        Added value: +{
        +  "default": null,
        +  "description": "The event the cue sits on, spelled as `cue_add` was given it.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
    • Addeddissolve
    • Addedfollow
    • Changedinset_add4 fields changed
      • changedInput schema / properties / gain_db / default
        Previous value: -0New value: +null
      • changedInput schema / properties / gain_db / description
        Previous value: -"The asset's own audio level in dB. Default 0. The music bed goes out under it."New value: +"The asset's own audio level in dB. Default 0. The music bed goes out under it, or dips under it when the bed has a duck."
      • changedInput schema / properties / gain_db / type
        Previous value: -"number"New value: +[
        +  "number",
        +  "null"
        +]
      • addedInput schema / properties / level
        Added value: +{
        +  "default": null,
        +  "description": "'speech' measures the span the inset plays, once, and records the gain_db that brings its speech to -18 dBFS RMS, the launch clip's film level. Not with gain_db.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
    • Changedmusic9 fields changed
      • addedInput schema / properties / clear_loudness
        Added value: +{
        +  "default": false,
        +  "description": "Drop the `loudness` level.",
        +  "type": "boolean"
        +}
      • changedInput schema / properties / clip_id / description
        Previous value: -"The transcript the bed's word indices address — the VO, not the music."New value: +"The clip whose words (or events) the bed addresses — the VO, not the music."
      • changedInput schema / properties / duck / description
        Previous value: -"Pull the bed this many dB down while the voice is speaking and let it back up in the pauses. It is keyed off the timeline's own audio at export rather than the transcript's word timings, which were measured against a bed recovered from a real render and beaten: 2.72 dB off for the audio gate against a word-span duck's 3.39."New value: +"Pull the bed this many dB down while the voice is speaking and let it back up in the pauses. It is keyed off the timeline's own audio at export rather than the transcript's word timings, which were measured against a bed recovered from a real render and beaten: 2.72 dB off for the audio gate against a word-span duck's 3.39. It also hears audible insets and sounds placed with `ducks`."
      • addedInput schema / properties / event
        Added value: +{
        +  "default": null,
        +  "description": "Start the bed on this event of clip_id instead of a word: `name`, or `name#k` when the name repeats. Replaces a start word.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
      • addedInput schema / properties / loudness
        Added value: +{
        +  "default": null,
        +  "description": "Level the whole bed to this many LUFS, measured — for a film with no voice for `under` to sit below, such as a screen recording. Setting it drops `under`, and `under` drops it. The launch clip's approved bed reads -23.3.",
        +  "type": [
        +    "number",
        +    "null"
        +  ]
        +}
      • addedInput schema / properties / over_tail
        Added value: +{
        +  "default": null,
        +  "description": "True runs a bed with no end boundary on under the tail's card, so the card is not silent and `fade_out` ends with it. False ends it with the edit, the default.",
        +  "type": [
        +    "boolean",
        +    "null"
        +  ]
        +}
      • changedInput schema / properties / passages / description
        Previous value: -"Replace the list of passages after the bed's own asset: each `{asset, word_index_start | phrase_start, src_in?, crossfade?, rotate?}`. `[]` clears them."New value: +"Replace the list of passages after the bed's own asset: each `{asset, word_index_start | phrase_start | event, src_in?, crossfade?, rotate?}`. `[]` clears them."
      • addedInput schema / properties / until_event
        Added value: +{
        +  "default": null,
        +  "description": "End the bed on this event of clip_id. Replaces an end word; `clear_end` drops it.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
      • changedInput schema / properties / word_index_end / description
        Previous value: -"Where the bed goes out. Unset means *to the end of the edit*, so a tail holds over silence."New value: +"Where the bed goes out. Unset means *to the end of the edit*, so a tail holds over silence unless `over_tail`."
    • Changedreview_add1 field changed
      • addedInput schema / properties / about
        Added value: +{
        +  "default": null,
        +  "description": "One plain line the served page prints under the name, saying what this item is (how it was made, what differs) — a reviewer judges nothing they cannot tell apart.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
    • Changedsound_add3 fields changed
      • addedInput schema / properties / ducks
        Added value: +{
        +  "default": false,
        +  "description": "The music bed's duck hears this sound as it hears the voice: set it for a narrator take or a line of dialogue placed as a sound, never for clicks. Only matters when the bed has a duck.",
        +  "type": "boolean"
        +}
      • addedInput schema / properties / src_in
        Added value: +{
        +  "default": null,
        +  "description": "Seconds into each asset where the sound starts. With src_out, plays one line of a long take, and the 30 s cap is on the trimmed part.",
        +  "type": [
        +    "number",
        +    "null"
        +  ]
        +}
      • addedInput schema / properties / src_out
        Added value: +{
        +  "default": null,
        +  "description": "Seconds into each asset where the sound stops. Unset plays to the file's end.",
        +  "type": [
        +    "number",
        +    "null"
        +  ]
        +}
    • Changedtail1 field changed
      • changedInput schema / properties / fade / description
        Previous value: -"Recorded and echoed, not yet drawn: this build cuts to the card hard, at `seconds`."New value: +"Seconds the card dissolves in over the film's last frames, opaque on the tail's first frame — overlapping the film, never added to `seconds`. 0 cuts to the card hard."
    • Changedundo2 fields changed
      • addedInput schema / properties / plan
        Added value: +{
        +  "default": false,
        +  "description": "Roll nothing back; return `changes`' account of what `steps` would undo. There is no redo, so read it before a `steps` above 1.",
        +  "type": "boolean"
        +}
      • addedInput schema / properties / steps
        Added value: +{
        +  "default": 1,
        +  "description": "How many mutations to roll back, from 1 (the last one) up to the undo depth; the same count `changes` takes. All or nothing: a number past the depth is refused, not walked as far as it goes.",
        +  "type": "integer"
        +}
  4. 16 tool updatesv0.36.0
    • Addedevents
    • Addedinset_add
    • Addedinset_ls
    • Addedinset_rm
    • Changedlocate1 field changed
      • addedInput schema / properties / event
        Added value: +{
        +  "default": null,
        +  "description": "Locate a named instant from `events`, as `name` or `name#k` (k counts that name's events from 0). Echoed with its neighbours.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
    • Addedoverlay_add
    • Addedoverlay_ls
    • Addedoverlay_rm
    • Changedreframe2 fields changed
      • addedInput schema / properties / ease
        Added value: +{
        +  "default": null,
        +  "description": "The curve of this window's slide: linear, ease (slow at both ends), ease-in or ease-out. Implies `interp`. The slide runs across the whole previous window, so to move between two moments put a window holding the old rect at the first.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
      • addedInput schema / properties / event
        Added value: +{
        +  "default": null,
        +  "description": "Start this window at a named instant from `events` (`name` or `name#k`) instead of `src_start`. The seconds it resolves to are stored; the listing says `event_moved` if the event later moves.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
    • Addedretime_add
    • Addedretime_ls
    • Addedretime_rm
    • Addedsound_add
    • Addedsound_generate
    • Addedsound_ls
    • Addedsound_rm
  5. 93 tool updatesv0.25.0
    • Changedadd_captions39 fields changed
      • removedInput schema / properties / burn / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / burn / description
        Added value: +"Burn the captions into this video with ffmpeg instead of writing a sidecar. It must be a render of **this** timeline — against any other video the timings will not line up. `export --render` does not burn captions, and nothing else reports a render that was made without them."
      • removedInput schema / properties / burn / title
        Removed value: -"Burn"
      • addedInput schema / properties / burn / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / burn_output / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / burn_output / description
        Added value: +"Where the burned video goes. Unset, it is derived from `burn`'s own name."
      • removedInput schema / properties / burn_output / title
        Removed value: -"Burn Output"
      • addedInput schema / properties / burn_output / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"Caption one transcript's words rather than every clip's."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / hold / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / hold / description
        Added value: +"How long a cue lingers after its last word, in seconds."
      • removedInput schema / properties / hold / title
        Removed value: -"Hold"
      • addedInput schema / properties / hold / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / max_duration / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / max_duration / description
        Added value: +"Longest a single cue stays on screen, in seconds."
      • removedInput schema / properties / max_duration / title
        Removed value: -"Max Duration"
      • addedInput schema / properties / max_duration / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / max_gap / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / max_gap / description
        Added value: +"Start a new cue when the silence between two words exceeds this many seconds."
      • removedInput schema / properties / max_gap / title
        Removed value: -"Max Gap"
      • addedInput schema / properties / max_gap / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / max_words / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / max_words / description
        Added value: +"Most words in one caption cue."
      • removedInput schema / properties / max_words / title
        Removed value: -"Max Words"
      • addedInput schema / properties / max_words / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • addedInput schema / properties / output / description
        Added value: +"Where to write the `.ass` sidecar, or the burned video under `burn`."
      • removedInput schema / properties / output / title
        Removed value: -"Output"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / preset / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / preset / description
        Added value: +"Override the project's base look for this one file — `clean`, `karaoke` or `boxed`. Nothing here is written back to the project."
      • removedInput schema / properties / preset / title
        Removed value: -"Preset"
      • addedInput schema / properties / preset / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"add_captionsArguments"
    • Changedassets5 fields changed
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"assetsArguments"
    • Changedattach_transcript9 fields changed
      • addedInput schema / properties / clip_id / description
        Added value: +"The clip this transcript belongs to. Its words become `(clip_id, word_index)`, which is how every cue, mark and caption addresses them afterwards."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / transcript_path / description
        Added value: +"The whisper JSON to ingest. It has to carry word-level timings — proofcut addresses words, not segments."
      • removedInput schema / properties / transcript_path / title
        Removed value: -"Transcript Path"
      • removedInput schema / title
        Removed value: -"attach_transcriptArguments"
    • Changedattenuate_noises19 fields changed
      • addedInput schema / properties / clip_id / description
        Added value: +"The clip to scan. It always reads that clip's **original** media, never a previous attenuated copy, so repeated calls never compound gain."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / confirm_suspect / description
        Added value: +"Go ahead even though a boundary word claims a suspect duration. Read the echoed words first — a suspect duration usually means whisper hid a retake inside that word, so the edge is not where it reads."
      • removedInput schema / properties / confirm_suspect / title
        Removed value: -"Confirm Suspect"
      • addedInput schema / properties / db / description
        Added value: +"How far to pull each qualifying event down, in dB. Negative is quieter."
      • removedInput schema / properties / db / title
        Removed value: -"Db"
      • addedInput schema / properties / max_event_seconds / description
        Added value: +"Longest an event may run and still qualify automatically. Anything longer is reported as `disqualified` and never written."
      • removedInput schema / properties / max_event_seconds / title
        Removed value: -"Max Event Seconds"
      • addedInput schema / properties / max_gap_seconds / description
        Added value: +"How wide the word-map gap around an event may be. A wide gap disqualifies even a very short event — that is the false-positive class this exists to prevent, speech sitting in a hole the transcript never wrote down."
      • removedInput schema / properties / max_gap_seconds / title
        Removed value: -"Max Gap Seconds"
      • addedInput schema / properties / pad / description
        Added value: +"Seconds added either side of each event before it is pulled down."
      • removedInput schema / properties / pad / title
        Removed value: -"Pad"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • removedInput schema / title
        Removed value: -"attenuate_noisesArguments"
    • Changedattribute_speakers23 fields changed
      • addedInput schema / properties / apply / description
        Added value: +"Write the labels onto the words. Off by default — it reports first, and applying keeps any label already on a word this refuses to call."
      • removedInput schema / properties / apply / title
        Removed value: -"Apply"
      • addedInput schema / properties / clip_id / description
        Added value: +"The co-hosted clip: one container, one mic per speaker, one transcript already attached."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • removedInput schema / properties / labels / anyOf
        Removed value: -[
        -  {
        -    "items": {
        -      "type": "string"
        -    },
        -    "type": "array"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / labels / description
        Added value: +"What to call each stream, in the same order — one per stream. Unset, `speaker1`, `speaker2`."
      • addedInput schema / properties / labels / items
        Added value: +{
        +  "type": "string"
        +}
      • removedInput schema / properties / labels / title
        Removed value: -"Labels"
      • addedInput schema / properties / labels / type
        Added value: +[
        +  "array",
        +  "null"
        +]
      • addedInput schema / properties / limit / description
        Added value: +"How many ambiguous spans to return; the reply also says how many there are in total."
      • removedInput schema / properties / limit / title
        Removed value: -"Limit"
      • addedInput schema / properties / margin_db / description
        Added value: +"How much louder one mic has to be to be believed, in dB. It reports a default and is not a threshold to trust: on words spoken over each other the rule is at chance, and anything under this margin comes back in `ambiguous_spans` to go and listen to."
      • removedInput schema / properties / margin_db / title
        Removed value: -"Margin Db"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / streams / anyOf
        Removed value: -[
        -  {
        -    "items": {
        -      "type": "integer"
        -    },
        -    "type": "array"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / streams / description
        Added value: +"Which audio streams the speakers are on, as ffmpeg audio ordinals (`[0, 1]`). Unset, the container's readable audio streams in order."
      • addedInput schema / properties / streams / items
        Added value: +{
        +  "type": "integer"
        +}
      • removedInput schema / properties / streams / title
        Removed value: -"Streams"
      • addedInput schema / properties / streams / type
        Added value: +[
        +  "array",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"attribute_speakersArguments"
    • Changedbroll_brief9 fields changed
      • removedInput schema / properties / fps / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / fps / description
        Added value: +"The frame grid the shot positions are projected on. Defaults to the rate `export` would use."
      • removedInput schema / properties / fps / title
        Removed value: -"Fps"
      • addedInput schema / properties / fps / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"broll_briefArguments"
    • Changedbuild_shots9 fields changed
      • removedInput schema / properties / fps / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / fps / description
        Added value: +"The frame grid to project onto. Unset, the project's timebase — which on an audio-only project is milliseconds rather than frames. Pass the rate `export` will use to see the frames the export actually cuts at."
      • removedInput schema / properties / fps / title
        Removed value: -"Fps"
      • addedInput schema / properties / fps / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"build_shotsArguments"
    • Changedcanvas13 fields changed
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • addedInput schema / properties / reset / description
        Added value: +"Drop the override and return to the footage-derived shape."
      • removedInput schema / properties / reset / title
        Removed value: -"Reset"
      • removedInput schema / properties / size / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / size / description
        Added value: +"`WIDTHxHEIGHT`, e.g. `1080x1920` for a vertical reel. Both edges must be even. Omit it to read what is in force plus the footage-derived shape it would fall back to."
      • removedInput schema / properties / size / title
        Removed value: -"Size"
      • addedInput schema / properties / size / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"canvasArguments"
    • Changedcaption_style81 fields changed
      • removedInput schema / properties / bold / anyOf
        Removed value: -[
        -  {
        -    "type": "boolean"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / bold / description
        Added value: +"Draw bold."
      • removedInput schema / properties / bold / title
        Removed value: -"Bold"
      • addedInput schema / properties / bold / type
        Added value: +[
        +  "boolean",
        +  "null"
        +]
      • removedInput schema / properties / box / anyOf
        Removed value: -[
        -  {
        -    "type": "boolean"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / box / description
        Added value: +"Draw an opaque box behind the words. It buys legibility over light footage — white captions over the film's own light cards measure 1.10:1 without one — and costs clean edges, since libass draws one box per override block."
      • removedInput schema / properties / box / title
        Removed value: -"Box"
      • addedInput schema / properties / box / type
        Added value: +[
        +  "boolean",
        +  "null"
        +]
      • removedInput schema / properties / box_colour / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / box_colour / description
        Added value: +"Colour of the box behind the type, when `box` is on."
      • removedInput schema / properties / box_colour / title
        Removed value: -"Box Colour"
      • addedInput schema / properties / box_colour / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / font / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / font / description
        Added value: +"Family name to draw with. Whether it actually draws is a different question from whether it is installed — `fonts` measures a render, and libass substitutes silently at exit 0."
      • removedInput schema / properties / font / title
        Removed value: -"Font"
      • addedInput schema / properties / font / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / highlight / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / highlight / description
        Added value: +"What a word turns as it is spoken. It only shows with `karaoke` on."
      • removedInput schema / properties / highlight / title
        Removed value: -"Highlight"
      • addedInput schema / properties / highlight / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / hold / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / hold / description
        Added value: +"How long a cue lingers after its last word, in seconds."
      • removedInput schema / properties / hold / title
        Removed value: -"Hold"
      • addedInput schema / properties / hold / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / karaoke / anyOf
        Removed value: -[
        -  {
        -    "type": "boolean"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / karaoke / description
        Added value: +"Fill each word as it is spoken. The fill is left-to-right within a line rather than a per-word step, which is what the grouping fields below shape."
      • removedInput schema / properties / karaoke / title
        Removed value: -"Karaoke"
      • addedInput schema / properties / karaoke / type
        Added value: +[
        +  "boolean",
        +  "null"
        +]
      • removedInput schema / properties / margin / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / margin / description
        Added value: +"Distance from the frame edge, in canvas pixels."
      • removedInput schema / properties / margin / title
        Removed value: -"Margin"
      • addedInput schema / properties / margin / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / max_duration / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / max_duration / description
        Added value: +"Longest a single cue stays on screen, in seconds."
      • removedInput schema / properties / max_duration / title
        Removed value: -"Max Duration"
      • addedInput schema / properties / max_duration / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / max_gap / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / max_gap / description
        Added value: +"Start a new cue when the silence between two words exceeds this many seconds."
      • removedInput schema / properties / max_gap / title
        Removed value: -"Max Gap"
      • addedInput schema / properties / max_gap / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / max_words / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / max_words / description
        Added value: +"Most words in one caption cue. Grouping is part of the look, which is why it is stored with it."
      • removedInput schema / properties / max_words / title
        Removed value: -"Max Words"
      • addedInput schema / properties / max_words / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / outline_colour / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / outline_colour / description
        Added value: +"Colour of the outline around the type."
      • removedInput schema / properties / outline_colour / title
        Removed value: -"Outline Colour"
      • addedInput schema / properties / outline_colour / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / outline_width / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / outline_width / description
        Added value: +"Outline thickness. With no box this is what holds the words apart from the picture."
      • removedInput schema / properties / outline_width / title
        Removed value: -"Outline Width"
      • addedInput schema / properties / outline_width / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • removedInput schema / properties / position / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / position / description
        Added value: +"Where captions sit, named: `bottom`, `top`, `top-right` and so on."
      • removedInput schema / properties / position / title
        Removed value: -"Position"
      • addedInput schema / properties / position / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / preset / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / preset / description
        Added value: +"The base look: `clean`, `karaoke` (per-word highlight) or `boxed`. Everything else overrides one of its fields, and only the overrides are stored."
      • removedInput schema / properties / preset / title
        Removed value: -"Preset"
      • addedInput schema / properties / preset / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / reset / description
        Added value: +"Drop every override first. `reset` together with `preset` starts clean from that preset."
      • removedInput schema / properties / reset / title
        Removed value: -"Reset"
      • removedInput schema / properties / shadow / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / shadow / description
        Added value: +"Drop-shadow distance."
      • removedInput schema / properties / shadow / title
        Removed value: -"Shadow"
      • addedInput schema / properties / shadow / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / size / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / size / description
        Added value: +"Type size, against the project's canvas as the reference frame."
      • removedInput schema / properties / size / title
        Removed value: -"Size"
      • addedInput schema / properties / size / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / text / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / text / description
        Added value: +"The word's own colour: `#rrggbb`, `#rrggbbaa`, a name, or an ASS `&H…` value. It comes back resolved, because ASS quotes colours backwards and alpha-inverted."
      • removedInput schema / properties / text / title
        Removed value: -"Text"
      • addedInput schema / properties / text / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"caption_styleArguments"
    • Changedcaption_view11 fields changed
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"Show one transcript's captions rather than every clip's."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / first
        Added value: +{
        +  "default": 0,
        +  "description": "Index of the first cue to return. 0 by default.",
        +  "type": "integer"
        +}
      • addedInput schema / properties / limit
        Added value: +{
        +  "default": 30,
        +  "description": "Most cues to return; `cues_next` says where to continue.",
        +  "type": "integer"
        +}
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"caption_viewArguments"
    • Changedcard_new21 fields changed
      • removedInput schema / properties / height / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / height / description
        Added value: +"Render height, given together with `width` or not at all."
      • removedInput schema / properties / height / title
        Removed value: -"Height"
      • addedInput schema / properties / height / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • addedInput schema / properties / name / description
        Added value: +"The `<name>` in `card:<name>` — the key a cue points at. The SVG and the PNG are both written under `assets/cards/`."
      • removedInput schema / properties / name / title
        Removed value: -"Name"
      • addedInput schema / properties / overwrite / description
        Added value: +"Redraw a card of this name that already exists. Refused without it, since a cue may already point at that card."
      • removedInput schema / properties / overwrite / title
        Removed value: -"Overwrite"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / slots / description
        Added value: +"The template's slots filled in, as text. A newline is a line break where the template takes several lines; ratings are numbers out of five, to the nearest half."
      • removedInput schema / properties / slots / title
        Removed value: -"Slots"
      • addedInput schema / properties / template / description
        Added value: +"Which template to fill; `card_templates` lists them with their slots. A per-aspect variant file is resolved from the canvas, never named here."
      • removedInput schema / properties / template / title
        Removed value: -"Template"
      • removedInput schema / properties / width / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / width / description
        Added value: +"Render width. **Leave it unset unless you mean something other than this film** — it defaults to the project's canvas, which is what stops a card pillarboxing inside the frame it was made for. Given at all, `height` must be too."
      • removedInput schema / properties / width / title
        Removed value: -"Width"
      • addedInput schema / properties / width / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"card_newArguments"
    • Changedcard_reauthor11 fields changed
      • removedInput schema / properties / name / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / name / description
        Added value: +"One card to redraw, whatever its canvas. Omit it to sweep every recorded card the canvas has left behind, plus any whose files have gone missing."
      • removedInput schema / properties / name / title
        Removed value: -"Name"
      • addedInput schema / properties / name / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • removedInput schema / title
        Removed value: -"card_reauthorArguments"
    • Changedcard_render15 fields changed
      • removedInput schema / properties / height / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / height / description
        Added value: +"Render height, given together with `width` or not at all."
      • removedInput schema / properties / height / title
        Removed value: -"Height"
      • addedInput schema / properties / height / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • addedInput schema / properties / name / description
        Added value: +"The card to rasterise: `assets/cards/<name>.svg` becomes the PNG that `card:<name>` resolves to."
      • removedInput schema / properties / name / title
        Removed value: -"Name"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / width / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / width / description
        Added value: +"Render width. The document is *drawn* at this scale rather than resampled, so text stays sharp, and it fits rather than distorts. Given together with `height` or not at all; omitted, the document renders at its own declared size."
      • removedInput schema / properties / width / title
        Removed value: -"Width"
      • addedInput schema / properties / width / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"card_renderArguments"
    • Changedcard_safe_zones9 fields changed
      • addedInput schema / properties / card / description
        Added value: +"The card to measure, read from its already-rendered PNG rather than from the recorded slots — so the ink measured is the ink on disk."
      • removedInput schema / properties / card / title
        Removed value: -"Card"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / platform / description
        Added value: +"Whose reserved band to measure against: one of proofcut's own zones (`tiktok-organic`, `tiktok-ads`, `reels`, `shorts`, `worst-case`) or one an applied pack's active variant declares. `pack_show` lists both."
      • removedInput schema / properties / platform / title
        Removed value: -"Platform"
      • removedInput schema / title
        Removed value: -"card_safe_zonesArguments"
    • Changedcard_templates2 fields changed
      • addedInput schema / properties / name
        Added value: +{
        +  "default": null,
        +  "description": "One template to return in full. The others come back as name and description only. Unset, every template in full.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
      • removedInput schema / title
        Removed value: -"card_templatesArguments"
    • Addedchanges
    • Changedcheck_black17 fields changed
      • removedInput schema / properties / fps / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / fps / description
        Added value: +"The rate the timeline's own frame arithmetic is counted on."
      • removedInput schema / properties / fps / title
        Removed value: -"Fps"
      • addedInput schema / properties / fps / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / min_duration / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / min_duration / description
        Added value: +"Shortest black run to report, in seconds."
      • removedInput schema / properties / min_duration / title
        Removed value: -"Min Duration"
      • addedInput schema / properties / min_duration / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / pix_th / description
        Added value: +"How dark a pixel counts as black, 0–1."
      • removedInput schema / properties / pix_th / title
        Removed value: -"Pix Th"
      • addedInput schema / properties / target / description
        Added value: +"The render to scan. Required — unlike `check_frames` there is no cheap no-target mode, since there is nothing to detect black in without a render."
      • removedInput schema / properties / target / title
        Removed value: -"Target"
      • removedInput schema / title
        Removed value: -"check_blackArguments"
    • Changedcheck_frames13 fields changed
      • removedInput schema / properties / fps / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / fps / description
        Added value: +"The rate the export ran at. It has to match, or the two sides are counting on different grids; it defaults to the rate `export` would have picked."
      • removedInput schema / properties / fps / title
        Removed value: -"Fps"
      • addedInput schema / properties / fps / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / target / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / target / description
        Added value: +"An NLE project (`.kdenlive`/`.mlt`/`.xml`) or a finished render. Omit it to just report `expected_frames`, the total the timeline lays down. Run it on the **exported project before rendering** — that is where it is worth the most."
      • removedInput schema / properties / target / title
        Removed value: -"Target"
      • addedInput schema / properties / target / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"check_framesArguments"
    • Changedclip_rm7 fields changed
      • addedInput schema / properties / clip_id / description
        Added value: +"The clip to un-register. Its media on disk is never touched."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"clip_rmArguments"
    • Changedclip_role13 fields changed
      • addedInput schema / properties / clip_id / description
        Added value: +"The clip to read or set."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / reset / description
        Added value: +"Clear the role back to undeclared."
      • removedInput schema / properties / reset / title
        Removed value: -"Reset"
      • removedInput schema / properties / role / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / role / description
        Added value: +"`voiceover` or `footage`. Omit it and `reset` to read what is stored. It is the assets pane's grouping and nothing else: neither transcribe/describe nor any render path reads it."
      • removedInput schema / properties / role / title
        Removed value: -"Role"
      • addedInput schema / properties / role / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"clip_roleArguments"
    • Changedcontact_sheet11 fields changed
      • addedInput schema / properties / clip_id / description
        Added value: +"The clip whose head to look at."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / interval / description
        Added value: +"Seconds between tiles."
      • removedInput schema / properties / interval / title
        Removed value: -"Interval"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / seconds / description
        Added value: +"How much of the head to cover, in seconds. Ten by default — long enough to catch credits, black or a slate before anything is cued to the clip."
      • removedInput schema / properties / seconds / title
        Removed value: -"Seconds"
      • removedInput schema / title
        Removed value: -"contact_sheetArguments"
    • Changedcontinuity_accept11 fields changed
      • addedInput schema / properties / clip_id / description
        Added value: +"The cue's own addressing transcript, as `continuity_check` reports it."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / kind / description
        Added value: +"Which finding to acknowledge: `rewind`, `replay`, `short_shot` or `stub`."
      • removedInput schema / properties / kind / title
        Removed value: -"Kind"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / word_index / description
        Added value: +"The cue's word. With `clip_id` and `kind` it is the finding's address — one shot can carry more than one finding."
      • removedInput schema / properties / word_index / title
        Removed value: -"Word Index"
      • removedInput schema / title
        Removed value: -"continuity_acceptArguments"
    • Changedcontinuity_check15 fields changed
      • addedInput schema / properties / gap / description
        Added value: +"How much timeline may pass before re-showing an asset reads as a replay rather than a rewind, in seconds."
      • removedInput schema / properties / gap / title
        Removed value: -"Gap"
      • addedInput schema / properties / min_shot / description
        Added value: +"Shortest a shot may run before it is reported as a short shot, in seconds. Stills are excluded."
      • removedInput schema / properties / min_shot / title
        Removed value: -"Min Shot"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / scene_threshold / description
        Added value: +"The scene-cut threshold for the stub scan. It defaults to the pinned 0.15, but darker footage from a different film has needed 0.12."
      • removedInput schema / properties / scene_threshold / title
        Removed value: -"Scene Threshold"
      • addedInput schema / properties / stub_tolerance / description
        Added value: +"How close a shot edge has to sit to its footage's own internal cut to be called a stub, in seconds."
      • removedInput schema / properties / stub_tolerance / title
        Removed value: -"Stub Tolerance"
      • addedInput schema / properties / stubs / description
        Added value: +"Look for stubs. On by default, and it costs a scene-cut decode per distinct asset placed — `false` skips that."
      • removedInput schema / properties / stubs / title
        Removed value: -"Stubs"
      • removedInput schema / title
        Removed value: -"continuity_checkArguments"
    • Changedcontinuity_ls5 fields changed
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"continuity_lsArguments"
    • Changedcontinuity_reject11 fields changed
      • addedInput schema / properties / clip_id / description
        Added value: +"The cue's own addressing transcript."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / kind / description
        Added value: +"Which finding to un-acknowledge: `rewind`, `replay`, `short_shot` or `stub`."
      • removedInput schema / properties / kind / title
        Removed value: -"Kind"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / word_index / description
        Added value: +"The cue's word, with `clip_id` and `kind` the address the acknowledgement was stored under."
      • removedInput schema / properties / word_index / title
        Removed value: -"Word Index"
      • removedInput schema / title
        Removed value: -"continuity_rejectArguments"
    • Changedcue_add29 fields changed
      • addedInput schema / properties / after / description
        Added value: +"A forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start."
      • removedInput schema / properties / after / title
        Removed value: -"After"
      • removedInput schema / properties / asset / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / asset / description
        Added value: +"What to show from that word onward: a registered clip id, or `card:<name>` for a card. An opaque key here, resolved by `build_shots` rather than checked against disk now."
      • removedInput schema / properties / asset / title
        Removed value: -"Asset"
      • addedInput schema / properties / asset / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / clip_id / description
        Added value: +"The transcript the cue is addressed against — the VO on a voiceover project, not the footage being shown. `asset` is what gets seen."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • removedInput schema / properties / occurrence / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / occurrence / description
        Added value: +"Disambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at."
      • removedInput schema / properties / occurrence / title
        Removed value: -"Occurrence"
      • addedInput schema / properties / occurrence / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / phrase / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / phrase / description
        Added value: +"Address the cue by what is said instead of by index. It binds to the phrase's **first** word — \"from this word onward\"."
      • removedInput schema / properties / phrase / title
        Removed value: -"Phrase"
      • addedInput schema / properties / phrase / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / src_start / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / src_start / description
        Added value: +"Where inside `asset` the shot reads from, in that asset's own source seconds — the number `describe_ls` reports for a window. An in-point and never a range: unpinned, the shot reads from wherever the per-asset cursor had got to, which is right for re-using a clip and wrong for showing the thing you searched for. A card takes none."
      • removedInput schema / properties / src_start / title
        Removed value: -"Src Start"
      • addedInput schema / properties / src_start / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / word_index / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / word_index / description
        Added value: +"The word the picture starts on, in `clip_id`'s transcript. Give this or `phrase`, not both."
      • removedInput schema / properties / word_index / title
        Removed value: -"Word Index"
      • addedInput schema / properties / word_index / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"cue_addArguments"
    • Changedcue_ls9 fields changed
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"List one clip's cues. Omit it for the whole table."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"cue_lsArguments"
    • Changedcue_reresolve11 fields changed
      • addedInput schema / properties / apply / description
        Added value: +"Rewrite `word_index` wherever the stored phrase still resolves to exactly one match. Off by default: it reports first, and anything ambiguous or unresolved is reported and left untouched either way."
      • removedInput schema / properties / apply / title
        Removed value: -"Apply"
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"Re-resolve one clip's entries. Omit it for every clip."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"cue_reresolveArguments"
    • Changedcue_rm21 fields changed
      • addedInput schema / properties / after / description
        Added value: +"A forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start."
      • removedInput schema / properties / after / title
        Removed value: -"After"
      • addedInput schema / properties / clip_id / description
        Added value: +"The transcript the cue was addressed against."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • removedInput schema / properties / occurrence / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / occurrence / description
        Added value: +"Disambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at."
      • removedInput schema / properties / occurrence / title
        Removed value: -"Occurrence"
      • addedInput schema / properties / occurrence / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / phrase / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / phrase / description
        Added value: +"Address it by wording instead; it resolves to its first word, the way `cue_add` placed it."
      • removedInput schema / properties / phrase / title
        Removed value: -"Phrase"
      • addedInput schema / properties / phrase / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / word_index / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / word_index / description
        Added value: +"The word the cue sits on. Give this or `phrase`."
      • removedInput schema / properties / word_index / title
        Removed value: -"Word Index"
      • addedInput schema / properties / word_index / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"cue_rmArguments"
    • Changedcut_by_time13 fields changed
      • addedInput schema / properties / confirm_suspect / description
        Added value: +"Go ahead even though a boundary word claims a suspect duration. Read the echoed words first — a suspect duration usually means whisper hid a retake inside that word, so the edge is not where it reads."
      • removedInput schema / properties / confirm_suspect / title
        Removed value: -"Confirm Suspect"
      • addedInput schema / properties / pad / description
        Added value: +"Widen only the outer edges of each requested span, in seconds."
      • removedInput schema / properties / pad / title
        Removed value: -"Pad"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • addedInput schema / properties / spans / description
        Added value: +"Half-open `[start, end)` spans in the seconds **an export plays at** — what a person reports off a watch, not source time and not word indices. Every span resolves against the current timeline before any is applied, so a list of notes from one watch stays valid together; overlapping spans are refused rather than double-applied."
      • removedInput schema / properties / spans / title
        Removed value: -"Spans"
      • removedInput schema / title
        Removed value: -"cut_by_timeArguments"
    • Changedcut_by_transcript25 fields changed
      • addedInput schema / properties / clip_id / description
        Added value: +"The transcript the word ranges address."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / confirm_suspect / description
        Added value: +"Go ahead even though a boundary word claims a suspect duration. Read the echoed words first — a suspect duration usually means whisper hid a retake inside that word, so the edge is not where it reads."
      • removedInput schema / properties / confirm_suspect / title
        Removed value: -"Confirm Suspect"
      • removedInput schema / properties / cut / anyOf
        Removed value: -[
        -  {
        -    "items": {
        -      "items": {
        -        "type": "integer"
        -      },
        -      "type": "array"
        -    },
        -    "type": "array"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / cut / description
        Added value: +"Inclusive word ranges to remove, e.g. `[[30, 45], [120, 131]]`. Pass exactly one of `cut` or `keep`."
      • addedInput schema / properties / cut / items
        Added value: +{
        +  "items": {
        +    "type": "integer"
        +  },
        +  "type": "array"
        +}
      • removedInput schema / properties / cut / title
        Removed value: -"Cut"
      • addedInput schema / properties / cut / type
        Added value: +[
        +  "array",
        +  "null"
        +]
      • removedInput schema / properties / keep / anyOf
        Removed value: -[
        -  {
        -    "items": {
        -      "items": {
        -        "type": "integer"
        -      },
        -      "type": "array"
        -    },
        -    "type": "array"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / keep / description
        Added value: +"Inclusive word ranges to keep, everything else going. Pass exactly one of `cut` or `keep`."
      • addedInput schema / properties / keep / items
        Added value: +{
        +  "items": {
        +    "type": "integer"
        +  },
        +  "type": "array"
        +}
      • removedInput schema / properties / keep / title
        Removed value: -"Keep"
      • addedInput schema / properties / keep / type
        Added value: +[
        +  "array",
        +  "null"
        +]
      • addedInput schema / properties / pad / description
        Added value: +"Widen each range on both sides, in seconds, so the cut lands in the silence between words rather than on them. `pad_reach` names any neighbour the padding eats."
      • removedInput schema / properties / pad / title
        Removed value: -"Pad"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • addedInput schema / properties / through_pause / description
        Added value: +"Extend each cut's trailing edge through the pause after its last word, wherever that gap was wide enough to draw a `[N.Ns]` marker — so cutting a phrase also takes the dead air after it. A no-op when the gap is short."
      • removedInput schema / properties / through_pause / title
        Removed value: -"Through Pause"
      • removedInput schema / title
        Removed value: -"cut_by_transcriptArguments"
    • Changeddescribe15 fields changed
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"One clip to describe. Omit it for every video clip not described yet; audio-only clips are refused, since their words are what `transcribe` indexes."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / force / description
        Added value: +"Describe clips that already have descriptions, replacing them. Without it they are skipped."
      • removedInput schema / properties / force / title
        Removed value: -"Force"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • addedInput schema / properties / window / description
        Added value: +"Seconds of footage per description. Do not widen it to save time: a single pass over a whole clip describes six frames as six people, fluently, with nothing saying it is wrong."
      • removedInput schema / properties / window / title
        Removed value: -"Window"
      • removedInput schema / title
        Removed value: -"describeArguments"
    • Changeddescribe_ls13 fields changed
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"List only this clip's windows."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / contains / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / contains / description
        Added value: +"Keep only windows whose text holds every whitespace-separated term, case-insensitively — so `\"kitchen knife\"` matches \"a knife on the kitchen counter\"."
      • removedInput schema / properties / contains / title
        Removed value: -"Contains"
      • addedInput schema / properties / contains / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"describe_lsArguments"
    • Changeddoctor1 field changed
      • removedInput schema / title
        Removed value: -"doctorArguments"
    • Changedexport30 fields changed
      • removedInput schema / properties / export_format / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / export_format / description
        Added value: +"`kdenlive` (the default) writes an MLT project Kdenlive opens and melt renders. Pass null to render media instead. Other auto-editor targets — shotcut, premiere, resolve, final-cut-pro — pass straight through."
      • removedInput schema / properties / export_format / title
        Removed value: -"Export Format"
      • addedInput schema / properties / export_format / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / fps / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / fps / description
        Added value: +"The NLE timeline's frame rate, defaulting to the picture's own (30 for an audio-only project). It sets the render's rate too wherever proofcut owns the profile, and is ignored when auto-editor renders a single-source timeline."
      • removedInput schema / properties / fps / title
        Removed value: -"Fps"
      • addedInput schema / properties / fps / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / loudness / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / loudness / description
        Added value: +"Master the render to this many LUFS integrated: one gain and a true-peak limiter, measured before and after, and refused — leaving the render as it was — if the result misses by more than 1 LU. Render only."
      • removedInput schema / properties / loudness / title
        Removed value: -"Loudness"
      • addedInput schema / properties / loudness / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • addedInput schema / properties / output / description
        Added value: +"Where to write the project file or the render. A file argument, not a project selector: it writes where you say."
      • removedInput schema / properties / output / title
        Removed value: -"Output"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / preset / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / preset / description
        Added value: +"A named quality bundle — `youtube`, `web`, `tiktok-reels`, or `custom` (which needs `resolution`) — meaningful only with `export_format=null`, since an NLE project file has no bitrate. `tiktok-reels` also **checks** that the project renders 9:16 and refuses otherwise; it never sets the shape. Use `canvas` for that."
      • removedInput schema / properties / preset / title
        Removed value: -"Preset"
      • addedInput schema / properties / preset / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / resolution / anyOf
        Removed value: -[
        -  {
        -    "items": {
        -      "type": "integer"
        -    },
        -    "type": "array"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / resolution / description
        Added value: +"`[width, height]`. It **letterboxes** the existing frame on the single-source render path rather than cropping or reframing it, and is refused outright on a melt (multi-source) project."
      • addedInput schema / properties / resolution / items
        Added value: +{
        +  "type": "integer"
        +}
      • removedInput schema / properties / resolution / title
        Removed value: -"Resolution"
      • addedInput schema / properties / resolution / type
        Added value: +[
        +  "array",
        +  "null"
        +]
      • addedInput schema / properties / true_peak / description
        Added value: +"The dBTP ceiling the loudness pass limits under. -1.0 by default."
      • removedInput schema / properties / true_peak / title
        Removed value: -"True Peak"
      • removedInput schema / title
        Removed value: -"exportArguments"
    • Changedfilm_check13 fields changed
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • removedInput schema / properties / reference / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / reference / description
        Added value: +"The delivered file this project is supposed to be. It is remembered, so a later call with no argument re-asks the same question against the same file."
      • removedInput schema / properties / reference / title
        Removed value: -"Reference"
      • addedInput schema / properties / reference / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / reset / description
        Added value: +"Drop the stored reference."
      • removedInput schema / properties / reset / title
        Removed value: -"Reset"
      • removedInput schema / title
        Removed value: -"film_checkArguments"
    • Changedfinish_check48 fields changed
      • addedInput schema / properties / black_min_duration / description
        Added value: +"Shortest black run to report, in seconds."
      • removedInput schema / properties / black_min_duration / title
        Removed value: -"Black Min Duration"
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"Diff against one transcript's expected words rather than all of them."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / duration_tolerance / description
        Added value: +"How far `final`'s duration may sit from the timeline's own arithmetic before it is a fault, in seconds."
      • removedInput schema / properties / duration_tolerance / title
        Removed value: -"Duration Tolerance"
      • addedInput schema / properties / final / description
        Added value: +"The delivered file to check — one an external mix pass produced, not a proofcut render. Every position reported is in this file's own absolute seconds."
      • removedInput schema / properties / final / title
        Removed value: -"Final"
      • removedInput schema / properties / fps / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / fps / description
        Added value: +"The frame grid the timeline's arithmetic is counted on. Defaults to the rate `export` would have picked."
      • removedInput schema / properties / fps / title
        Removed value: -"Fps"
      • addedInput schema / properties / fps / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / holds / anyOf
        Removed value: -[
        -  {
        -    "items": {
        -      "additionalProperties": true,
        -      "type": "object"
        -    },
        -    "type": "array"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / holds / description
        Added value: +"The holds to expect in `final`, resolved and offset the same way the stored ones are. Defaults to the project's own; pass a list (an empty one included) to check against a different set."
      • addedInput schema / properties / holds / items
        Added value: +{
        +  "additionalProperties": true,
        +  "type": "object"
        +}
      • removedInput schema / properties / holds / title
        Removed value: -"Holds"
      • addedInput schema / properties / holds / type
        Added value: +[
        +  "array",
        +  "null"
        +]
      • removedInput schema / properties / language / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / language / description
        Added value: +"Force a language code for the transcription."
      • removedInput schema / properties / language / title
        Removed value: -"Language"
      • addedInput schema / properties / language / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / overlap / description
        Added value: +"How far each window overlaps the one before, in seconds."
      • removedInput schema / properties / overlap / title
        Removed value: -"Overlap"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / pix_th / description
        Added value: +"blackdetect's pixel threshold: how dark a pixel counts as black."
      • removedInput schema / properties / pix_th / title
        Removed value: -"Pix Th"
      • removedInput schema / properties / prepend_seconds / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / prepend_seconds / description
        Added value: +"How much runs before the timeline's first frame in `final` — a cold open concatenated on outside proofcut. Defaults to the project's stored head length."
      • removedInput schema / properties / prepend_seconds / title
        Removed value: -"Prepend Seconds"
      • addedInput schema / properties / prepend_seconds / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • addedInput schema / properties / recheck_pad / description
        Added value: +"How much to pad a dropped run when re-cutting it for its own transcription — the pass that separates a real miss from a false one at a window stitch."
      • removedInput schema / properties / recheck_pad / title
        Removed value: -"Recheck Pad"
      • removedInput schema / properties / transcript_path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / transcript_path / description
        Added value: +"An existing transcription of `final`, to diff again without re-transcribing."
      • removedInput schema / properties / transcript_path / title
        Removed value: -"Transcript Path"
      • addedInput schema / properties / transcript_path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / window / description
        Added value: +"Length of each transcription window, in seconds."
      • removedInput schema / properties / window / title
        Removed value: -"Window"
      • removedInput schema / properties / windowed_model / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / windowed_model / description
        Added value: +"The whisper model for the windowed transcription of `final`. A deliberately small one is the default, since the windowed pass runs over twice the audio."
      • removedInput schema / properties / windowed_model / title
        Removed value: -"Windowed Model"
      • addedInput schema / properties / windowed_model / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"finish_checkArguments"
    • Changedfinish_report11 fields changed
      • addedInput schema / properties / continuity / description
        Added value: +"Add the continuity finding counts by kind and how many are accepted. Off by default — its stub half pays the same scene-cut decode `framing` does."
      • removedInput schema / properties / continuity / title
        Removed value: -"Continuity"
      • addedInput schema / properties / framing / description
        Added value: +"Add stale-framing numbers. Off by default because it decodes placed footage for a scene-cut scan (5.7s wall, 46s of CPU on the film, uncached, every call). Off, `framing` is null, which means *not measured* rather than nothing stale."
      • removedInput schema / properties / framing / title
        Removed value: -"Framing"
      • addedInput schema / properties / holds / description
        Added value: +"Add the per-hold seam and transcription report against the last render. Off by default for the same reason: it decodes and transcribes render spans. Null when not asked for, and also null when nothing has rendered here yet."
      • removedInput schema / properties / holds / title
        Removed value: -"Holds"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"finish_reportArguments"
    • Changedfonts7 fields changed
      • addedInput schema / properties / install / description
        Added value: +"Copy the vendored face where this OS's font system looks (fontconfig, CoreText or DirectWrite). Off by default, because it writes into the home directory."
      • removedInput schema / properties / install / title
        Removed value: -"Install"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"A project directory, or nothing. Omitting it means *no project* here — never the bound one — and reports proofcut's own default caption face; with a project, it reports the face that project's caption style would burn."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"fontsArguments"
    • Changedfootage_sheet19 fields changed
      • addedInput schema / properties / clip_id / description
        Added value: +"The registered clip to browse. This sheet reads the clip's **own source**, so it needs no edit, no cues and no transcript."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / interval / description
        Added value: +"Seconds between tiles when drawing by interval (`interval`, or `auto` on a clip with no descriptions). It is `describe`'s own window length, so a tile lines up with a description."
      • removedInput schema / properties / interval / title
        Removed value: -"Interval"
      • addedInput schema / properties / mode / description
        Added value: +"Which instants to draw: `auto` (the default) uses the clip's described windows if it has any and the interval otherwise, and never scans; `interval` draws every `interval` seconds; `describe` draws one tile per described window, beside its text; `scenes` draws one per detected cut. Scenes is opt-in because its yield is uncorrelated with anything the caller knows — 0 cuts on a 29s b-roll loop, 17 in 60s of gameplay — and it decodes the whole clip."
      • removedInput schema / properties / mode / title
        Removed value: -"Mode"
      • removedInput schema / properties / out / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / out / description
        Added value: +"Write the image to this path as well, replacing whatever file is there. Unset, it goes to the project's own sheet cache and only the bytes come back."
      • removedInput schema / properties / out / title
        Removed value: -"Out"
      • addedInput schema / properties / out / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / page / description
        Added value: +"Which page of rows to draw, from 1. Unset, the first."
      • removedInput schema / properties / page / title
        Removed value: -"Page"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / per_page / description
        Added value: +"Rows per page. `null` draws the whole project in one montage, which returns a path rather than readable bytes — for a person to open, not for an agent to read."
      • removedInput schema / properties / per_page / title
        Removed value: -"Per Page"
      • removedInput schema / title
        Removed value: -"footage_sheetArguments"
    • Changedget_transcript20 fields changed
      • addedInput schema / properties / clip_id / description
        Added value: +"The clip to read."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • removedInput schema / properties / first / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / first / description
        Added value: +"First word index to return, inclusive."
      • removedInput schema / properties / first / title
        Removed value: -"First"
      • addedInput schema / properties / first / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / last / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / last / description
        Added value: +"Last word index to return, inclusive."
      • removedInput schema / properties / last / title
        Removed value: -"Last"
      • addedInput schema / properties / last / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • addedInput schema / properties / limit
        Added value: +{
        +  "default": 300,
        +  "description": "Most words to return in one call, counted from `first`. The reply's `next_first` says where to continue. Bounded by default because a whole transcript can be past what a client will put in context.",
        +  "type": "integer"
        +}
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / search / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / search / description
        Added value: +"Return each match as a word range ready to hand to `cut_by_transcript`, instead of the whole transcript. Prefer it: a transcript is a lot of words to read to find two."
      • removedInput schema / properties / search / title
        Removed value: -"Search"
      • addedInput schema / properties / search / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"get_transcriptArguments"
    • Changedhead33 fields changed
      • removedInput schema / properties / asset / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / asset / description
        Added value: +"The footage the cold open plays, as a registered clip id — never `card:name`. A cold open is real footage with real dialogue by definition, and `verify` accounts for its words rather than forbidding them."
      • removedInput schema / properties / asset / title
        Removed value: -"Asset"
      • addedInput schema / properties / asset / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / fade_in / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / fade_in / description
        Added value: +"Seconds of fade at the head. Unlike `tail`'s fade this is drawn, and it is the whole reason the feature exists — a hard butt-join between room tone and digital silence is exactly the seam a missing fade produces."
      • removedInput schema / properties / fade_in / title
        Removed value: -"Fade In"
      • addedInput schema / properties / fade_in / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / fade_out / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / fade_out / description
        Added value: +"Seconds of fade where the cold open hands over to the film."
      • removedInput schema / properties / fade_out / title
        Removed value: -"Fade Out"
      • addedInput schema / properties / fade_out / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / gain_db / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / gain_db / description
        Added value: +"A flat level shift for the cold open, in dB, distinct from the fades. 0.0 is unity."
      • removedInput schema / properties / gain_db / title
        Removed value: -"Gain Db"
      • addedInput schema / properties / gain_db / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • addedInput schema / properties / reset / description
        Added value: +"Drop the cold open entirely."
      • removedInput schema / properties / reset / title
        Removed value: -"Reset"
      • removedInput schema / properties / seconds / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / seconds / description
        Added value: +"How long the cold open runs. Setting `asset` or `seconds` for the first time needs both together; either alone afterwards updates just that field."
      • removedInput schema / properties / seconds / title
        Removed value: -"Seconds"
      • addedInput schema / properties / seconds / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / src_start / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / src_start / description
        Added value: +"Where inside that asset the cold open reads from, in source seconds. 0.0 on a first set."
      • removedInput schema / properties / src_start / title
        Removed value: -"Src Start"
      • addedInput schema / properties / src_start / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"headArguments"
    • Changedhear21 fields changed
      • addedInput schema / properties / clip_id / description
        Added value: +"The clip whose source audio to listen to."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / end / description
        Added value: +"Where to stop, in the same source seconds. Past the end of the clip it is refused rather than clamped."
      • removedInput schema / properties / end / title
        Removed value: -"End"
      • removedInput schema / properties / language / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / language / description
        Added value: +"Force a language code, e.g. `en`. Unset, whisper detects it."
      • removedInput schema / properties / language / title
        Removed value: -"Language"
      • addedInput schema / properties / language / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / model / description
        Added value: +"The whisper model for this windowed pass."
      • removedInput schema / properties / model / title
        Removed value: -"Model"
      • addedInput schema / properties / overlap / description
        Added value: +"How far each window overlaps the one before it, in seconds. The overlap is what stops a word straddling a boundary from being lost between two windows."
      • removedInput schema / properties / overlap / title
        Removed value: -"Overlap"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / start / description
        Added value: +"Where to start listening, in that clip's own **source** seconds — never timeline seconds and never a word index."
      • removedInput schema / properties / start / title
        Removed value: -"Start"
      • addedInput schema / properties / window / description
        Added value: +"Length of each window, in seconds."
      • removedInput schema / properties / window / title
        Removed value: -"Window"
      • removedInput schema / title
        Removed value: -"hearArguments"
    • Changedhold_add67 fields changed
      • addedInput schema / properties / after / description
        Added value: +"A forward cursor over the matches of `gap_phrase`/`cue_phrase`/`asset_phrase`: any match at or before this word index is skipped. -1, the default, means from the start."
      • removedInput schema / properties / after / title
        Removed value: -"After"
      • removedInput schema / properties / asset / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / asset / description
        Added value: +"The film clip whose own audio plays in the gap, and whose picture the cue pins."
      • removedInput schema / properties / asset / title
        Removed value: -"Asset"
      • addedInput schema / properties / asset / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / asset_phrase / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / asset_phrase / description
        Added value: +"The line to play, resolved against `asset`'s **own** transcript, binding its first and last words together. One phrase is the source of truth for both ends; hand-typed indices drift the moment a transcript changes under them."
      • removedInput schema / properties / asset_phrase / title
        Removed value: -"Asset Phrase"
      • addedInput schema / properties / asset_phrase / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / clip_id / description
        Added value: +"The VO track the gap opens in."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • removedInput schema / properties / cue_phrase / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / cue_phrase / description
        Added value: +"Address the cue by wording; it binds its **first** word."
      • removedInput schema / properties / cue_phrase / title
        Removed value: -"Cue Phrase"
      • addedInput schema / properties / cue_phrase / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / cue_word_index / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / cue_word_index / description
        Added value: +"The word the picture cue for `asset` is placed on."
      • removedInput schema / properties / cue_word_index / title
        Removed value: -"Cue Word Index"
      • addedInput schema / properties / cue_word_index / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / fade_in / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / fade_in / description
        Added value: +"Seconds of fade as the held audio comes in. Re-settable."
      • removedInput schema / properties / fade_in / title
        Removed value: -"Fade In"
      • addedInput schema / properties / fade_in / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / fade_out / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / fade_out / description
        Added value: +"Seconds of fade as it goes out. Re-settable."
      • removedInput schema / properties / fade_out / title
        Removed value: -"Fade Out"
      • addedInput schema / properties / fade_out / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / gap_phrase / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / gap_phrase / description
        Added value: +"Address the gap by wording; it binds its **last** word, since the gap opens right after it."
      • removedInput schema / properties / gap_phrase / title
        Removed value: -"Gap Phrase"
      • addedInput schema / properties / gap_phrase / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / gap_word_index / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / gap_word_index / description
        Added value: +"The word the gap opens right after. With `clip_id` it is the hold's address, and a second `hold_add` at the same address is refused."
      • removedInput schema / properties / gap_word_index / title
        Removed value: -"Gap Word Index"
      • addedInput schema / properties / gap_word_index / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / head_margin / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / head_margin / description
        Added value: +"Seconds kept before the line, so it does not start on the word. Re-settable on an already-spliced hold."
      • removedInput schema / properties / head_margin / title
        Removed value: -"Head Margin"
      • addedInput schema / properties / head_margin / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / occurrence / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / occurrence / description
        Added value: +"Disambiguate `gap_phrase`/`cue_phrase`/`asset_phrase` by count, **1-based**. Unset, an ambiguous phrase is refused rather than guessed at."
      • removedInput schema / properties / occurrence / title
        Removed value: -"Occurrence"
      • addedInput schema / properties / occurrence / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • removedInput schema / properties / tail_margin / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / tail_margin / description
        Added value: +"Seconds kept after the line. Re-settable."
      • removedInput schema / properties / tail_margin / title
        Removed value: -"Tail Margin"
      • addedInput schema / properties / tail_margin / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / under / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / under / description
        Added value: +"How far below the VO the held audio sits, in LU. Re-settable."
      • removedInput schema / properties / under / title
        Removed value: -"Under"
      • addedInput schema / properties / under / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / word_index_first / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / word_index_first / description
        Added value: +"First word of the line to play, in **`asset`'s own** transcript — not the VO's."
      • removedInput schema / properties / word_index_first / title
        Removed value: -"Word Index First"
      • addedInput schema / properties / word_index_first / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / word_index_last / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / word_index_last / description
        Added value: +"Last word of that line. With `word_index_first` it is one-way once spliced: resizing means `hold_rm` then `hold_add`, or `undo`."
      • removedInput schema / properties / word_index_last / title
        Removed value: -"Word Index Last"
      • addedInput schema / properties / word_index_last / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"hold_addArguments"
    • Changedhold_check7 fields changed
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / render / description
        Added value: +"The rendered file to listen to. Each hold's span is resolved live against the current edit and transcribed off this file."
      • removedInput schema / properties / render / title
        Removed value: -"Render"
      • removedInput schema / title
        Removed value: -"hold_checkArguments"
    • Changedhold_ls5 fields changed
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"hold_lsArguments"
    • Changedhold_rm9 fields changed
      • addedInput schema / properties / clip_id / description
        Added value: +"The VO track the hold was spliced into."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / gap_word_index / description
        Added value: +"The hold's address, with `clip_id`. The record and its owned cue go; the spliced silence stays, since there is no clean un-splice — only `undo`."
      • removedInput schema / properties / gap_word_index / title
        Removed value: -"Gap Word Index"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"hold_rmArguments"
    • Changedhold_under45 fields changed
      • addedInput schema / properties / after / description
        Added value: +"A forward cursor over the matches of `phrase_start`/`phrase_end`: any match at or before this word index is skipped. -1, the default, means from the start."
      • removedInput schema / properties / after / title
        Removed value: -"After"
      • addedInput schema / properties / asset / description
        Added value: +"The film clip whose audio plays under the voice. It has to be on screen across the span — the audio reads from wherever the shot showing it has got to — so cue it first."
      • removedInput schema / properties / asset / title
        Removed value: -"Asset"
      • addedInput schema / properties / clip_id / description
        Added value: +"The VO track whose words the span is measured in."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • removedInput schema / properties / fade_in / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / fade_in / description
        Added value: +"Seconds of fade as the film audio comes in."
      • removedInput schema / properties / fade_in / title
        Removed value: -"Fade In"
      • addedInput schema / properties / fade_in / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / fade_out / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / fade_out / description
        Added value: +"Seconds of fade as it goes out."
      • removedInput schema / properties / fade_out / title
        Removed value: -"Fade Out"
      • addedInput schema / properties / fade_out / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / occurrence / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / occurrence / description
        Added value: +"Disambiguate `phrase_start`/`phrase_end` by count, **1-based**. Unset, an ambiguous phrase is refused rather than guessed at."
      • removedInput schema / properties / occurrence / title
        Removed value: -"Occurrence"
      • addedInput schema / properties / occurrence / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / phrase_end / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / phrase_end / description
        Added value: +"Set the span's end by wording instead."
      • removedInput schema / properties / phrase_end / title
        Removed value: -"Phrase End"
      • addedInput schema / properties / phrase_end / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / phrase_start / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / phrase_start / description
        Added value: +"Set the span's start by wording instead."
      • removedInput schema / properties / phrase_start / title
        Removed value: -"Phrase Start"
      • addedInput schema / properties / phrase_start / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • removedInput schema / properties / under / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / under / description
        Added value: +"How far below the VO the film audio sits, in LU. 13 by default."
      • removedInput schema / properties / under / title
        Removed value: -"Under"
      • addedInput schema / properties / under / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / word_index_end / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / word_index_end / description
        Added value: +"Last VO word of the span."
      • removedInput schema / properties / word_index_end / title
        Removed value: -"Word Index End"
      • addedInput schema / properties / word_index_end / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / word_index_start / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / word_index_start / description
        Added value: +"First VO word of the span. With `clip_id` it is the entry's address; a second call at the same address replaces it."
      • removedInput schema / properties / word_index_start / title
        Removed value: -"Word Index Start"
      • addedInput schema / properties / word_index_start / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"hold_underArguments"
    • Changedhold_under_rm9 fields changed
      • addedInput schema / properties / clip_id / description
        Added value: +"The VO track the entry was addressed against."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / word_index_start / description
        Added value: +"The span's first VO word — the entry's address, with `clip_id`."
      • removedInput schema / properties / word_index_start / title
        Removed value: -"Word Index Start"
      • removedInput schema / title
        Removed value: -"hold_under_rmArguments"
    • Changedimport_edit13 fields changed
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"The registered clip to attribute a single-source document to, when its media sits at a path this project does not know."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / document / description
        Added value: +"The `.kdenlive` or `.mlt` playlist somebody already trimmed by hand. Every clip it references has to be registered already; ones that do not match a registered clip by resolved path are named rather than imported behind your back."
      • removedInput schema / properties / document / title
        Removed value: -"Document"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • removedInput schema / title
        Removed value: -"import_editArguments"
    • Changedimport_media21 fields changed
      • removedInput schema / properties / audio_stream / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / audio_stream / description
        Added value: +"Keep one of a container's audio streams and drop the rest, numbered from 0 in ffmpeg's own audio ordering — not the container's absolute stream index, which is a different number once there is video."
      • removedInput schema / properties / audio_stream / title
        Removed value: -"Audio Stream"
      • addedInput schema / properties / audio_stream / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"The id every later tool addresses this clip by. Unset, one is derived from the filename. Keep it short: it becomes part of cache paths, and a stock Windows measures those against 248 characters."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / copy / description
        Added value: +"Copy the media into the project instead of referencing it where it sits. Off by default — a reference costs no disk, and it is also the fallback where symlinks are rejected."
      • removedInput schema / properties / copy / title
        Removed value: -"Copy"
      • addedInput schema / properties / mix / description
        Added value: +"Sum a container's audio streams into one track, for two mics on one performance. It writes a derived copy every later op reads without knowing it."
      • removedInput schema / properties / mix / title
        Removed value: -"Mix"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / sheet / description
        Added value: +"Draw a contact sheet of the clip's first ten seconds onto the returned record. On by default, because a first look that has to be asked for is one nobody takes."
      • removedInput schema / properties / sheet / title
        Removed value: -"Sheet"
      • addedInput schema / properties / source / description
        Added value: +"The media file to register. A file argument rather than a project selector, so it is deliberately left unconfined — footage usually lives outside the project."
      • removedInput schema / properties / source / title
        Removed value: -"Source"
      • removedInput schema / title
        Removed value: -"import_mediaArguments"
    • Changedinit9 fields changed
      • removedInput schema / properties / name / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / name / description
        Added value: +"A name for the project, recorded in the manifest. Unset, the directory's own name is used."
      • removedInput schema / properties / name / title
        Removed value: -"Name"
      • addedInput schema / properties / name / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"initArguments"
    • Changedlist_media9 fields changed
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / recursive / description
        Added value: +"Walk subdirectories too. On by default."
      • removedInput schema / properties / recursive / title
        Removed value: -"Recursive"
      • addedInput schema / properties / source_dir / description
        Added value: +"The directory to list. It names where footage lives rather than which project, so it is deliberately not confined to the bound project."
      • removedInput schema / properties / source_dir / title
        Removed value: -"Source Dir"
      • removedInput schema / title
        Removed value: -"list_mediaArguments"
    • Changedlocate33 fields changed
      • addedInput schema / properties / after / description
        Added value: +"A forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start."
      • removedInput schema / properties / after / title
        Removed value: -"After"
      • addedInput schema / properties / clip_id / description
        Added value: +"The transcript, or the recording, the address belongs to."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • removedInput schema / properties / first / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / first / description
        Added value: +"First word index, inclusive. Address it one way per call: `first`/`last`, `source_start`/`source_end`, or `phrase`."
      • removedInput schema / properties / first / title
        Removed value: -"First"
      • addedInput schema / properties / first / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / last / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / last / description
        Added value: +"Last word index, inclusive. Defaults to `first`."
      • removedInput schema / properties / last / title
        Removed value: -"Last"
      • addedInput schema / properties / last / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / occurrence / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / occurrence / description
        Added value: +"Disambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at."
      • removedInput schema / properties / occurrence / title
        Removed value: -"Occurrence"
      • addedInput schema / properties / occurrence / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / phrase / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / phrase / description
        Added value: +"Locate by wording. A phrase is naturally a range, so it resolves straight to first and last with no edge to pick."
      • removedInput schema / properties / phrase / title
        Removed value: -"Phrase"
      • addedInput schema / properties / phrase / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / source_end / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / source_end / description
        Added value: +"End of the source interval, in the recording's own seconds."
      • removedInput schema / properties / source_end / title
        Removed value: -"Source End"
      • addedInput schema / properties / source_end / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / source_start / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / source_start / description
        Added value: +"Seconds into the original recording. Omit `source_end` to locate an instant."
      • removedInput schema / properties / source_start / title
        Removed value: -"Source Start"
      • addedInput schema / properties / source_start / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"locateArguments"
    • Changedmigrate_project7 fields changed
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • removedInput schema / title
        Removed value: -"migrate_projectArguments"
    • Changedmusic75 fields changed
      • addedInput schema / properties / after / description
        Added value: +"A forward cursor over the matches of `phrase_start`/`phrase_end`: any match at or before this word index is skipped. -1, the default, means from the start."
      • removedInput schema / properties / after / title
        Removed value: -"After"
      • removedInput schema / properties / asset / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / asset / description
        Added value: +"The bed's own music, as a registered clip id — never `card:name`, since a held frame has no sound. It plays from its own head; shorter than its span pads with real silence, longer is trimmed."
      • removedInput schema / properties / asset / title
        Removed value: -"Asset"
      • addedInput schema / properties / asset / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / clear_duck
        Added value: +{
        +  "default": false,
        +  "description": "Return the bed to one level, with no ducking.",
        +  "type": "boolean"
        +}
      • addedInput schema / properties / clear_end / description
        Added value: +"Drop the end word, returning the bed to running to the end of the edit."
      • removedInput schema / properties / clear_end / title
        Removed value: -"Clear End"
      • addedInput schema / properties / clear_under / description
        Added value: +"Return every asset to its own level."
      • removedInput schema / properties / clear_under / title
        Removed value: -"Clear Under"
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"The transcript the bed's word indices address — the VO, not the music."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / crossfade / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / crossfade / description
        Added value: +"Seconds two pieces overlap by. A crossfade edge is equal-power rather than the straight dB line an ordinary fade draws — two straight fades crossing sum to a hole."
      • removedInput schema / properties / crossfade / title
        Removed value: -"Crossfade"
      • addedInput schema / properties / crossfade / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • addedInput schema / properties / duck
        Added value: +{
        +  "default": null,
        +  "description": "Pull the bed this many dB down while the voice is speaking and let it back up in the pauses. It is keyed off the timeline's own audio at export rather than the transcript's word timings, which were measured against a bed recovered from a real render and beaten: 2.72 dB off for the audio gate against a word-span duck's 3.39.",
        +  "type": [
        +    "number",
        +    "null"
        +  ]
        +}
      • removedInput schema / properties / fade_in / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / fade_in / description
        Added value: +"Seconds of fade at the bed's start. The fades ride the bed's own entry, so a fade-out ends where the music audibly ends."
      • removedInput schema / properties / fade_in / title
        Removed value: -"Fade In"
      • addedInput schema / properties / fade_in / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / fade_out / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / fade_out / description
        Added value: +"Seconds of fade at the bed's end. A fade pair the bed cannot hold refuses at build time rather than being clamped."
      • removedInput schema / properties / fade_out / title
        Removed value: -"Fade Out"
      • addedInput schema / properties / fade_out / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / occurrence / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / occurrence / description
        Added value: +"Disambiguate `phrase_start`/`phrase_end` by count, **1-based**. Unset, an ambiguous phrase is refused rather than guessed at."
      • removedInput schema / properties / occurrence / title
        Removed value: -"Occurrence"
      • addedInput schema / properties / occurrence / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / passages / anyOf
        Removed value: -[
        -  {
        -    "items": {
        -      "additionalProperties": true,
        -      "type": "object"
        -    },
        -    "type": "array"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / passages / description
        Added value: +"Replace the list of passages after the bed's own asset: each `{asset, word_index_start | phrase_start, src_in?, crossfade?, rotate?}`. `[]` clears them."
      • addedInput schema / properties / passages / items
        Added value: +{
        +  "additionalProperties": true,
        +  "type": "object"
        +}
      • removedInput schema / properties / passages / title
        Removed value: -"Passages"
      • addedInput schema / properties / passages / type
        Added value: +[
        +  "array",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / phrase_end / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / phrase_end / description
        Added value: +"Set the out-point by wording instead; it binds the phrase's last word. Each boundary is independent — one can be a phrase and the other an index."
      • removedInput schema / properties / phrase_end / title
        Removed value: -"Phrase End"
      • addedInput schema / properties / phrase_end / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / phrase_start / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / phrase_start / description
        Added value: +"Set the in-point by wording instead; it binds the phrase's first word. The resolved phrase is stored beside the index, so `cue_reresolve` can re-derive it after a re-record."
      • removedInput schema / properties / phrase_start / title
        Removed value: -"Phrase Start"
      • addedInput schema / properties / phrase_start / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • addedInput schema / properties / reset / description
        Added value: +"Drop the bed entirely."
      • removedInput schema / properties / reset / title
        Removed value: -"Reset"
      • removedInput schema / properties / rotate / anyOf
        Removed value: -[
        -  {
        -    "items": {
        -      "type": "string"
        -    },
        -    "type": "array"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / rotate / description
        Added value: +"Further assets to play in turn as each one runs out, overlapping by `crossfade`. `[]` clears them."
      • addedInput schema / properties / rotate / items
        Added value: +{
        +  "type": "string"
        +}
      • removedInput schema / properties / rotate / title
        Removed value: -"Rotate"
      • addedInput schema / properties / rotate / type
        Added value: +[
        +  "array",
        +  "null"
        +]
      • removedInput schema / properties / src_in / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / src_in / description
        Added value: +"Where inside the bed's own asset it starts, in seconds."
      • removedInput schema / properties / src_in / title
        Removed value: -"Src In"
      • addedInput schema / properties / src_in / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / under / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / under / description
        Added value: +"Level the whole bed this many LU below the voice, measured. It is a fixed offset; `duck` is the moving one."
      • removedInput schema / properties / under / title
        Removed value: -"Under"
      • addedInput schema / properties / under / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / word_index_end / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / word_index_end / description
        Added value: +"Where the bed goes out. Unset means *to the end of the edit*, so a tail holds over silence."
      • removedInput schema / properties / word_index_end / title
        Removed value: -"Word Index End"
      • addedInput schema / properties / word_index_end / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / word_index_start / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / word_index_start / description
        Added value: +"Where the bed comes in, as a word of `clip_id`. The bed stores words and never a length, so a cut before either boundary moves it automatically."
      • removedInput schema / properties / word_index_start / title
        Removed value: -"Word Index Start"
      • addedInput schema / properties / word_index_start / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"musicArguments"
    • Changedpack_activate9 fields changed
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • addedInput schema / properties / variant / description
        Added value: +"Which already-snapshotted variant to switch to. No file is re-read, and an unknown name is refused by listing the ones that are available."
      • removedInput schema / properties / variant / title
        Removed value: -"Variant"
      • removedInput schema / title
        Removed value: -"pack_activateArguments"
    • Changedpack_apply15 fields changed
      • addedInput schema / properties / allow_fallback / description
        Added value: +"Accept a declared CSS fallback for a font family that does not actually draw on this machine, recording which was used. Without it, a family that does not draw refuses the whole call."
      • removedInput schema / properties / allow_fallback / title
        Removed value: -"Allow Fallback"
      • addedInput schema / properties / install_fonts / description
        Added value: +"Vendor the pack's own `fonts/` directory, if it ships one. Off by default, since it writes into `$HOME`."
      • removedInput schema / properties / install_fonts / title
        Removed value: -"Install Fonts"
      • addedInput schema / properties / pack_path / description
        Added value: +"The pack file to load. An external file, never confined to the project — a pack usually lives in a separate branding repo — and nothing after this call depends on it staying reachable."
      • removedInput schema / properties / pack_path / title
        Removed value: -"Pack Path"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • addedInput schema / properties / variant / description
        Added value: +"Which resolved variant to activate. Every declared variant is snapshotted regardless, so `pack_activate` can switch later with no file re-read."
      • removedInput schema / properties / variant / title
        Removed value: -"Variant"
      • removedInput schema / title
        Removed value: -"pack_applyArguments"
    • Changedpack_apply_captions9 fields changed
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • addedInput schema / properties / preset / description
        Added value: +"Which caption preset of the active variant to apply, through the ordinary `caption_style` call. This is the only thing that restyles captions from a pack; `pack_apply` never does it on its own."
      • removedInput schema / properties / preset / title
        Removed value: -"Preset"
      • removedInput schema / title
        Removed value: -"pack_apply_captionsArguments"
    • Changedpack_show13 fields changed
      • removedInput schema / properties / pack_path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / pack_path / description
        Added value: +"Read and resolve this pack file fresh, needing no project. With `path` as well, it compares what the file says now against what the project is still running."
      • removedInput schema / properties / pack_path / title
        Removed value: -"Pack Path"
      • addedInput schema / properties / pack_path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"A project directory, or nothing. Omitting it means *no project* here — never the bound one — so `pack_path` alone reads the file fresh; given, it reports what that project has applied."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / variant / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / variant / description
        Added value: +"Report one variant rather than all of them."
      • removedInput schema / properties / variant / title
        Removed value: -"Variant"
      • addedInput schema / properties / variant / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"pack_showArguments"
    • Changedpack_status5 fields changed
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"pack_statusArguments"
    • Changedping2 fields changed
      • removedInput schema / title
        Removed value: -"pingArguments"
      • changedOutput schema / additionalProperties
        Previous value: -{
        -  "type": "string"
        -}New value: +true
    • Changedproperties13 fields changed
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"Add this clip's assets entry, framing windows and cue table to the report."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / word_index / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / word_index / description
        Added value: +"With `clip_id`, add the cue at that word — or, when there is none, the word plus three either side. It needs `clip_id`."
      • removedInput schema / properties / word_index / title
        Removed value: -"Word Index"
      • addedInput schema / properties / word_index / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"propertiesArguments"
    • Changedproxy_transcode9 fields changed
      • addedInput schema / properties / clip_id / description
        Added value: +"The clip the preview cannot decode. A clip that already plays is refused, and so is one with no decodable streams — that is a broken file, not a codec problem."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / force / description
        Added value: +"Rebuild a proxy that is already current. It touches nothing authored: a proxy is a preview artefact the manifest never records, so no render can reach one. It overrides neither refusal."
      • removedInput schema / properties / force / title
        Removed value: -"Force"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"proxy_transcodeArguments"
    • Changedreel23 fields changed
      • removedInput schema / properties / canvas / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / canvas / description
        Added value: +"The shape to set on the derived project only, e.g. `1080x1920`. Setting it on the film instead is what deriving exists to avoid — a canvas is project state and would stay."
      • removedInput schema / properties / canvas / title
        Removed value: -"Canvas"
      • addedInput schema / properties / canvas / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / confirm_suspect / description
        Added value: +"Go ahead even though a boundary word claims a suspect duration. Read the echoed words first — a suspect duration usually means whisper hid a retake inside that word, so the edge is not where it reads."
      • removedInput schema / properties / confirm_suspect / title
        Removed value: -"Confirm Suspect"
      • addedInput schema / properties / dest / description
        Added value: +"Where the derived project is created. It is a project selector too, not a file, so a bound server confines it to the same tree as `path` rather than letting a reel be written anywhere on disk."
      • removedInput schema / properties / dest / title
        Removed value: -"Dest"
      • addedInput schema / properties / end / description
        Added value: +"Where it ends, in those same render seconds. `start`/`end` name the span to **keep**, the opposite direction from every other tool here."
      • removedInput schema / properties / end / title
        Removed value: -"End"
      • removedInput schema / properties / name / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / name / description
        Added value: +"A name for the derived project. Unset, it is derived from `dest`."
      • removedInput schema / properties / name / title
        Removed value: -"Name"
      • addedInput schema / properties / name / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • addedInput schema / properties / start / description
        Added value: +"Where the reel begins, in the seconds **an export plays at** — the same numbers `cut_by_time` takes, read off a watch."
      • removedInput schema / properties / start / title
        Removed value: -"Start"
      • removedInput schema / title
        Removed value: -"reelArguments"
    • Changedreframe28 fields changed
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"The clip to read or frame. Omit it to read the crops in force for every clip, including how much of each is kept."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / fill
        Added value: +{
        +  "default": null,
        +  "description": "`blur` draws this window **blur-filled**: the whole source contained in the frame, over a blurred, darkened copy of the same moment covering the canvas. For a shot every crop loses something from and no split divides. Takes no `rect`, `pane` or `interp`; set `src_start` for one shot.",
        +  "type": [
        +    "string",
        +    "null"
        +  ]
        +}
      • addedInput schema / properties / interp / description
        Added value: +"Slide into this window from whatever governed before it instead of stepping to it. It needs `src_start` past 0 — there is nothing before the head of the source to slide from — and cannot be combined with `pane`."
      • removedInput schema / properties / interp / title
        Removed value: -"Interp"
      • removedInput schema / properties / pane / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / pane / description
        Added value: +"A second rect making this window a **stacked split**: `rect` on top, `pane` below, each about twice the width one 9:16 window gets. For the shot one window cannot frame. Both are grown to the full source height — nothing masks a pane, so a shorter crop scales into the other half at exit 0."
      • removedInput schema / properties / pane / title
        Removed value: -"Pane"
      • addedInput schema / properties / pane / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • removedInput schema / properties / rect / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / rect / description
        Added value: +"`X,Y,W,H` in that clip's **own source pixels** — the region kept. An override is a floor rather than a frame: a rect that is not the canvas's shape is grown to it, so nothing named is pushed off screen, and the reply gives both `asked` and the `crop` it became."
      • removedInput schema / properties / rect / title
        Removed value: -"Rect"
      • addedInput schema / properties / rect / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / reset / description
        Added value: +"With `clip_id`, drop that clip's overrides; with `src_start` as well, only the window there. Alone, drop every override."
      • removedInput schema / properties / reset / title
        Removed value: -"Reset"
      • removedInput schema / properties / src_start / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / src_start / description
        Added value: +"Frame a **shot** rather than a clip: seconds into that clip's own source, the rect holding from there until the next window. Because the address is the source's own clock, a clip used seven times picks up the right window at each placement. Omitted, it is the window from the head of the file."
      • removedInput schema / properties / src_start / title
        Removed value: -"Src Start"
      • addedInput schema / properties / src_start / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"reframeArguments"
    • Changedreframe_coverage11 fields changed
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"Walk one clip's placements. Omit it for the whole project."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / threshold / description
        Added value: +"How strong a scene change has to be to **demand** a window. Boundaries are scored against every detected cut rather than only these, since a cut too weak to demand a window still explains one."
      • removedInput schema / properties / threshold / title
        Removed value: -"Threshold"
      • removedInput schema / title
        Removed value: -"reframe_coverageArguments"
    • Changedreframe_detect17 fields changed
      • addedInput schema / properties / apply / description
        Added value: +"Write the proposals through `reframe`. Off by default — the opposite of `cut --plan` — because the pass runs 24% of a window's width out on average. Call `reframe_sheet` and look first. It never writes over a window that is already an override."
      • removedInput schema / properties / apply / title
        Removed value: -"Apply"
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"Propose windows for one clip. Omit it for every placed clip."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / frames / description
        Added value: +"How many moments to sample inside each window before centring it on the faces found there."
      • removedInput schema / properties / frames / title
        Removed value: -"Frames"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / split / description
        Added value: +"Offer a stacked split where every sampled frame holds two or three faces one window cannot hold. On by default; `false` turns the offer off."
      • removedInput schema / properties / split / title
        Removed value: -"Split"
      • addedInput schema / properties / threshold / description
        Added value: +"How strong a scene change has to be to count as a camera cut, 0–1. 0.15 is pinned by judging detections on real footage: every candidate from 0.141 to 0.244 was a real cut, and the first non-cut is 0.137."
      • removedInput schema / properties / threshold / title
        Removed value: -"Threshold"
      • removedInput schema / title
        Removed value: -"reframe_detectArguments"
    • Changedreframe_sheet22 fields changed
      • addedInput schema / properties / extremes / description
        Added value: +"Draw the subject's own leftmost and rightmost moments, worst first, instead of fixed fractions — the rect does not move inside a stretch, so that is where a static window is worst. Off by default: it costs the face detector and about half a second a probe. Read `worst_offset` beside `multi_face`, never after it."
      • removedInput schema / properties / extremes / title
        Removed value: -"Extremes"
      • removedInput schema / properties / moments / anyOf
        Removed value: -[
        -  {
        -    "items": {
        -      "type": "number"
        -    },
        -    "type": "array"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / moments / description
        Added value: +"Fractions of each window to draw tiles at, e.g. `[0.1, 0.5, 0.9]`. A tile is evidence about one instant while a rect is a claim about a stretch, so where the subject moves these decide what the sheet can see. Refused alongside `extremes`."
      • addedInput schema / properties / moments / items
        Added value: +{
        +  "type": "number"
        +}
      • removedInput schema / properties / moments / title
        Removed value: -"Moments"
      • addedInput schema / properties / moments / type
        Added value: +[
        +  "array",
        +  "null"
        +]
      • removedInput schema / properties / out / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / out / description
        Added value: +"Write the image to this path as well, replacing whatever file is there. Unset, it goes to the project's own sheet cache and only the bytes come back."
      • removedInput schema / properties / out / title
        Removed value: -"Out"
      • addedInput schema / properties / out / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / page / description
        Added value: +"Which page of rows to draw, from 1. Unset, the first."
      • removedInput schema / properties / page / title
        Removed value: -"Page"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / per_page / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / per_page / description
        Added value: +"Rows per page. `null` draws the whole project in one montage, which returns a path rather than readable bytes — for a person to open, not for an agent to read."
      • removedInput schema / properties / per_page / title
        Removed value: -"Per Page"
      • addedInput schema / properties / per_page / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"reframe_sheetArguments"
    • Changedresolve_phrase17 fields changed
      • addedInput schema / properties / after / description
        Added value: +"A forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start."
      • removedInput schema / properties / after / title
        Removed value: -"After"
      • addedInput schema / properties / clip_id / description
        Added value: +"The transcript to resolve against."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / fuzzy / description
        Added value: +"Fall back to a fuzzy match when nothing matches exactly. A fuzzy hit sets `ratio` and is never reported as an exact one; `false` refuses instead."
      • removedInput schema / properties / fuzzy / title
        Removed value: -"Fuzzy"
      • removedInput schema / properties / occurrence / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / occurrence / description
        Added value: +"Disambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at."
      • removedInput schema / properties / occurrence / title
        Removed value: -"Occurrence"
      • addedInput schema / properties / occurrence / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / phrase / description
        Added value: +"The words to find, as they were spoken."
      • removedInput schema / properties / phrase / title
        Removed value: -"Phrase"
      • removedInput schema / title
        Removed value: -"resolve_phraseArguments"
    • Changedrestore13 fields changed
      • addedInput schema / properties / clip_id / description
        Added value: +"The clip whose cut material to bring back."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / pad / description
        Added value: +"Pass the same `pad` the original cut used to bring its padding sliver back, not only the words."
      • removedInput schema / properties / pad / title
        Removed value: -"Pad"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • addedInput schema / properties / ranges / description
        Added value: +"Inclusive word ranges, the shape `cut_by_transcript` takes. Only the part the edit says is actually absent comes back; material still present is left alone."
      • removedInput schema / properties / ranges / title
        Removed value: -"Ranges"
      • removedInput schema / title
        Removed value: -"restoreArguments"
    • Changedreview_add15 fields changed
      • removedInput schema / properties / baseline / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / baseline / description
        Added value: +"Required for `kind=\"control\"`: the name of the already-registered item this one claims to be identical to. Both files' sha256 must match or the call is refused — nothing is labelled a control here unless it is byte-identical to what it claims."
      • removedInput schema / properties / baseline / title
        Removed value: -"Baseline"
      • addedInput schema / properties / baseline / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / kind / description
        Added value: +"One of `render`, `sheet`, `ab`, `control`."
      • removedInput schema / properties / kind / title
        Removed value: -"Kind"
      • addedInput schema / properties / name / description
        Added value: +"What to call this item in the served round. Re-using a name replaces that entry while its verdict stays attached."
      • removedInput schema / properties / name / title
        Removed value: -"Name"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / source / description
        Added value: +"The file to point at — never copied. A render already lives in `renders/`, a sheet in the sheet directory."
      • removedInput schema / properties / source / title
        Removed value: -"Source"
      • removedInput schema / title
        Removed value: -"review_addArguments"
    • Changedreview_list5 fields changed
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"review_listArguments"
    • Changedreview_verdict13 fields changed
      • addedInput schema / properties / name / description
        Added value: +"The registered item being answered. An unregistered name is refused."
      • removedInput schema / properties / name / title
        Removed value: -"Name"
      • removedInput schema / properties / note / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / note / description
        Added value: +"Anything to record beside the verdict."
      • removedInput schema / properties / note / title
        Removed value: -"Note"
      • addedInput schema / properties / note / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / verdict / description
        Added value: +"The answer, as free text rather than an enum — past rounds answered yes/no, loop/hold, or a specific choice by name, and a fixed vocabulary would misfit whichever question the next round asks."
      • removedInput schema / properties / verdict / title
        Removed value: -"Verdict"
      • removedInput schema / title
        Removed value: -"review_verdictArguments"
    • Changedseed_timeline19 fields changed
      • addedInput schema / properties / clip_id / description
        Added value: +"The clip to lay down as the timeline."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • removedInput schema / properties / edit_expr / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / edit_expr / description
        Added value: +"auto-editor's edit language, passed straight through — e.g. `(or audio:0.03 motion:0.06)`. It replaces the threshold-based rule."
      • removedInput schema / properties / edit_expr / title
        Removed value: -"Edit Expr"
      • addedInput schema / properties / edit_expr / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / margin / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / margin / description
        Added value: +"How much to leave either side of kept audio, in auto-editor's own notation (e.g. `0.2s`), so an edge lands in the silence rather than on the breath."
      • removedInput schema / properties / margin / title
        Removed value: -"Margin"
      • addedInput schema / properties / margin / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / remove_silences / description
        Added value: +"Silence-cut the clip on the way in, through auto-editor. On by default; false lays the whole clip down untouched."
      • removedInput schema / properties / remove_silences / title
        Removed value: -"Remove Silences"
      • addedInput schema / properties / threshold / description
        Added value: +"auto-editor's audio loudness threshold, 0–1. Lower keeps quieter material."
      • removedInput schema / properties / threshold / title
        Removed value: -"Threshold"
      • removedInput schema / title
        Removed value: -"seed_timelineArguments"
    • Changedshot_sheet13 fields changed
      • removedInput schema / properties / out / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / out / description
        Added value: +"Write the image to this path as well, replacing whatever file is there. Unset, it goes to the project's own sheet cache and only the bytes come back."
      • removedInput schema / properties / out / title
        Removed value: -"Out"
      • addedInput schema / properties / out / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / page / description
        Added value: +"Which page of rows to draw, from 1. Unset, the first."
      • removedInput schema / properties / page / title
        Removed value: -"Page"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / per_page / description
        Added value: +"Rows per page. `null` draws the whole project in one montage, which returns a path rather than readable bytes — for a person to open, not for an agent to read."
      • removedInput schema / properties / per_page / title
        Removed value: -"Per Page"
      • removedInput schema / title
        Removed value: -"shot_sheetArguments"
    • Changedspeech_overlap29 fields changed
      • addedInput schema / properties / at / description
        Added value: +"Where the clip would sit on the timeline, in seconds."
      • removedInput schema / properties / at / title
        Removed value: -"At"
      • addedInput schema / properties / cap / description
        Added value: +"How far a word's claimed duration is trusted, as a multiple of the median. Whisper inflates the word after a collapsed retake until it covers the second take, so believing the claim masks exactly the hole being looked for — 3x is the same multiple a suspect duration is flagged at."
      • removedInput schema / properties / cap / title
        Removed value: -"Cap"
      • addedInput schema / properties / clip_evidence / description
        Added value: +"`auto` (the default) uses the clip's transcript if it has one and its energy envelope otherwise, saying which in the result. `transcript` refuses a clip with none; `energy` forces the envelope even on a clip that has one — sound rather than speech, which counts a sting or a swell too."
      • removedInput schema / properties / clip_evidence / title
        Removed value: -"Clip Evidence"
      • addedInput schema / properties / clip_id / description
        Added value: +"The clip whose placement is being proposed. It need not be on the timeline yet, and usually is not."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • removedInput schema / properties / clip_in / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_in / description
        Added value: +"Where inside the clip the proposed placement starts, in its own source seconds. Unset, its head."
      • removedInput schema / properties / clip_in / title
        Removed value: -"Clip In"
      • addedInput schema / properties / clip_in / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / clip_out / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_out / description
        Added value: +"Where it ends, in the clip's own source seconds. Unset, its end."
      • removedInput schema / properties / clip_out / title
        Removed value: -"Clip Out"
      • addedInput schema / properties / clip_out / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • addedInput schema / properties / max_gap / description
        Added value: +"How short a silence may be and still be swallowed into one speech run, in seconds — a 0.05s gap is not a usable seam."
      • removedInput schema / properties / max_gap / title
        Removed value: -"Max Gap"
      • addedInput schema / properties / min_seam / description
        Added value: +"How wide a gap has to be to be reported as a `clean_seam`, in seconds."
      • removedInput schema / properties / min_seam / title
        Removed value: -"Min Seam"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / vo_clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / vo_clip_id / description
        Added value: +"Which transcript is the VO. Unset, the project's own. The VO always needs a transcript; the placed clip does not."
      • removedInput schema / properties / vo_clip_id / title
        Removed value: -"Vo Clip Id"
      • addedInput schema / properties / vo_clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"speech_overlapArguments"
    • Changedspot_frames18 fields changed
      • addedInput schema / properties / count / description
        Added value: +"How many evenly-spaced frames to pull. They come back ranked darkest-first, with a montage of them as an image."
      • removedInput schema / properties / count / title
        Removed value: -"Count"
      • removedInput schema / properties / fps / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / fps / description
        Added value: +"The rate used to map a frame back to the clip and word it lands near — refused rather than guessed when the render's duration no longer matches the timeline."
      • removedInput schema / properties / fps / title
        Removed value: -"Fps"
      • addedInput schema / properties / fps / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / target / description
        Added value: +"The render to pull frames from."
      • removedInput schema / properties / target / title
        Removed value: -"Target"
      • removedInput schema / properties / times / anyOf
        Removed value: -[
        -  {
        -    "items": {
        -      "type": "number"
        -    },
        -    "type": "array"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / times / description
        Added value: +"Explicit seconds to sample as well as the evenly-spaced ones."
      • addedInput schema / properties / times / items
        Added value: +{
        +  "type": "number"
        +}
      • removedInput schema / properties / times / title
        Removed value: -"Times"
      • addedInput schema / properties / times / type
        Added value: +[
        +  "array",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"spot_framesArguments"
    • Changedsynopsis15 fields changed
      • addedInput schema / properties / clear / description
        Added value: +"Remove this clip's synopsis."
      • removedInput schema / properties / clear / title
        Removed value: -"Clear"
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"The clip to read or write. Omit it to list every clip's synopsis and which are missing one."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / text / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / text / description
        Added value: +"What this footage **is** — the work, the scene, the people. A different fact from a `describe` window, which says what is in front of the camera. Write it yourself: nothing generates one, because a model reading the pixels measurably cannot."
      • removedInput schema / properties / text / title
        Removed value: -"Text"
      • addedInput schema / properties / text / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"synopsisArguments"
    • Changedtail21 fields changed
      • removedInput schema / properties / asset / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / asset / description
        Added value: +"The end card or bumper, as `card:name` — never a clip id. `verify` diffs the render's own transcription against the timeline's words, and a card behind silence adds none of its own, which a media clip would."
      • removedInput schema / properties / asset / title
        Removed value: -"Asset"
      • addedInput schema / properties / asset / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / fade / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / fade / description
        Added value: +"Recorded and echoed, not yet drawn: this build cuts to the card hard, at `seconds`."
      • removedInput schema / properties / fade / title
        Removed value: -"Fade"
      • addedInput schema / properties / fade / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • addedInput schema / properties / reset / description
        Added value: +"Drop the tail entirely. Note a derivation inherits none of it anyway and reports `tail_dropped`."
      • removedInput schema / properties / reset / title
        Removed value: -"Reset"
      • removedInput schema / properties / seconds / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / seconds / description
        Added value: +"The tail's **whole** length, card included — not a hold with `fade` added on top of it."
      • removedInput schema / properties / seconds / title
        Removed value: -"Seconds"
      • addedInput schema / properties / seconds / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"tailArguments"
    • Changedthumbnail11 fields changed
      • addedInput schema / properties / at / description
        Added value: +"Source seconds to pull the frame at. It snaps to a multiple of `interval` first, so a repeated ask for a nearby instant is a cache hit."
      • removedInput schema / properties / at / title
        Removed value: -"At"
      • addedInput schema / properties / clip_id / description
        Added value: +"The clip to pull a frame from."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / interval / description
        Added value: +"The grid `at` snaps to, in seconds."
      • removedInput schema / properties / interval / title
        Removed value: -"Interval"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"thumbnailArguments"
    • Changedtimeline_status5 fields changed
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"timeline_statusArguments"
    • Changedtimeline_view11 fields changed
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"The transcript whose words' fate to report. A clip that is registered but not on the edit still answers — read `off_timeline`, or every word reads `present: false` and looks cut."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / first
        Added value: +{
        +  "default": 0,
        +  "description": "Index into the `words` list to start the window at. 0 by default.",
        +  "type": "integer"
        +}
      • addedInput schema / properties / limit
        Added value: +{
        +  "default": 100,
        +  "description": "Most entries of `words` to return; `words_next` says where to continue. The segments, seams and shots are always whole.",
        +  "type": "integer"
        +}
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"timeline_viewArguments"
    • Changedtranscribe13 fields changed
      • addedInput schema / properties / clip_id / description
        Added value: +"The clip whose own media whisper transcribes."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • removedInput schema / properties / language / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / language / description
        Added value: +"Force a language code, e.g. `en`. Unset, whisper detects it, which it gets wrong on short or noisy clips."
      • removedInput schema / properties / language / title
        Removed value: -"Language"
      • addedInput schema / properties / language / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / model / description
        Added value: +"The whisper model to run, e.g. `small.en`. Larger is slower, and there is no timeout."
      • removedInput schema / properties / model / title
        Removed value: -"Model"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"transcribeArguments"
    • Changedtranscript_checks9 fields changed
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"One clip to re-check. Omit it for every clip that has a transcript."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"transcript_checksArguments"
    • Changedundo5 fields changed
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"undoArguments"
    • Changedunspoken_add21 fields changed
      • addedInput schema / properties / after / description
        Added value: +"A forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start."
      • removedInput schema / properties / after / title
        Removed value: -"After"
      • addedInput schema / properties / clip_id / description
        Added value: +"The transcript holding the word."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • removedInput schema / properties / occurrence / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / occurrence / description
        Added value: +"Disambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at."
      • removedInput schema / properties / occurrence / title
        Removed value: -"Occurrence"
      • addedInput schema / properties / occurrence / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / phrase / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / phrase / description
        Added value: +"Address it by wording instead — but unlike `cue_add`, a phrase matching more than one word is refused rather than bound to an edge: a mark addresses exactly one word."
      • removedInput schema / properties / phrase / title
        Removed value: -"Phrase"
      • addedInput schema / properties / phrase / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / word_index / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / word_index / description
        Added value: +"The word to mark. Give this or `phrase`."
      • removedInput schema / properties / word_index / title
        Removed value: -"Word Index"
      • addedInput schema / properties / word_index / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"unspoken_addArguments"
    • Changedunspoken_detect27 fields changed
      • addedInput schema / properties / apply / description
        Added value: +"Mark the proposals. Off by default, like `reframe_detect`: a wrong mark deletes a real word from every check proofcut has, so read the echoes first."
      • removedInput schema / properties / apply / title
        Removed value: -"Apply"
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"Limit the scan to one transcript."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / language / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / language / description
        Added value: +"Force a language code for that transcription."
      • removedInput schema / properties / language / title
        Removed value: -"Language"
      • addedInput schema / properties / language / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / model / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / model / description
        Added value: +"The whisper model to transcribe the render with, when no `transcript_path` is given."
      • removedInput schema / properties / model / title
        Removed value: -"Model"
      • addedInput schema / properties / model / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / pad / description
        Added value: +"Widen the window each candidate is counted in, in seconds."
      • removedInput schema / properties / pad / title
        Removed value: -"Pad"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / render / description
        Added value: +"The rendered file to judge against — the witness. A word is proposed only where the timeline holds more of it over a span than the render's own transcription heard."
      • removedInput schema / properties / render / title
        Removed value: -"Render"
      • removedInput schema / properties / transcript_path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / transcript_path / description
        Added value: +"An existing transcription of `render`, which is what `verify` leaves in `cache/verify/`. It is never found automatically: a re-render under the same filename would otherwise be judged against the previous render's audio."
      • removedInput schema / properties / transcript_path / title
        Removed value: -"Transcript Path"
      • addedInput schema / properties / transcript_path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"unspoken_detectArguments"
    • Changedunspoken_ls5 fields changed
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"unspoken_lsArguments"
    • Changedunspoken_rm21 fields changed
      • addedInput schema / properties / after / description
        Added value: +"A forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start."
      • removedInput schema / properties / after / title
        Removed value: -"After"
      • addedInput schema / properties / clip_id / description
        Added value: +"The transcript holding the marked word."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • removedInput schema / properties / occurrence / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / occurrence / description
        Added value: +"Disambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at."
      • removedInput schema / properties / occurrence / title
        Removed value: -"Occurrence"
      • addedInput schema / properties / occurrence / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / phrase / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / phrase / description
        Added value: +"Address it by wording instead; it has to resolve to exactly one word."
      • removedInput schema / properties / phrase / title
        Removed value: -"Phrase"
      • addedInput schema / properties / phrase / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / word_index / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / word_index / description
        Added value: +"The marked word. Give this or `phrase`."
      • removedInput schema / properties / word_index / title
        Removed value: -"Word Index"
      • addedInput schema / properties / word_index / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"unspoken_rmArguments"
    • Changedverify29 fields changed
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"Diff against one transcript's expected words rather than all of them."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / language / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / language / description
        Added value: +"Force a language code for it."
      • removedInput schema / properties / language / title
        Removed value: -"Language"
      • addedInput schema / properties / language / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / model / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / model / description
        Added value: +"The whisper model for the single-pass transcription."
      • removedInput schema / properties / model / title
        Removed value: -"Model"
      • addedInput schema / properties / model / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / overlap / description
        Added value: +"How far each window overlaps the one before, in seconds."
      • removedInput schema / properties / overlap / title
        Removed value: -"Overlap"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / render / description
        Added value: +"The finished render to transcribe and diff against the timeline."
      • removedInput schema / properties / render / title
        Removed value: -"Render"
      • removedInput schema / properties / transcript_path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / transcript_path / description
        Added value: +"An existing transcription of `render` — what a previous run cached and reported as `heard_transcript`. Pass it back to re-diff without spending the minutes again."
      • removedInput schema / properties / transcript_path / title
        Removed value: -"Transcript Path"
      • addedInput schema / properties / transcript_path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / window / description
        Added value: +"Length of each window in the windowed pass, in seconds."
      • removedInput schema / properties / window / title
        Removed value: -"Window"
      • addedInput schema / properties / windowed / description
        Added value: +"Transcribe in short overlapping windows instead of one pass. **A clean single-pass result is not proof** — one pass collapses an immediate repeat the same way the source transcript did, and three surviving retakes passed a correct single-pass run on a real video. It costs a run over twice the audio and a smaller model."
      • removedInput schema / properties / windowed / title
        Removed value: -"Windowed"
      • removedInput schema / title
        Removed value: -"verifyArguments"
    • Changedvo_extend27 fields changed
      • addedInput schema / properties / after / description
        Added value: +"A forward cursor over a phrase's matches: any match at or before this word index is skipped. -1, the default, means from the start."
      • removedInput schema / properties / after / title
        Removed value: -"After"
      • addedInput schema / properties / clip_id / description
        Added value: +"The track the gap opens in — the VO."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • removedInput schema / properties / occurrence / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / occurrence / description
        Added value: +"Disambiguate a phrase by count when it matches more than once, **1-based** in transcript order among the matches after `after`: 1 is the first, 2 the second. Unset, an ambiguous phrase is refused — listing every candidate's range and text — rather than guessed at."
      • removedInput schema / properties / occurrence / title
        Removed value: -"Occurrence"
      • addedInput schema / properties / occurrence / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / phrase / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / phrase / description
        Added value: +"Address it by wording instead. A phrase binds to its **last** word here, which is this tool's own meaning: the last word before the gap."
      • removedInput schema / properties / phrase / title
        Removed value: -"Phrase"
      • addedInput schema / properties / phrase / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • removedInput schema / properties / seconds / anyOf
        Removed value: -[
        -  {
        -    "type": "number"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / seconds / description
        Added value: +"How long the hold runs. An editorial call this makes no attempt to derive."
      • removedInput schema / properties / seconds / title
        Removed value: -"Seconds"
      • addedInput schema / properties / seconds / type
        Added value: +[
        +  "number",
        +  "null"
        +]
      • removedInput schema / properties / word_index / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / word_index / description
        Added value: +"The last word **before** the gap; the hold opens immediately after that word's own end. It has to be on the timeline: an index naming cut material is refused rather than guessed at."
      • removedInput schema / properties / word_index / title
        Removed value: -"Word Index"
      • addedInput schema / properties / word_index / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"vo_extendArguments"
    • Changedvo_synth37 fields changed
      • addedInput schema / properties / candidates / description
        Added value: +"How many seeds to render and rank. Seed moves a render more than the reference does, which is why this ranks rather than renders once."
      • removedInput schema / properties / candidates / title
        Removed value: -"Candidates"
      • removedInput schema / properties / clip_id / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / clip_id / description
        Added value: +"With `word_index`, the track to splice the winner into. Omitted, nothing is spliced and the renders are just ranked."
      • removedInput schema / properties / clip_id / title
        Removed value: -"Clip Id"
      • addedInput schema / properties / clip_id / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / flat_floor / description
        Added value: +"Below this much voiced pitch movement (semitones) a render starts paying the flatness penalty. Likeness alone keeps the flattest read, because sims in one pool differ by thousandths while spread differs by semitones."
      • removedInput schema / properties / flat_floor / title
        Removed value: -"Flat Floor"
      • addedInput schema / properties / flat_weight / description
        Added value: +"How much likeness to subtract per semitone of flatness under the floor. 0 restores likeness-only ranking."
      • removedInput schema / properties / flat_weight / title
        Removed value: -"Flat Weight"
      • removedInput schema / properties / lexicon / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / lexicon / description
        Added value: +"A `{\"say\": {…}, \"hear\": {…}}` file: `say` respells what the model is given, `hear` folds whisper's spelling back to the script's before the WER is scored. Defaults to the project's own `lexicon.json` if it has one."
      • removedInput schema / properties / lexicon / title
        Removed value: -"Lexicon"
      • addedInput schema / properties / lexicon / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / max_seconds / description
        Added value: +"Length cap per render. One that hits it is reported `capped` and never wins while an uncapped one exists — a 21s reference once ran every render to 655s."
      • removedInput schema / properties / max_seconds / title
        Removed value: -"Max Seconds"
      • removedInput schema / properties / path / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / path / description
        Added value: +"The project directory to act on. Omit it — the usual case — when this server is bound to a project (started as `proofcut -C DIR mcp`, or inside a project; `ping` says which): it then resolves to that one bound project, a relative path resolves against it, and a path outside it is refused by name. Unbound, `path` is the whole address and omitting it refuses rather than guessing."
      • removedInput schema / properties / path / title
        Removed value: -"Path"
      • addedInput schema / properties / path / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • addedInput schema / properties / plan / description
        Added value: +"Resolve the whole call and report what it would do, writing nothing. Prefer it over doing the thing and undoing it."
      • removedInput schema / properties / plan / title
        Removed value: -"Plan"
      • addedInput schema / properties / readback / description
        Added value: +"Transcribe the winner with whisper and report `heard`/`wer`. On by default: a clone that sounds right and says the wrong words is the failure nothing else sees. The numbers are a report, never a gate."
      • removedInput schema / properties / readback / title
        Removed value: -"Readback"
      • addedInput schema / properties / seed / description
        Added value: +"First seed of the range; seeds `seed .. seed+candidates-1` render in one process. A new range renders only what the cache lacks."
      • removedInput schema / properties / seed / title
        Removed value: -"Seed"
      • addedInput schema / properties / text / description
        Added value: +"What the voice says. It is respelled first through the project's `lexicon.json` `say` folds, if one exists — the fix for a mispronounced name."
      • removedInput schema / properties / text / title
        Removed value: -"Text"
      • removedInput schema / properties / voice / anyOf
        Removed value: -[
        -  {
        -    "type": "string"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / voice / description
        Added value: +"A directory holding `ref.wav` + `ref.txt`, the ≈19s reference the clone is zero-shot from. Unset, `$PROOFCUT_TTS_VOICE`. There is no built-in voice, and none ships in the repo: a voice is somebody's recorded speech."
      • removedInput schema / properties / voice / title
        Removed value: -"Voice"
      • addedInput schema / properties / voice / type
        Added value: +[
        +  "string",
        +  "null"
        +]
      • removedInput schema / properties / word_index / anyOf
        Removed value: -[
        -  {
        -    "type": "integer"
        -  },
        -  {
        -    "type": "null"
        -  }
        -]
      • addedInput schema / properties / word_index / description
        Added value: +"The word to splice the winner in right after, through `vo_extend`'s own mechanism — so the same one-way consequences follow (melt routing, `restore` refusing across the seam)."
      • removedInput schema / properties / word_index / title
        Removed value: -"Word Index"
      • addedInput schema / properties / word_index / type
        Added value: +[
        +  "integer",
        +  "null"
        +]
      • removedInput schema / title
        Removed value: -"vo_synthArguments"
  6. 92 tool updatesv0.24.0
    • First observedadd_captions
    • First observedassets
    • First observedattach_transcript
    • First observedattenuate_noises
    • First observedattribute_speakers
    • First observedbroll_brief
    • First observedbuild_shots
    • First observedcanvas
    • First observedcaption_style
    • First observedcaption_view
    • First observedcard_new
    • First observedcard_reauthor
    • First observedcard_render
    • First observedcard_safe_zones
    • First observedcard_templates
    • First observedcheck_black
    • First observedcheck_frames
    • First observedclip_rm
    • First observedclip_role
    • First observedcontact_sheet
    • First observedcontinuity_accept
    • First observedcontinuity_check
    • First observedcontinuity_ls
    • First observedcontinuity_reject
    • First observedcue_add
    • First observedcue_ls
    • First observedcue_reresolve
    • First observedcue_rm
    • First observedcut_by_time
    • First observedcut_by_transcript
    • First observeddescribe
    • First observeddescribe_ls
    • First observeddoctor
    • First observedexport
    • First observedfilm_check
    • First observedfinish_check
    • First observedfinish_report
    • First observedfonts
    • First observedfootage_sheet
    • First observedget_transcript
    • First observedhead
    • First observedhear
    • First observedhold_add
    • First observedhold_check
    • First observedhold_ls
    • First observedhold_rm
    • First observedhold_under
    • First observedhold_under_rm
    • First observedimport_edit
    • First observedimport_media
    • First observedinit
    • First observedlist_media
    • First observedlocate
    • First observedmigrate_project
    • First observedmusic
    • First observedpack_activate
    • First observedpack_apply
    • First observedpack_apply_captions
    • First observedpack_show
    • First observedpack_status
    • First observedping
    • First observedproperties
    • First observedproxy_transcode
    • First observedreel
    • First observedreframe
    • First observedreframe_coverage
    • First observedreframe_detect
    • First observedreframe_sheet
    • First observedresolve_phrase
    • First observedrestore
    • First observedreview_add
    • First observedreview_list
    • First observedreview_verdict
    • First observedseed_timeline
    • First observedshot_sheet
    • First observedspeech_overlap
    • First observedspot_frames
    • First observedsynopsis
    • First observedtail
    • First observedthumbnail
    • First observedtimeline_status
    • First observedtimeline_view
    • First observedtranscribe
    • First observedtranscript_checks
    • First observedundo
    • First observedunspoken_add
    • First observedunspoken_detect
    • First observedunspoken_ls
    • First observedunspoken_rm
    • First observedverify
    • First observedvo_extend
    • First observedvo_synth

TDQS

A3.6/5.0

Scored across 132 tools

Disambiguation3/5

Domain prefixes (cue_, caption_, graphic_, card_, sound_, hold_, reframe_) create useful separation, but several clusters are genuinely easy to mis-select: hold_under vs hold_add, restore vs undo, verify vs film_check vs finish_check vs check_frames, and the five *_sheet tools all return similar-looking image tiles. The extremely detailed descriptions rescue most ambiguity, but at 132 tools an agent will struggle to pick correctly under time pressure.

Naming Consistency4/5

The dominant pattern is consistent verb_noun with strong domain prefixes (cue_add/cue_rm/cue_ls, overlay_add/ls/rm, inset_add/ls/rm, retime_add/ls/rm, unspoken_add/rm/ls/detect). Deviations exist: bare verbs (ping, export, verify, transcribe, restore, locate, undo), mixed styles (cut_by_transcript/cut_by_time against restore), and check appearing as both prefix (check_frames, check_black) and suffix (film_check, finish_check, hold_check).

Tool Count2/5

132 tools is well into the extreme range by any calibration, even though the server covers a genuinely broad post-production domain — transcription, editing, captions, graphics, cards, packs, reframing, sound design, verification, and review. Each subdomain is reasonably scoped on its own, but the aggregate surface is overwhelming for an agent to navigate coherently.

Completeness4/5

For its enormous stated scope, coverage is remarkably thorough: full transcript lifecycle, timeline editing with undo, cues/overlays/insets, captions with lexicon and spans, cards/graphics/packs, reframing with detection and sheets, sound generation, holds, retiming, and multiple verification layers. Notable gaps: review_add is referenced by review_verdict and review_list but absent from the tool set, creating a dead end for the review workflow; there is no graphic_rm or card_rm for removing those assets.

Maintenance

ActivityActive
ResponsivenessResponsive

Related MCP Connectors

Related MCP Servers