Just like ParseOptions, there may be some things that a caller wants to configure during a write. These options would be passed to AudioFile::save_to and TagExt::save_to.
Some options I can think of being useful are:
preferred_padding: Right now we make use of padding, but in its absence we don't end up adding any. Since this is something multiple tags support, it would be nice to add a specified amount of padding to tags when requested.
remove_others: Removing tags from an existing file isn't the easiest process currently. It would be nice if the caller could specify that they want to, for example, remove an APE and ID3v1 tag when they are only attempting to save an ID3v2 tag.
There are currently three ways to remove tags:
These remove tags one at a time, but that isn't helpful if there a singular preferred tag type to be written, as it would require the caller to remove each tag, as well as seek back to the beginning of the file to then do their write.
This will handle the seeking, but will not remove any tag field that is None. This means that calling <AudioFile>::remove_<tag> will not remove from a file it is saving to. A workaround for this is to do <AudioFile>::<tag>_mut followed by TagExt::clear, as empty tags will be treated as a removal request.
respect_read_only: Some tags allow items to be marked read only, so we should have an option to retain any read only items found in the tags of the file being written to. Read only items are currently (unavoidably) respected in APE tags.
uppercase_id3v2_chunk: I think I read somewhere that some software expects an "id3 " chunk instead of the normal "ID3 " for ID3v2 in WAV/AIFF. Might as well allow the caller to decide which case we write.
API design
pub struct WriteOptions {
// Default: 1024, seems like a safe size
preferred_padding: usize,
// Default: false, destructive
remove_others: bool,
// Default: true, potentially destructive?
// Read only items would take priority over newly created tag items.
respect_read_only: bool,
// Default: true, this is what 99% of software will expect
uppercase_id3v2_chunk: bool,
// ...?
}
pub trait TagExt {
fn save_to(&self, file: &mut File, options: WriteOptions) -> std::result::Result<(), Self::Err>;
}
pub trait AudioFile {
fn save_to(&self, file: &mut File, options: WriteOptions) -> Result<()>;
}
Summary
Just like
ParseOptions
, there may be some things that a caller wants to configure during a write. These options would be passed toAudioFile::save_to
andTagExt::save_to
.Some options I can think of being useful are:
preferred_padding
: Right now we make use of padding, but in its absence we don't end up adding any. Since this is something multiple tags support, it would be nice to add a specified amount of padding to tags when requested.remove_others
: Removing tags from an existing file isn't the easiest process currently. It would be nice if the caller could specify that they want to, for example, remove an APE and ID3v1 tag when they are only attempting to save an ID3v2 tag. There are currently three ways to remove tags:TagExt::remove_from
/TagType::remove_from
TagExt::save_to
with an empty tagAudioFile::save_to
None
. This means that calling<AudioFile>::remove_<tag>
will not remove<AudioFile>::<tag>_mut
followed byTagExt::clear
, as empty tags will be treated as a removal request.respect_read_only
: Some tags allow items to be marked read only, so we should have an option to retain any read only items found in the tags of the file being written to. Read only items are currently (unavoidably) respected in APE tags.uppercase_id3v2_chunk
: I think I read somewhere that some software expects an"id3 "
chunk instead of the normal"ID3 "
for ID3v2 in WAV/AIFF. Might as well allow the caller to decide which case we write.API design