Skip to main content

clipwright-render

MCP tool to realize OTIO timelines with FFmpeg.

Clipwright is a toolkit centered on "separation of detection (detect) and application (render)". detect-type tools only return annotations to OTIO without modifying media, and this single clipwright-render tool performs all realization in one pass (completes segment extraction, concatenation, and trimming in a single transcode pass).


Prerequisites

This tool targets materials and timelines that meet the following conditions. Inputs outside these conditions return errors.

Condition Details
Frame rate CFR (constant frame rate) only. VFR (variable frame rate) not supported
Resolution Fixed resolution only. Materials with per-frame resolution changes not supported
Source count Only single source (1 file) in timeline
Video track Required. No video not supported
Audio track 0 or 1 stream only. If multiple, first audio stream adopted

Out of Scope (Planned for Future)

  • VFR / resolution-changing materials
  • Multiple source file concatenation
  • Subtitle burn-in
  • Transitions
  • 2+ video tracks in timeline

FFmpeg Setup

FFmpeg / FFprobe are not bundled with this package. Install in your environment.

# macOS (Homebrew)
brew install ffmpeg

# Ubuntu / Debian
sudo apt install ffmpeg

If ffmpeg / ffprobe are on PATH, it works as-is. In environments where PATH cannot be modified, explicitly specify paths with environment variables.

export CLIPWRIGHT_FFMPEG=/usr/local/bin/ffmpeg
export CLIPWRIGHT_FFPROBE=/usr/local/bin/ffprobe

About license: This wrapper package itself is MIT licensed. Since FFmpeg binaries are not bundled, FFmpeg's LGPL / GPL redistribution obligations do not apply to this wrapper. Verify FFmpeg's own license (LGPL v2.1 / GPL v2) in your environment.


Installation

uv sync

MCP Client Registration

Add the following to your MCP client configuration (e.g. .mcp.json):

{
  "mcpServers": {
    "clipwright-render": {
      "command": "clipwright-render",
      "args": []
    }
  }
}

If ffmpeg / ffprobe are not on PATH, pass them as environment variables:

{
  "mcpServers": {
    "clipwright-render": {
      "command": "clipwright-render",
      "args": [],
      "env": {
        "CLIPWRIGHT_FFMPEG": "/path/to/ffmpeg",
        "CLIPWRIGHT_FFPROBE": "/path/to/ffprobe"
      }
    }
  }
}

Usage

MCP Tool (clipwright_render)

Invoked from Claude / agents via MCP.

{
  "tool": "clipwright_render",
  "arguments": {
    "timeline": "/path/to/timeline.otio",
    "output": "/path/to/output.mp4",
    "dry_run": false,
    "options": {
      "video_codec": "libx264",
      "audio_codec": "aac",
      "width": 1920,
      "height": 1080,
      "fps": 29.97,
      "crf": 23,
      "overwrite": false
    }
  }
}

Arguments

Argument Type Required Description
timeline string yes Input OTIO file path
output string yes Output file path (.mp4 / .mkv / .mov / .webm)
dry_run bool optional (default false) If true, returns plan without actual rendering
options object optional Output options (see RenderOptions below)

RenderOptions

Field Type Description
video_codec string | null Video codec (e.g. libx264, default: inherit from source)
audio_codec string | null Audio codec (e.g. aac, default: inherit from source)
width int | null Output width (must be set with height)
height int | null Output height (must be set with width)
fps float | null Output frame rate
crf int | null Quality CRF value (0-51)
overwrite bool If true, overwrite existing output file (default false)

width / height must both be specified or both null. Specifying only one is an error.

Return Value (Success)

{
  "ok": true,
  "summary": "2 clips → 45.2 sec / 42.1 MB / outputs/out.mp4",
  "data": {
    "output_path": "/path/to/output.mp4",
    "duration_sec": 45.2,
    "size_bytes": 44150784,
    "clip_count": 2
  },
  "artifacts": ["/path/to/output.mp4"],
  "warnings": []
}

Return Value (dry_run)

{
  "ok": true,
  "summary": "dry_run: 2 segments / estimated 45.2 sec / approx 42.1 MB",
  "data": {
    "dry_run": true,
    "clip_count": 2,
    "estimated_duration_sec": 45.2,
    "estimated_size_bytes": 44150784,
    "ffmpeg_args": ["ffmpeg", "-i", "source.mp4", "-filter_complex", "..."]
  },
  "artifacts": [],
  "warnings": []
}

estimated_size_bytes is calculated from source bitrate obtained by FFprobe and output duration. If bitrate cannot be obtained, it is null with reason in warnings. If any of video_codec / width / height / fps / crf are specified, estimation based on source bitrate may differ significantly from actual, so warnings includes a note.

Return Value (Error)

{
  "ok": false,
  "error": {
    "code": "FILE_NOT_FOUND",
    "message": "Timeline file not found: /path/to/timeline.otio",
    "hint": "Verify the file path"
  }
}

Main error codes:

Code Meaning
FILE_NOT_FOUND Timeline / source / output directory does not exist
INVALID_INPUT Invalid extension / existing output with overwrite=false / empty timeline
PATH_NOT_ALLOWED Output path is same as input source
UNSUPPORTED_OPERATION No video / multiple sources / Transition / 2+ video tracks
PROBE_FAILED FFprobe analysis failed
SUBPROCESS_FAILED FFmpeg exit code non-zero
SUBPROCESS_TIMEOUT FFmpeg timeout (max(300, duration_sec × 10) seconds)
DEPENDENCY_MISSING ffmpeg / ffprobe not found in PATH or environment variables

Testing

Unit Tests (FFmpeg Not Required)

uv run --package clipwright-render pytest clipwright-render/tests/ -m "not integration"

Integration Tests (FFmpeg Required)

Tests that verify single-source concatenation and output using actual FFmpeg. Automatically skipped in environments without FFmpeg.

Set environment variables before running:

export CLIPWRIGHT_FFMPEG=/path/to/ffmpeg
export CLIPWRIGHT_FFPROBE=/path/to/ffprobe

uv run --package clipwright-render pytest clipwright-render/tests/ -m integration

Integration tests skip if CLIPWRIGHT_FFMPEG / CLIPWRIGHT_FFPROBE are not set. Set these variables when running in CI.


License

This wrapper package itself is MIT licensed.

Since FFmpeg binaries are not bundled, FFmpeg's LGPL v2.1 / GPL v2 redistribution obligations do not apply to this package.

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

clipwright_render-0.5.0.tar.gz (42.0 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

clipwright_render-0.5.0-py3-none-any.whl (44.6 kB view details)

Uploaded Python 3

File details

Details for the file clipwright_render-0.5.0.tar.gz.

File metadata

  • Download URL: clipwright_render-0.5.0.tar.gz
  • Upload date:
  • Size: 42.0 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for clipwright_render-0.5.0.tar.gz
Algorithm Hash digest
SHA256 84037ab9408f9bf11ac2c425a740520f3020781f7dce6e649d1e5dbfeda2ed3c
MD5 5ab7053812d4c9dc2a9e3d3b06634378
BLAKE2b-256 800f73f10e25d8803e4530d408a0ecb3d14bdec3d1163899924ccc162d8ba150

See more details on using hashes here.

Provenance

The following attestation bundles were made for clipwright_render-0.5.0.tar.gz:

Publisher: publish.yml on satoh-y-0323/clipwright

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file clipwright_render-0.5.0-py3-none-any.whl.

File metadata

File hashes

Hashes for clipwright_render-0.5.0-py3-none-any.whl
Algorithm Hash digest
SHA256 0b2c6ed87376e957ee2eb8f52d01b5669d92278275ca4be480f9612273700bcf
MD5 1c9409d1ce77860f5d7aacbd59f3032a
BLAKE2b-256 c4a2a193a516dfcbd3357aa3dfd9e9b37f3aee3ffcf1c29461d8f5b135f59240

See more details on using hashes here.

Provenance

The following attestation bundles were made for clipwright_render-0.5.0-py3-none-any.whl:

Publisher: publish.yml on satoh-y-0323/clipwright

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page