简体   繁体   中英

How to Get Response from URLSession in SwiftUI

I'm trying to build a URLSession in SwiftUI to handle API token based authentication for login to a web app.

I'm able to get the API working fine in Postman, but unable to get any sort of readable response in SwiftUI. I'm new to SwiftUI and debugging. From my web server's logs, which handles the authorization, it appears as though the login request from my Swift code is successful, but I can't seem to parse out the body or headers.

I keep getting "LoginResponse(message: nil)" in my canvas.

Here's my SwiftUI code reduced to just trying to print the URLSession response.

import Foundation

enum AuthenticationError: Error {
    case invalidCredentials
    case custom(errorMessage: String)
}

struct LoginRequestBody: Codable {
    let email: String
    let password: String
}

struct LoginResponse: Codable {
    let message: String?
}

class Sessionservice {
    
    func login(emailAddress: String, password: String, completion: @escaping (Result<String, AuthenticationError>) -> Void){
        
        guard let url = URL(string: "https://www.example.com/api/v1/auth/sign_in") else {
            completion(.failure(.custom(errorMessage:"Site is unavailable.  Try again later.")))
            return
        }
        
        let body = LoginRequestBody(email: "email@example.com", password: "password")
        
        
        var request = URLRequest(url: url)
                request.httpMethod = "POST"
                request.addValue("application/json", forHTTPHeaderField: "Content-Type")
                request.httpBody = try? JSONEncoder().encode(body)

                
                URLSession.shared.dataTask(with: request) { (data, response, error) in
                    
                    guard let data = data, error == nil else {
                        completion(.failure(.custom(errorMessage: "No data")))
                        return
                    }
                    
                    try! JSONDecoder().decode(LoginResponse.self, from: data)

                    guard let loginResponse = try? JSONDecoder().decode(LoginResponse.self, from: data) else {
                        completion(.failure(.custom(errorMessage: "loginResponse Failure")))
                        return
                    }
                    print(loginResponse)
                }.resume()
    }
}
import Foundation
import SwiftUI


enum AuthenticationError: Error {
case invalidCredentials
case custom(errorMessage: String)
}

struct LoginRequestBody: Codable {
let email: String
let password: String
}

struct LoginResponse: Decodable {
let data: LoginValue?
let success: Bool?
let client: String?
}

struct LoginToken: Decodable {
let token: String?
}

struct LoginValue: Decodable {
let message: String?
let user: UserRole?
let success: Bool?
}

struct UserRole: Decodable {
let role: String?
}

class Sessionservice {


func login(email: String, password: String, completion: @escaping (Result<String, AuthenticationError>) -> Void){

    guard let url = URL(string: "https://www.example.com/api/v1/auth/sign_in") else {
        completion(.failure(.custom(errorMessage:"Site is unavailable.  Try again later.")))
        return
    }
    
    let body = LoginRequestBody(email: email, password: password)
    
    
    var request = URLRequest(url: url)
            request.httpMethod = "POST"
            request.addValue("application/json", forHTTPHeaderField: "Content-Type")
            request.httpBody = try? JSONEncoder().encode(body)

            
            URLSession.shared.dataTask(with: request) { (data, response, error) in
                
                if let response = response as? HTTPURLResponse {

                    guard let token = response.value(forHTTPHeaderField: "Accesstoken") else {
                        completion(.failure(.custom(errorMessage: "Missing Access Token")))
                        return
                    }
                    completion(.success(token))
                }
                
                guard let data = data, error == nil else { return }
                guard let loginResponse = try? JSONDecoder().decode(LoginResponse.self, from: data) else { return }
                guard let messageData = loginResponse.data else {return}
                guard let message = messageData.message else {return}
                guard let userRole = messageData.user else {return}
                guard let role = userRole.role else {return}
                completion(.success(message))
                completion(.success(role))
               
            }.resume()
    
            
}
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM