You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Swift网络请求解析问题:无法获取错误信息及成功响应数据

问题解决方案

核心问题分析

两个问题本质都是Codable模型与JSON-RPC响应结构不匹配,以及网络层解析逻辑未适配JSON-RPC的成功/错误响应差异导致的。


问题1:错误响应无法提取ErrorClass的message和meaning字段

修正步骤

  1. 确保ErrorClass的Codable属性与JSON字段完全匹配,若字段名不一致需通过CodingKeys映射。
  2. 定义JSON-RPC通用响应模型,明确区分成功(含result)和错误(含error)的结构。

修正后的ErrorClass及通用响应模型

// 错误信息模型
struct ErrorClass: Codable {
    let code: Int
    let message: String
    let meaning: String // 确保与JSON返回的字段名一致,若JSON字段名不同,添加CodingKeys映射
    
    // 示例:若JSON中meaning字段名为error_meaning,需添加以下代码
    // enum CodingKeys: String, CodingKey {
    //     case code, message, meaning = "error_meaning"
    // }
}

// JSON-RPC通用响应模型
struct RPCResponse<T: Codable>: Codable {
    let jsonrpc: String
    let id: Int?
    let result: T?
    let error: ErrorClass?
}

问题2:成功响应时PostModel的jsonrpc和result为nil

修正步骤

  1. 移除直接将响应解析为PostModel的逻辑,改用通用RPCResponse<PostModel>解析。
  2. 确保PostModel的属性与JSON-RPC返回的result字段结构完全匹配。
  3. 调整NetworkManager的解析逻辑,先解析通用响应,再提取result或error。

修正后的NetworkManager核心代码

class NetworkManager {
    static let shared = NetworkManager()
    
    func performRPCRequest<T: Codable>(url: String, method: String, params: [String: Any], resultType: T.Type, completion: @escaping (Result<T, ErrorClass>) -> Void) {
        let rpcRequestBody = [
            "jsonrpc": "2.0",
            "method": method,
            "params": params,
            "id": 1
        ]
        
        AF.request(url, method: .post, parameters: rpcRequestBody, encoding: JSONEncoding.default)
            .validate()
            .responseDecodable(of: RPCResponse<T>.self) { response in
                switch response.result {
                case .success(let rpcResponse):
                    if let error = rpcResponse.error {
                        completion(.failure(error))
                    } else if let result = rpcResponse.result {
                        completion(.success(result))
                    } else {
                        // 处理无result也无error的异常情况
                        let emptyError = ErrorClass(code: -1, message: "Empty response", meaning: "No result or error returned")
                        completion(.failure(emptyError))
                    }
                case .failure(let afError):
                    // 处理网络层错误,转为自定义ErrorClass
                    let networkError = ErrorClass(code: afError.responseCode ?? -2, message: afError.localizedDescription, meaning: "Network request failed")
                    completion(.failure(networkError))
                }
            }
    }
}

修正后的ViewController调用代码

// PostModel需与JSON-RPC返回的result字段结构完全匹配
struct PostModel: Codable {
    let postId: Int
    let title: String
    // 其他对应result字段的属性
}

class ViewController: UIViewController {
    func fetchTargetPost() {
        let requestParams = ["postId": 100]
        NetworkManager.shared.performRPCRequest(
            url: "https://your-rpc-api-endpoint.com",
            method: "get_post", // 替换为实际的RPC方法名
            params: requestParams,
            resultType: PostModel.self
        ) { [weak self] result in
            DispatchQueue.main.async {
                switch result {
                case .success(let post):
                    // 此时post的属性已正确解析
                    print("Post title: \(post.title)")
                case .failure(let error):
                    // 直接获取错误的message和meaning
                    print("Error: \(error.message) | Meaning: \(error.meaning)")
                }
            }
        }
    }
}

关键注意事项

  • 所有Codable模型的属性名与JSON字段严格一致,大小写敏感(JSON-RPC通常用小写蛇形或驼峰,需完全对应)。
  • JSON-RPC响应必须包含jsonrpc(固定为"2.0")和id字段,通用响应模型必须声明这两个属性。
  • 若API返回的result是数组或嵌套结构,需对应调整PostModel的结构。

内容的提问来源于stack exchange,提问作者Swift

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.02 18:40:31