Lets say I have the following struct and json data. Can We write a init(decode: Decoder) function to covert object with this condition? If the randomKey for the OptionContainer exist, use the randomKey value to look for the id for the option. If the randomKey doesn’t exist, then simply use the id.
Example, both the ids for the two options below would be ["1","2","3"]
My Struct
struct OptionContainer: Decodable {
let randomKey: String?
let id: String
let text: String
struct Option: Decodable {
let id: String
let text: String
}
}
Json Data
[
{
"id": "123",
"text": "text",
"randomKey": "level",
"options": [
{
"text": "Hello",
"level": "1"
},
{
"text": "Hello2",
"level": "2"
},
{
"text": "Hello3",
"level": "3"
},
]
},
{
"id": "222",
"text": "text2",
"options": [
{
"text": "Hello",
"id": "1"
},
{
"text": "Hello2",
"id": "2"
},
{
"text": "Hello3",
"id": "3"
},
]
},
]
2
Answers
A possible solution is to decode
options
as[String:String]
dictionary, get the random key (set it toid
if it doesn’t exist) and createOption
instances manuallySince you want a generic string key, you’ll need a special CodingKey:
This is mostly just boilerplate. I use it so often I have a snippet for it. It’s just a CodingKey that can be any String or Int.
Next, you’ll want a special init for Option. It is not actually Decodable. It just has an init that takes a Decoder:
This allows you to pass the key you want to use for
id
.And with that, you can write the OptionContainer Decodable init:
All the code together: