-
-
Save IanKeen/788e2ce55e5c91257bc639efc5dbb1c1 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import Foundation | |
struct AnyCodingKey: CodingKey { | |
var stringValue: String | |
var intValue: Int? | |
init?(intValue: Int) { | |
self.intValue = intValue | |
self.stringValue = "\(intValue)" | |
} | |
init?(stringValue: String) { | |
self.intValue = nil | |
self.stringValue = stringValue | |
} | |
} | |
// MARK: - Identifier<T> | |
struct Identifier<T> { | |
let value: String | |
} | |
extension Identifier: Codable { | |
init(from decoder: Decoder) throws { | |
self.value = try String(from: decoder) | |
} | |
func encode(to encoder: Encoder) throws { | |
try value.encode(to: encoder) | |
} | |
} | |
// MARK: - Identified<T> | |
struct Identified<T> { | |
let identifier: Identifier<T> | |
let value: T | |
} | |
extension Identified: Codable where T: Codable { | |
init(from decoder: Decoder) throws { | |
let container = try decoder.container(keyedBy: AnyCodingKey.self) | |
self.identifier = try container.decode(Identifier<T>.self, forKey: AnyCodingKey(stringValue: "identifier")!) | |
self.value = try T.init(from: decoder) | |
} | |
func encode(to encoder: Encoder) throws { | |
var container = encoder.container(keyedBy: AnyCodingKey.self) | |
try container.encode(identifier, forKey: AnyCodingKey(stringValue: "identifier")!) | |
try value.encode(to: encoder) | |
} | |
} | |
// MARK: - Models | |
struct Author: Codable { | |
let name: String | |
} | |
struct Book: Codable { | |
let title: String | |
let authorIdentifier: Identifier<Author> | |
} | |
// MARK: - Usage | |
let authorJson = """ | |
{ | |
"identifier": "A13424B6", | |
"name": "Robert C. Martin" | |
} | |
""".data(using: .utf8)! | |
let bookJson = """ | |
{ | |
"identifier": "A161F15C", | |
"title": "Clean Code", | |
"authorIdentifier": "A13424B6" | |
} | |
""".data(using: .utf8)! | |
let author = try! JSONDecoder().decode(Identified<Author>.self, from: authorJson) | |
print("Author ID:", author.identifier.value) | |
print("Author Name:", author.value.name) | |
print("") | |
let book = try! JSONDecoder().decode(Identified<Book>.self, from: bookJson) | |
print("Book ID:", book.identifier.value) | |
print("Book Title:", book.value.title) | |
print("Book Author ID:", book.value.authorIdentifier.value) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment