Deencoding de tokens web JSON en Swift

tratando de decodificar una carga útil JWT en Swift y teniendo un momento realmente difícil

static func decodePayload(tokenstr: String) { //splitting JWT to extract payload let arr = split(tokenstr) {$0 == "."} //base64 encoded string i want to decode let base64String = arr[1] as String println(base64String) //eyJleHAiOjE0MjY4MjIxNjMsImlkIjoiNTUwYjA3NzM4ODk1NjAwZTk5MDAwMDAxIn0 //attempting to convert base64 string to nsdata let nsdata: NSData = NSData(base64EncodedString: base64String, options: NSDataBase64DecodingOptions(rawValue: 0)) //decoding fails because nsdata unwraps as nil let base64Decoded: NSString = NSString(data: nsdata!, encoding: NSUTF8StringEncoding)! } 

 eyJleHAiOjE0MjY4MjIxNjMsImlkIjoiNTUwYjA3NzM4ODk1NjAwZTk5MDAwMDAxIn0 

no es una cadena codificada en Base64 válida porque su longitud no es un múltiplo de 4. Algunos decodificadores Base64 toleran este error, pero los métodos NSData no lo hacen.

Entonces esto es realmente un error en el lado del servidor que crea la cadena codificada en Base64. Si es necesario, puede solucionarlo en su aplicación agregando el relleno requerido con = caracteres (código actualizado para Swift 2):

 var base64String = arr[1] as String if base64String.characters.count % 4 != 0 { let padlen = 4 - base64String.characters.count % 4 base64String += String(count: padlen, repeatedValue: Character("=")) } 

Y ahora la deencoding funciona como se esperaba:

 if let data = NSData(base64EncodedString: base64String, options: []), let str = String(data: data, encoding: NSUTF8StringEncoding) { print(str) // {"exp":1426822163,"id":"550b07738895600e99000001"} } 

Swift 4:

 var base64String = "eyJleHAiOjE0MjY4MjIxNjMsImlkIjoiNTUwYjA3NzM4ODk1NjAwZTk5MDAwMDAxIn0" if base64String.count % 4 != 0 { let padlen = 4 - base64String.count % 4 base64String.append(contentsOf: repeatElement("=", count: padlen)) } if let data = Data(base64Encoded: base64String) , let str = String(data: data, encoding: .utf8) { print(str) // {"exp":1426822163,"id":"550b07738895600e99000001"} } 

La solución anterior está funcionando para mí, la convertí en swift3

Aquí puedes encontrar el código swift3

 var base64Str = arr[1] as String if base64Str.characters.count % 4 != 0 { let padlen = 4 - base64Str.characters.count % 4 base64Str += String(repeating: "=", count: padlen) } if let data = Data(base64Encoded: base64Str, options: []), let str = String(data: data, encoding: String.Encoding.utf8) { print(str) } 

Swift 4 como a continuación:

 if let data = Data(base64Encoded: base64String, options: []), let str = String(data: data as Data, encoding: String.Encoding.utf8) { print(str) // {"exp":1426822163,"id":"550b07738895600e99000001"} }