@@ -210,22 +210,42 @@ impl YamlLoader {
210210 parser. load ( & mut loader, true ) ?;
211211 Ok ( loader. docs )
212212 }
213+ }
213214
214- pub fn load_from_bytes ( mut source : impl std:: io:: Read ) -> Result < Vec < Yaml > , LoadError > {
215- let mut buffer = Vec :: new ( ) ;
216- source. read_to_end ( & mut buffer) ?;
217-
218- // Decodes the input buffer using either UTF-8, UTF-16LE or UTF-16BE depending on the BOM codepoint.
219- // If the buffer doesn't start with a BOM codepoint, it will use a fallback encoding obtained by
220- // detect_utf16_endianness.
221- let ( res, _) = encoding:: types:: decode (
222- & buffer,
223- encoding:: DecoderTrap :: Strict ,
224- detect_utf16_endianness ( & buffer) ,
225- ) ;
226- let s = res. map_err ( LoadError :: Decode ) ?;
227- YamlLoader :: load_from_str ( & s) . map_err ( LoadError :: Scan )
215+ pub struct YamlDecoder < T : std:: io:: Read > {
216+ source : T ,
217+ trap : encoding:: types:: DecoderTrap ,
218+ }
219+
220+
221+ impl < T : std:: io:: Read > YamlDecoder < T > {
222+ pub fn read ( source : T ) -> YamlDecoder < T > {
223+ YamlDecoder {
224+ source : source,
225+ trap : encoding:: DecoderTrap :: Strict ,
228226 }
227+ }
228+
229+ pub fn encoding_trap ( mut self , trap : encoding:: types:: DecoderTrap ) -> YamlDecoder < T > {
230+ self . trap = trap;
231+ self
232+ }
233+
234+ pub fn decode ( mut self ) -> Result < Vec < Yaml > , LoadError > {
235+ let mut buffer = Vec :: new ( ) ;
236+ self . source . read_to_end ( & mut buffer) ?;
237+
238+ // Decodes the input buffer using either UTF-8, UTF-16LE or UTF-16BE depending on the BOM codepoint.
239+ // If the buffer doesn't start with a BOM codepoint, it will use a fallback encoding obtained by
240+ // detect_utf16_endianness.
241+ let ( res, _) = encoding:: types:: decode (
242+ & buffer,
243+ self . trap ,
244+ detect_utf16_endianness ( & buffer) ,
245+ ) ;
246+ let s = res. map_err ( LoadError :: Decode ) ?;
247+ YamlLoader :: load_from_str ( & s) . map_err ( LoadError :: Scan )
248+ }
229249}
230250
231251/// The encoding crate knows how to tell apart UTF-8 from UTF-16LE and utf-16BE, when the
793813b: 2.2
794814c: [1, 2]
795815" ;
796- let out = YamlLoader :: load_from_bytes ( s as & [ u8 ] ) . unwrap ( ) ;
816+ let out = YamlDecoder :: read ( s as & [ u8 ] ) . decode ( ) . unwrap ( ) ;
797817 let doc = & out[ 0 ] ;
798818 assert_eq ! ( doc[ "a" ] . as_i64( ) . unwrap( ) , 1i64 ) ;
799819 assert_eq ! ( doc[ "b" ] . as_f64( ) . unwrap( ) , 2.2f64 ) ;
@@ -808,7 +828,7 @@ c: [1, 2]
808828\x00 b\x00 :\x00 \x00 2\x00 .\x00 2\x00
809829\x00 c\x00 :\x00 \x00 [\x00 1\x00 ,\x00 \x00 2\x00 ]\x00
810830\x00 ";
811- let out = YamlLoader :: load_from_bytes ( s as & [ u8 ] ) . unwrap ( ) ;
831+ let out = YamlDecoder :: read ( s as & [ u8 ] ) . decode ( ) . unwrap ( ) ;
812832 let doc = & out[ 0 ] ;
813833 println ! ( "GOT: {:?}" , doc) ;
814834 assert_eq ! ( doc[ "a" ] . as_i64( ) . unwrap( ) , 1i64 ) ;
@@ -824,7 +844,7 @@ c: [1, 2]
824844\x00 b\x00 :\x00 \x00 2\x00 .\x00 2\x00
825845\x00 c\x00 :\x00 \x00 [\x00 1\x00 ,\x00 \x00 2\x00 ]\x00
826846" ;
827- let out = YamlLoader :: load_from_bytes ( s as & [ u8 ] ) . unwrap ( ) ;
847+ let out = YamlDecoder :: read ( s as & [ u8 ] ) . decode ( ) . unwrap ( ) ;
828848 let doc = & out[ 0 ] ;
829849 println ! ( "GOT: {:?}" , doc) ;
830850 assert_eq ! ( doc[ "a" ] . as_i64( ) . unwrap( ) , 1i64 ) ;
@@ -840,7 +860,23 @@ c: [1, 2]
840860\x00 b\x00 :\x00 \x00 2\x00 .\x00 2\x00
841861\x00 c\x00 :\x00 \x00 [\x00 1\x00 ,\x00 \x00 2\x00 ]\x00
842862\x00 ";
843- let out = YamlLoader :: load_from_bytes ( s as & [ u8 ] ) . unwrap ( ) ;
863+ let out = YamlDecoder :: read ( s as & [ u8 ] ) . decode ( ) . unwrap ( ) ;
864+ let doc = & out[ 0 ] ;
865+ println ! ( "GOT: {:?}" , doc) ;
866+ assert_eq ! ( doc[ "a" ] . as_i64( ) . unwrap( ) , 1i64 ) ;
867+ assert_eq ! ( doc[ "b" ] . as_f64( ) . unwrap( ) , 2.2f64 ) ;
868+ assert_eq ! ( doc[ "c" ] [ 1 ] . as_i64( ) . unwrap( ) , 2i64 ) ;
869+ assert ! ( doc[ "d" ] [ 0 ] . is_badvalue( ) ) ;
870+ }
871+
872+ #[ test]
873+ fn test_read_trap ( ) {
874+ let s = b"---
875+ a\xa9 : 1
876+ b: 2.2
877+ c: [1, 2]
878+ " ;
879+ let out = YamlDecoder :: read ( s as & [ u8 ] ) . encoding_trap ( encoding:: DecoderTrap :: Ignore ) . decode ( ) . unwrap ( ) ;
844880 let doc = & out[ 0 ] ;
845881 println ! ( "GOT: {:?}" , doc) ;
846882 assert_eq ! ( doc[ "a" ] . as_i64( ) . unwrap( ) , 1i64 ) ;
0 commit comments