Skip to content

fix(remotion): stage local assets into public/ before Explainer render#328

Open
amitm7 wants to merge 1 commit into
calesthio:mainfrom
amitm7:fix/remotion-public-asset-staging
Open

fix(remotion): stage local assets into public/ before Explainer render#328
amitm7 wants to merge 1 commit into
calesthio:mainfrom
amitm7:fix/remotion-public-asset-staging

Conversation

@amitm7

@amitm7 amitm7 commented Jul 7, 2026

Copy link
Copy Markdown

Summary

Fixes a production bug in the Remotion render path: local narration and music files fail to load when passed as absolute filesystem paths. Hybrid / real-photo workflows (user photos + local TTS audio) failed unless contributors manually copied assets into remotion-composer/public/.

This PR adds automatic asset staging before npx remotion render — the same pattern hyperframes_compose already uses via _resolve_and_stage_assets, but was missing from the Remotion Explainer path.

Related issue

Refs — (no linked issue; discovered during hybrid real-photo production)

Background (what existed)

Area Prior behavior
video_compose._remotion_render Rewrote local image paths to file:// URIs
Explainer resolveAsset() Absolute → file://; relative → staticFile() under public/
hyperframes_compose Already copies assets into workspace before render
Compose-director skills Mentioned public/ staging for agents, but no tool implemented it for Remotion

Failure observed:

Not allowed to load local resource: file:///.../narration.mp3
Could not play audio with src file://...

Headless Chromium blocks file:// for <Audio>. Manual public/ copy was the only workaround — undocumented.

Gap

  1. No Remotion asset staging (unlike HyperFrames)
  2. file:// rewrite incompatible with headless audio
  3. Undocumented contract between skills and tooling
  4. Mechanical step left to ad-hoc agent scripts instead of video_compose

What we created

  • lib/remotion_asset_staging.py — copies local cuts[].source, audio.narration.src, audio.music.src into remotion-composer/public/<slug>/; rewrites props to staticFile() paths (<slug>/file.mp3); dedupes shared sources; skips remote https:// URLs
  • video_compose._remotion_render — calls staging before render; removes file:// rewrite; writes metadata.remotion_asset_staging report
  • Tests — 7 unit + 1 integration (mocked Remotion CLI)
  • Skills — hybrid + explainer compose-director.md document the contract

Changes

  • Add lib/remotion_asset_staging.py
  • Update tools/video/video_compose.py (_remotion_render)
  • Add tests/lib/test_remotion_asset_staging.py
  • Add tests/tools/test_video_compose_remotion_staging.py
  • Update skills/pipelines/hybrid/compose-director.md
  • Update skills/pipelines/explainer/compose-director.md
  • Add docs/contributions/pr-remotion-public-asset-staging.md (full contribution write-up)
  • Excluded: unrelated package-lock.json peer-metadata churn

Testing

python -m pytest tests/lib/test_remotion_asset_staging.py -q
python -m pytest tests/tools/test_video_compose_remotion_staging.py -q
  • 8/8 tests passed locally
  • Manual: hybrid project with local JPG + narration.mp3 renders without manual public/ copy

Architecture

  • Mechanical staging only (agent-first; no creative orchestration in Python)
  • No schema changes, no silent runtime swap
  • Aligns with docs/PR_REVIEW_GUIDE.md render-runtime scenario

Checklist

  • The change is focused on a single logical concern.
  • I ran the relevant tests locally.
  • I updated docs/skills where behavior changed.
  • No unrelated files are included in the diff.

Made with Cursor

Headless Chromium blocks file:// audio in Remotion renders. Copy local cut
sources and narration/music into remotion-composer/public/<slug>/ and rewrite
props to staticFile-compatible paths. Mirrors hyperframes_compose staging.

Co-authored-by: Cursor <cursoragent@cursor.com>
@amitm7 amitm7 requested a review from calesthio as a code owner July 7, 2026 21:28
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant