타임라인 합성
이 문서는 영문 원고를 AI로 번역한 내용이라 표현이 어색할 수 있습니다.
현재 SoT. Timeline 1.0 compose(
sume/timeline-1.0/compose, #3976). dest와 prod. 이것은 샷 하나를 만듭니다. 조립 — 시퀀스, 트랜지션, 오디오 스파인 — 은 Timeline 1.0에 남습니다. 이미지 다음 비디오를 이어 붙이는 것은 compose 모드가 아닙니다: 렌더의 인접video[]슬롯이 이미 그렇게 합니다.
Compose는 스틸 하나 + 비디오 하나를 받아 둘 다 한 화면에 있는
MP4 하나를 반환합니다. 서버가 워커 미디어 런타임에서 ffmpeg를
컴파일합니다(apps/api/src/routes.ts createTimelineV1Compose /
submitSumeTimelineComposeJob;
packages/timeline-compiler/src/compose.ts). 호출자는 필터그래프,
코덱, 셸 조각을 보내지 않습니다.
GET /v1/timeline-1.0/compose/:id는 없습니다. Job 봉투로 폴링하세요:
호스티드 MCP: timeline_compose(packages/mcp-server/src/mcp.ts).
쓰기는 idempotency_key가 필요합니다(OAuth에서는 mcp:write). 흐름:
timeline_compose → jobs_wait → jobs_result → video_url을
timeline_create video[]에 넣습니다.
stack vs overlay의 HTTP 필드는 **operation**이지 mode가 아닙니다.
mode는 평소의 async / sync / webhook 통신 옵션입니다.
합성 만들기
필수: operation(stack | overlay), image.url, video.url. 두
URL 모두 이 워크스페이스의 media.sume.com 아티팩트 또는 에셋이어야
합니다. image.url은 스틸이어야 하고(compose_image_not_still),
video.url은 비디오여야 합니다(compose_video_not_video). 먼저
가져오세요(POST /v1/media-imports). Idempotency-Key는 필수입니다.
선택: layout, output, video.source_in, video.duration, 평소의
mode / webhook_url / wait_timeout_seconds 통신 필드.
기본 mode는 **async**입니다. mode: "sync"를 주면 최대 30초
기다리고 끝난 Job을 200으로 주거나, 202로 폴링합니다.
출력 길이는 항상 비디오 레이어에서 옵니다(video.duration, 없으면
source_in부터 파일 나머지). 스틸은 클립 전체 동안 홀드되며 길이를
늘릴 수 없습니다. 천장 300초
(TIMELINE_COMPOSE_MAX_DURATION_SECONDS). 소스를 넘으면 클램프됩니다
(compose_duration_clamped_to_source).
성공한 submit은 Job을 반환합니다(model: sume/timeline-1.0/compose).
result_ready이면 GET /v1/jobs/:id/result는
kind: timeline_compose이고 video_url(새 artf_)과
duration_seconds를 줍니다. 그 MP4를
Timeline 1.0 video[]에 넣으세요.
공개 요금: Job당 $0.02 정액(TIMELINE_COMPOSE_PUBLIC_PRICING;
GET /v1/catalog에서 확인). video.duration이 워커 프로브 전까지
생략될 수 있어서 정액입니다. 프로바이더 추론 없음 — 워커 ffmpeg만.
기본 출력은 1080×1920 MP4이고 프레임레이트는 비디오 레이어 고유의
레이트입니다 — 프레임을 반복하거나 버리지 않는 유일한 레이트. 클립 레이트와
다른 output.fps를 명시하면 output_fps_resamples_sources 경고가
납니다. 조립할 타임라인에 맞춰
output을 두면 샷이 두 번 스케일되지 않습니다.
오디오는 비디오에서 통과합니다. 무음 비디오는 경고
(compose_video_has_no_audio)이지 실패가 아닙니다 — 클립은 렌더되고,
조립 때 Timeline 1.0 스파인이 오디오를 공급합니다.
레이아웃
stack은 한 프레임의 두 영역을 타일합니다. 기본값
horizontal / top / 0.5가 반배너입니다(위 스틸, 아래 비디오).
ratio는 스틸 몫(0.1–0.9)이고 비디오가 나머지를 정확히 가져갑니다.
layout 키 | stack | overlay |
|---|---|---|
split | horizontal | vertical | 불가 |
image_region | 가로 분할은 top | bottom; 세로 분할은 left | right | 불가 |
ratio | 스틸이 차지하는 프레임 비율 | 불가 |
image_fit / video_fit | cover | contain | stretch (compose fit에 blur 없음) | video_fit만 |
position | 불가 | top | center | bottom |
width_ratio | 불가 | 너비의 0.05–1 (기본 0.9); 플레이트는 종횡비 유지 |
margin_ratio | 불가 | 높이의 0–0.45 (기본 0.05) |
stack 키와 overlay 키를 섞으면 400
(compose_stack_takes_no_overlay_layout /
compose_overlay_takes_no_stack_layout).
축과 안 맞는 region은 compose_image_region_wrong_axis입니다.
거부 (안정 코드)
| 코드 | 언제 |
|---|---|
compose_image_not_still | image.url이 스틸이 아님. |
compose_video_not_video | video.url이 비디오가 아님. |
compose_image_region_wrong_axis | 가로 분할에 left/right, 또는 세로 분할에 top/bottom. |
compose_stack_takes_no_overlay_layout / compose_overlay_takes_no_stack_layout | 레이아웃 어휘를 섞음. |
compose_duration_clamped_to_source | 경고: video.duration이 파일을 넘음. Job은 성공합니다. |
compose_video_has_no_audio | 경고: 무음 비디오 소스. Job은 성공합니다. |
unsupported_media_source / source_not_found | 호스트 밖 또는 죽은 URL. |
| 프로바이더 / ffmpeg 키 | 400 — filtergraph, ffmpeg_args, codec, crf 등. |
호스트 밖 URL(https://example.com/…)은 admit에서 거부됩니다. 먼저
가져오세요.
이 표면이 아닌 것
| 필요 | 사용 |
|---|---|
| 여러 클립 시퀀스 | Timeline 1.0 |
| 오디오 concat / split로 재사용 파일 | 타임라인 오디오 |
클립 하나의 [start, end) | 비디오 트림 |
| 픽셀 패스 (dim / crop) | 비디오 필터 |
| 오디오 트랙을 내구성 wav / mp3로 | 오디오 분리 |

