Необходимо кодировать в JSON, структуру, которая имеет 2 переменные экземпляра Date (день и время), однако мне нужно кодировать каждую переменную экземпляра даты в другом формате, т.е.для "day": "yyyy-Md" и "time": "H: m: s".
Написал собственный декодер, который работает без проблем.Но не знаю, как написать требуемый пользовательский кодировщик для решения этой проблемы.
Например, я могу декодировать следующую строку JSON: {"biometrics": [{"biometricId": 1, "amount": 2.1, "source ":" Alderaan "," day ":" 2019-1-3 "," time ":" 11-3-3 "," unitId ": 2}, {" biometricId ": 10," amount ": 3.1, "source": "Endoor", "day": "2019-2-4", "time": "11-4-4", "unitId": 20}]}
Однако, когдаЯ кодирую его, я могу кодировать его только в одном формате даты :( Справка, будет принята с благодарностью. Спасибо.
import UIKit
let biometricsJson = """
{ "biometrics" : [
{"biometricId":1,"amount":2.1,"source":"Alderaan","day":"2019-1-3","time":"11-3-3","unitId":2},
{"biometricId":10,"amount":3.1,"source":"Endoor","day":"2019-2-4","time":"11-4-4","unitId":20}]
}
"""
struct Biometrics: Codable {
var biometrics: [Biometric]
}
struct Biometric: Codable {
var biometricId: Int
var unitId: Int
var source: String?
var amount: Double
var day: Date
var time: Date
init(biometricId: Int, unitId: Int, source: String, amount: Double, day: Date, time: Date){
self.biometricId = biometricId
self.unitId = unitId
self.source = source
self.amount = amount
self.day = day
self.time = time
}
}
extension Biometric {
static let decoder: JSONDecoder = {
let decoder = JSONDecoder()
decoder.dateDecodingStrategy = .custom { decoder in
let container = try decoder.singleValueContainer()
let dateString = try container.decode(String.self)
let formatter = DateFormatter()
formatter.timeZone = TimeZone.current
formatter.dateFormat = "H:m:s"
if let date = formatter.date(from: dateString) {
return date
}
formatter.dateFormat = "yyyy-M-d"
if let date = formatter.date(from: dateString) {
return date
}
throw DecodingError.dataCorruptedError(in: container,
debugDescription: "Cannot decode date string \(dateString)")
}
return decoder
}()
}
let biometrics = try Biometric.decoder.decode(Biometrics.self, from:biometricsJson.data(using: .utf8)!)
let jsonEncoder = JSONEncoder()
let encodedJson = try jsonEncoder.encode(biometrics)
let jsonString = String(data: encodedJson, encoding: .utf8)
if biometricsJson != jsonString {
print("error: decoding, then encoding does not give the same string")
print("biometricsJson: \(biometricsJson)")
print("jsonString: \(jsonString!)")
}
Я ожидаю, что закодированный JSON будет декодируемым декодером. То есть biometricsJson== jsonString