Skip to content

feat: mp3 output, video_to_sound output_format, v2v-music ducking + segments - #22

Merged
spencer-zqian merged 2 commits into
mainfrom
feat/mp3-and-v2v-music-params
Aug 1, 2026
Merged

feat: mp3 output, video_to_sound output_format, v2v-music ducking + segments#22
spencer-zqian merged 2 commits into
mainfrom
feat/mp3-and-v2v-music-params

Conversation

@spencer-zqian

Copy link
Copy Markdown
Contributor

Syncs the client with three API changes shipped in sonilo-api-dashboard (#191, #192, #195).

mp3 output container

text_to_music and video_to_music accept output_format="mp3" (320 kbps) alongside "m4a" and "wav".

The async gate widened with it. _resolve_music_mode previously tested output_format == "wav"; any container other than the m4a default is a finalize-time transcode and needs async, so it now tests != "m4a". Without that, output_format="mp3" would have silently streamed and been ignored — the new test confirms it: reverting just that line turns test_non_m4a_formats_force_async[mp3] red.

CLI --format accepts mp3 on text-to-music and video-to-music, and anything but m4a implies async.

video_to_sound gains output_format

Defaults to wav; applies to the combined music + SFX track only, since the music and sfx stems keep their native formats.

video_to_video_sound does not take it — that endpoint always muxes the mix into an mp4. build_v2s_parts takes it keyword-only with a None default and the VideoToVideoSound resource simply never passes it, so video_to_video_sound.py is untouched by this PR.

video_to_video_music gains ducking + segments

ducking is default-ON server-side, so it is omitted from the request when unset rather than sent as an explicit "false" — the same rule build_v2s_parts already follows. segments takes the same Segment shape as video_to_music and is JSON-serialized by the shared build_v2m_parts.

Added to submit() and generate() on both the sync and async resources (four methods), with generate() forwarding both through.

Behavior changes documented

/v1/video-to-video-music was rebuilt on the video-to-music pipeline plus a local ffmpeg mux, which changed three things users need to know, now in the README:

  • The default audio changed. The returned video carries the source's speech with the music ducked under it; it was previously music-only. ducking=False restores the old sound.
  • Input codecs are restricted. The picture is copied without re-encoding, so the source must carry H.264, H.265/HEVC, VP9 or AV1 (mp4/mov/m4v/webm). Animated gif and VP8 webm are rejected.
  • 360-second limit.

Also fixed: version drift

src/sonilo/_version.py and sonilo-cli/src/sonilo_cli/__init__.py carry the version independently of their pyproject.toml, and the existing test only asserts the client-identity header matches __version__ — self-consistent, so it cannot catch the two drifting apart. Both are bumped here alongside the pyprojects; without that the published package would have reported the old version in X-Sonilo-Client-Version.

Testing

226 tests pass (was 218). Eight new ones cover: wav and mp3 both forcing async, m4a still streaming, output_format emitted and omitted on video-to-sound, ducking omitted when unset, ducking=False on the wire, and segments JSON serialization.

sonilo 0.9.0 → 0.10.0, sonilo-cli 0.6.0 → 0.7.0. Not tagged — this PR is for review only.

🤖 Generated with Claude Code

https://claude.ai/code/session_01MjRsj2vTCwnUQYRc7hP41D

…egments

- output_format accepts 'mp3' (320 kbps) on text_to_music and video_to_music.
  The async gate widened with it: any container other than the m4a default is
  a finalize-time transcode, where the check previously named 'wav'. Without
  that, output_format='mp3' would have silently streamed and been ignored.
- video_to_sound gains output_format (wav default), applying to the combined
  track only. video_to_video_sound does not take it -- that endpoint always
  returns an mp4 -- so build_v2s_parts takes it keyword-only and the video
  resource simply never passes it.
- video_to_video_music gains ducking and segments. ducking is default-ON
  server-side, so it is omitted when unset rather than sent as 'false'.
- Documents the v2v-music behavior change: the returned video's audio now
  carries the source speech with music ducked under it, the input must carry
  H.264/HEVC/VP9/AV1, and the limit is 360 seconds.

sonilo 0.9.0 -> 0.10.0, sonilo-cli 0.6.0 -> 0.7.0.
@sapient-app

sapient-app Bot commented Aug 1, 2026

Copy link
Copy Markdown

Sapient docs evals

Waiting for the staging docs URL before running evals.

Sapient will start the selected PR evals automatically when GitHub reports a successful docs deployment for this PR. This usually happens within 15 minutes.

Commit: b3aad0c
Status: waiting for staging docs URL

sonilo-cli pins the core package to one minor (>=0.8.0,<0.9), so bumping
sonilo to 0.10.0 without moving the pin made the workspace unresolvable --
CI's editable install of all three packages failed with ResolutionImpossible.
A pre-existing local venv hides this: pip only re-resolves on a fresh
install, which is why the suite passed locally.
@spencer-zqian
spencer-zqian merged commit 6f92c8c into main Aug 1, 2026
2 checks passed
@spencer-zqian
spencer-zqian deleted the feat/mp3-and-v2v-music-params branch August 1, 2026 00:50
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