Skip to content

MP4: Make most Mp4Properties fields Option<_>#662

Closed
truffle-dev wants to merge 2 commits into
Serial-ATA:mainfrom
truffle-dev:mp4-properties-option-types
Closed

MP4: Make most Mp4Properties fields Option<_>#662
truffle-dev wants to merge 2 commits into
Serial-ATA:mainfrom
truffle-dev:mp4-properties-option-types

Conversation

@truffle-dev

Copy link
Copy Markdown

Closes #661.

Per your note on the issue: only duration, ftyp, and drm_protected are guaranteed to be set. The rest now match the public FileProperties contract.

Mp4Properties.codec, overall_bitrate, audio_bitrate, sample_rate, and channels become Option<_>. Every write site wraps in Some(_). The From<Mp4Properties> for FileProperties conversion forwards the Options directly instead of wrapping plain values, so codecs the dispatch match doesn't handle (today ec-3, opus, wave, dts) no longer leak the placeholder 0 reads from read_stsd into the public API.

One internal read site changes too: the audio-bitrate fallback condition at mp4/properties.rs:685 goes from properties.audio_bitrate == 0 to matches!(properties.audio_bitrate, None | Some(0)), preserving the prior "no codec-specific bitrate was computed" semantics.

Existing taglib tests and the four expected_mp4_*_properties fixtures in src/properties/tests.rs are updated to wrap their expectations in Some(_). Full suite passes locally (797 tests, 0 failed).

Breaking change for downstream callers of Mp4Properties::channels(), sample_rate(), audio_bitrate(), overall_bitrate(), and codec() — getter return types changed to Option<_>. Added to the Changed section in CHANGELOG.md alongside the existing #650 / #652 unreleased breakages.

Closes Serial-ATA#661.

Per the maintainer note on Serial-ATA#661: only `duration`, `ftyp`, and
`drm_protected` are guaranteed to be set. The rest now match the public
`FileProperties` contract.

`Mp4Properties.codec`, `overall_bitrate`, `audio_bitrate`, `sample_rate`,
and `channels` become `Option<_>`. Every write wraps in `Some(_)`. The
`From<Mp4Properties> for FileProperties` conversion forwards the Options
directly instead of wrapping plain values, so codecs the dispatch match
doesn't handle (today `ec-3`, `opus`, `wave`, `dts`) no longer leak the
placeholder `0` reads from `read_stsd` into the public API.

The internal fallback condition at line 685 changes from
`properties.audio_bitrate == 0` to `matches!(.., None | Some(0))`,
preserving the prior semantics for "no codec-specific bitrate was
computed."
The Option type-change in the previous commit covered the public
contract, but the runtime still leaked `Some(0)` for codecs the
descriptor match doesn't dispatch. `read_stsd` reads the QuickTime
sound sample-entry slots (`channels`, `sample_rate`) before
dispatching, and the `_` arm fell through with those placeholder
reads still in place.

Explicitly clear both fields in the `_` arm so unknown codecs
(today `ec-3`, `opus`, `wave`, `dts`) return `None` instead of
`Some(0)`. Regression test patches the `mp4a` FourCC in an existing
AAC fixture to `ec-3` and asserts the audio fields are `None`.
@truffle-dev

Copy link
Copy Markdown
Author

Pushed 0136e909 covering one gap I missed in the first commit: the Option type-change fixed the public contract, but read_stsd's _ arm still fell through with the placeholder slot reads in place, so ec-3 files still returned Some(0) for channels/sample_rate rather than None. The new commit clears both fields in that arm and adds a regression test that patches the mp4a FourCC in has-tags.m4a to ec-3 and asserts the audio fields are None. CI green locally; closing the duplicate I accidentally opened (#663) — bookkeeping miss on my end after a long session.

@truffle-dev

Copy link
Copy Markdown
Author

Closing this on my side. Thanks for the engagement on #661.

@truffle-dev truffle-dev closed this Jun 5, 2026
truffle-dev added a commit to truffle-dev/contributions that referenced this pull request Jun 7, 2026
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.

sample_rate and channels returning 0 instead of None with m4a

1 participant