An easy way to handle JSON objects x-^
extensions in Codable structures, e.g. the OpenAPI Specification Extensions. All extension fields are aggregated in extensions storage
field during decoding and are encoded at the same level as base object field.
To support extensions decoding and encoding for your Codable structs, just conform to XTendedCodable
protocol, e.g.:
import XTendedCodable
struct ExampleCodable: XTendedCodable {
let name: String
let date: Date
// Default provided [String: AnyCodable] storage
var extensions: XTension?
}
It can now decode the x-^
properties from JSON:
{
"name" : "Extended Example Codable",
"timestamp": "2018-07-12T09:13:42Z",
"x-bool" : false,
"x-custom" : {
"key" : -1,
"description": "something"
},
"x-double" : 3.14,
"x-string" : "Hello!",
"x-nil": null,
"x-int" : 10,
"x-int-array" : [1, 2, 3],
"x-string?-array" : ["a", null, "c"]
}
For example:
// Decode the JSON above
let decoder = JSONDecoder()
decoder.dateDecodingStrategy = .iso8601
let exampleCodable = try decoder.decode(ExampleCodable.self, from: jsonData)
if let ext = exampleCodable.extensions {
let xOptionalStringArray = ext["x-string?-array"]?.to([String?].self)
for string in xOptionalStringArray.compactMap { $0 } {
print (string)
}
}
// Output:
"a"
"c"
More examples of Decoding and Encoding could be found in tests sources.
You can add properties to your ExampleCodable
later in extensions or just for convenience if you know what you will be working with, e.g.:
extension TestCodable {
var xProperty: Int? {
get { return extensions?["x-some-property"]?.int }
set { extensions?["x-some-property"] = .init(from: newValue) }
}
}
Note: non-prefixed with "x-" keys will not be encoded. Possibly, you can use this to hide some properties from decoding/encoding - without modifying CodingKeys
, decode
and encode
methods.
XTendedCodable provides Extendable
generic protocol so you can set your own Storage type (with needed conformance limitations) and per-model fields filtering rules.
Any custom type conforming Codable could be handled by just another AnyCodable
bycicle, if no, I possibly messed up somewhere :)
AnyCodable.register(CustomCodableType.self)
To install it add following package to needed Packages.swift
dependencies:
.package(url: "https://github.com/rinold/XTendedCodable.git", from: "0.2.1")
We use SemVer for versioning. For the versions available, see the tags on this repository.
- rinold - Mikhail Churbanov, [email protected]
ProxyResolver is available under the MIT license. See the LICENSE file for more info.