File tree Expand file tree Collapse file tree 5 files changed +49
-2
lines changed Expand file tree Collapse file tree 5 files changed +49
-2
lines changed Original file line number Diff line number Diff line change @@ -23,6 +23,10 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
2323 - ` Ilst::remove ` will now return all of the removed atoms
2424 - ` Ilst::insert_picture ` will now combine all pictures into a single ` covr ` atom
2525 - ` Ilst::insert ` will now merge atoms with the same identifier into a single atom
26+ - ** FLAC** : Allow multiple Vorbis Comment blocks when not using ` ParsingMode::Strict `
27+ - This is not allowed [ by spec] ( https://xiph.org/flac/format.html#def_VORBIS_COMMENT ) , but is still possible
28+ to encounter in the wild. Now we will just tag whichever tag happens to be latest in the stream and
29+ use it, they ** will not be merged** .
2630
2731## [ 0.15.0] - 2023-07-11
2832
Original file line number Diff line number Diff line change @@ -11,7 +11,7 @@ use crate::id3::{find_id3v2, ID3FindResults};
1111use crate :: macros:: decode_err;
1212use crate :: ogg:: read:: read_comments;
1313use crate :: picture:: Picture ;
14- use crate :: probe:: ParseOptions ;
14+ use crate :: probe:: { ParseOptions , ParsingMode } ;
1515
1616use std:: io:: { Read , Seek , SeekFrom } ;
1717
7474 }
7575
7676 if block. ty == BLOCK_ID_VORBIS_COMMENTS {
77- if flac_file. vorbis_comments_tag . is_some ( ) {
77+ // NOTE: According to the spec
78+ //
79+ // <https://xiph.org/flac/format.html#def_VORBIS_COMMENT>:
80+ // "There may be only one VORBIS_COMMENT block in a stream."
81+ //
82+ // But of course, we can't ever expect any spec compliant inputs, so we just
83+ // take whatever happens to be the latest block in the stream. This is safe behavior,
84+ // as when writing to a file with multiple tags, we end up removing all `VORBIS_COMMENT`
85+ // blocks anyway.
86+ if flac_file. vorbis_comments_tag . is_some ( )
87+ && parse_options. parsing_mode == ParsingMode :: Strict
88+ {
7889 decode_err ! ( @BAIL Flac , "Streams are only allowed one Vorbis Comments block per stream" ) ;
7990 }
8091
Original file line number Diff line number Diff line change 1+ use lofty:: flac:: FlacFile ;
2+ use lofty:: { Accessor , AudioFile , ParseOptions , ParsingMode } ;
3+
4+ use std:: fs:: File ;
5+ use std:: io:: Seek ;
6+
7+ #[ test]
8+ fn multiple_vorbis_comments ( ) {
9+ let mut file = File :: open ( "tests/files/assets/two_vorbis_comments.flac" ) . unwrap ( ) ;
10+
11+ // Reading a file with multiple VORBIS_COMMENT blocks should error when using `Strict`, as it is
12+ // not allowed by spec.
13+ assert ! ( FlacFile :: read_from(
14+ & mut file,
15+ ParseOptions :: new( )
16+ . read_properties( false )
17+ . parsing_mode( ParsingMode :: Strict )
18+ )
19+ . is_err( ) ) ;
20+
21+ file. rewind ( ) . unwrap ( ) ;
22+
23+ // But by default, we should just take the last tag in the stream
24+ let f = FlacFile :: read_from ( & mut file, ParseOptions :: new ( ) . read_properties ( false ) ) . unwrap ( ) ;
25+
26+ // The first tag has the artist "Artist 1", the second has "Artist 2".
27+ assert_eq ! (
28+ f. vorbis_comments( ) . unwrap( ) . artist( ) . as_deref( ) ,
29+ Some ( "Artist 2" )
30+ ) ;
31+ }
Original file line number Diff line number Diff line change 11mod aac;
22mod aiff;
33mod ape;
4+ mod flac;
45mod mp4;
56mod mpc;
67mod mpeg;
You can’t perform that action at this time.
0 commit comments