Это ... выглядит хорошо? (Предполагая, что Resource
также Decodable
, но это будет отдельной проблемой). Возможно, ошибка на самом деле говорит вам правду, возможно, вы пытаетесь декодировать BLOB-объект JSON, который не имеет значения даты.
Вы можете явно увидеть то, что мы пытаемся декодировать, с добавленной печатью непосредственно перед тем, как мы попытаемся декодировать:
if let data = data {
print(String(data: data, encoding: .utf8)!)
do {
...
Затем отдельно, если поле даты не гарантированно существует впри каждом ответе вы должны сделать его необязательным:
struct EarthImages: Codable {
let date: String?
let id: String
let resource: Resource
let serviceVersion: String
let url: String
}
Небольшое примечание, перечисления строк не нужно повторно декларировать, если они точно совпадают с регистром перечисления:
enum CodingKeys: String, CodingKey {
case date // "date" is implied
case id
case resource
case serviceVersion = "service_version"
case url
}
Еще один забавный факт: JSONDecoder
также может автоматически преобразовывать регистр змеи без необходимости определять CodingKeys
, если каждый ключ согласован.
Так что вы также можете сделать:
struct EarthImages: Codable {
let date: String
let id: String
let resource: Resource
let serviceVersion: String
let url: String
}
...
do {
let decoder = JSONDecoder()
decoder.keyDecodingStrategy = .convertFromSnakeCase
let earthImages = try decoder.decode(EarthImages.self, from: data)
}