22
33use std:: convert:: TryInto ;
44use std:: fmt;
5+ use std:: string:: FromUtf8Error ;
56
67#[ derive( Debug , Clone , Copy , PartialEq , Eq , Hash ) ]
78pub enum SpotifyAudioType {
@@ -136,15 +137,15 @@ impl SpotifyId {
136137
137138 /// Returns the `SpotifyId` as a base16 (hex) encoded, `SpotifyId::SIZE_BASE16` (32)
138139 /// character long `String`.
139- pub fn to_base16 ( & self ) -> String {
140+ pub fn to_base16 ( & self ) -> Result < String , FromUtf8Error > {
140141 to_base16 ( & self . to_raw ( ) , & mut [ 0u8 ; SpotifyId :: SIZE_BASE16 ] )
141142 }
142143
143144 /// Returns the `SpotifyId` as a [canonically] base62 encoded, `SpotifyId::SIZE_BASE62` (22)
144145 /// character long `String`.
145146 ///
146147 /// [canonically]: https://developer.spotify.com/documentation/web-api/#spotify-uris-and-ids
147- pub fn to_base62 ( & self ) -> String {
148+ pub fn to_base62 ( & self ) -> Result < String , FromUtf8Error > {
148149 let mut dst = [ 0u8 ; 22 ] ;
149150 let mut i = 0 ;
150151 let n = self . id ;
@@ -182,10 +183,7 @@ impl SpotifyId {
182183
183184 dst. reverse ( ) ;
184185
185- unsafe {
186- // Safety: We are only dealing with ASCII characters.
187- String :: from_utf8_unchecked ( dst. to_vec ( ) )
188- }
186+ String :: from_utf8 ( dst. to_vec ( ) )
189187 }
190188
191189 /// Returns a copy of the `SpotifyId` as an array of `SpotifyId::SIZE` (16) bytes in
@@ -202,25 +200,26 @@ impl SpotifyId {
202200 /// be encoded as `unknown`.
203201 ///
204202 /// [Spotify URI]: https://developer.spotify.com/documentation/web-api/#spotify-uris-and-ids
205- pub fn to_uri ( & self ) -> String {
203+ pub fn to_uri ( & self ) -> Result < String , FromUtf8Error > {
206204 // 8 chars for the "spotify:" prefix + 1 colon + 22 chars base62 encoded ID = 31
207205 // + unknown size audio_type.
208206 let audio_type: & str = self . audio_type . into ( ) ;
209207 let mut dst = String :: with_capacity ( 31 + audio_type. len ( ) ) ;
210208 dst. push_str ( "spotify:" ) ;
211209 dst. push_str ( audio_type) ;
212210 dst. push ( ':' ) ;
213- dst. push_str ( & self . to_base62 ( ) ) ;
211+ let base62 = self . to_base62 ( ) ?;
212+ dst. push_str ( & base62) ;
214213
215- dst
214+ Ok ( dst)
216215 }
217216}
218217
219218#[ derive( Copy , Clone , PartialEq , Eq , PartialOrd , Ord , Hash ) ]
220219pub struct FileId ( pub [ u8 ; 20 ] ) ;
221220
222221impl FileId {
223- pub fn to_base16 ( & self ) -> String {
222+ pub fn to_base16 ( & self ) -> Result < String , FromUtf8Error > {
224223 to_base16 ( & self . 0 , & mut [ 0u8 ; 40 ] )
225224 }
226225}
@@ -233,23 +232,20 @@ impl fmt::Debug for FileId {
233232
234233impl fmt:: Display for FileId {
235234 fn fmt ( & self , f : & mut fmt:: Formatter ) -> fmt:: Result {
236- f. write_str ( & self . to_base16 ( ) )
235+ f. write_str ( & self . to_base16 ( ) . unwrap_or_default ( ) )
237236 }
238237}
239238
240239#[ inline]
241- fn to_base16 ( src : & [ u8 ] , buf : & mut [ u8 ] ) -> String {
240+ fn to_base16 ( src : & [ u8 ] , buf : & mut [ u8 ] ) -> Result < String , FromUtf8Error > {
242241 let mut i = 0 ;
243242 for v in src {
244243 buf[ i] = BASE16_DIGITS [ ( v >> 4 ) as usize ] ;
245244 buf[ i + 1 ] = BASE16_DIGITS [ ( v & 0x0f ) as usize ] ;
246245 i += 2 ;
247246 }
248247
249- unsafe {
250- // Safety: We are only dealing with ASCII characters.
251- String :: from_utf8_unchecked ( buf. to_vec ( ) )
252- }
248+ String :: from_utf8 ( buf. to_vec ( ) )
253249}
254250
255251#[ cfg( test) ]
@@ -366,7 +362,7 @@ mod tests {
366362 audio_type : c. kind ,
367363 } ;
368364
369- assert_eq ! ( id. to_base62( ) , c. base62) ;
365+ assert_eq ! ( id. to_base62( ) . unwrap ( ) , c. base62) ;
370366 }
371367 }
372368
@@ -389,7 +385,7 @@ mod tests {
389385 audio_type : c. kind ,
390386 } ;
391387
392- assert_eq ! ( id. to_base16( ) , c. base16) ;
388+ assert_eq ! ( id. to_base16( ) . unwrap ( ) , c. base16) ;
393389 }
394390 }
395391
@@ -415,7 +411,7 @@ mod tests {
415411 audio_type : c. kind ,
416412 } ;
417413
418- assert_eq ! ( id. to_uri( ) , c. uri) ;
414+ assert_eq ! ( id. to_uri( ) . unwrap ( ) , c. uri) ;
419415 }
420416 }
421417
0 commit comments