为什么在使用JSONDecoder.decode方法时未调用Decodable的init方法?

时间:2019-06-11 17:14:16

标签: swift codable

我正在尝试覆盖JSONDecoder如何解码数据。

我尝试了以下操作:

struct Response : Decodable {
    init(from decoder: Decoder) throws {
        print("Hello")
    }
}

let result = try JSONDecoder().decode(Response.self, from: Data())

但是init(from:)没有被调用。 基本上,我希望JSONDecoder在将空数据解码为空Response对象时总是成功

2 个答案:

答案 0 :(得分:1)

空的Data对象导致init方法引发错误

  

给定的数据不是有效的JSON。

在打印“ Hello”之前。


如果您想获取一个空的Response对象(假设您不必调用任何指定的初始化方法),则会捕获dataCorrupted解码错误

struct Response : Decodable {}

var response : Response?
do {
    response = try JSONDecoder().decode(Response.self, from: Data())
} catch DecodingError.dataCorrupted(let context) where (context.underlyingError as NSError?)?.code == 3840 { // "The given data was not valid JSON."
    response = Response()
} catch { print(error) }

答案 1 :(得分:-1)

无论谁来到此页面,寻找可以在您只需要使用的可解码类上强制使用INIT的解决方案:

required init(from decoder: Decoder) throws {

完整示例:

class DeviceListElement: Codable {
    
    var firmwareVersion, deviceName: String
    var status: Int
    
    
    enum CodingKeys: String, CodingKey {
        case firmwareVersion = "fwVer"
        case deviceName
        case status
    }
    

    required init(from decoder: Decoder) throws {
        
        let container = try decoder.container(keyedBy: CodingKeys.self)
        firmwareVersion = try container.decode(String.self, forKey: .firmwareVersion)
        deviceName = try container.decode(String.self, forKey: .deviceName)
        status = try container.decode(Int.self, forKey: .status)
        
        
        //if is optional use this: container.decodeIfPresent(String.self, forKey: .blabla)
    }
    
}