I'm writing in Swift 3.1, using ObjectMapper to map my JSON response to my models.
I'm trying to map this rather complex JSON response with dynamic keys and am hoping to get some feedback on what I'm doing wrong.
A group has statistics about it's progress. It has stats broken down to years and then months. Each month within a year has results, ROI and win. The ROI and win are just percentages but the results key is fixed with the keys below, 1-5, and then some integer as a value.
My JSON
"stats": {
"2017": {
"1": {
"results": {
"1": 13,
"2": 3,
"3": 1,
"4": 1,
"5": 0
},
"roi": 0.40337966202464975,
"win": 0.8181818181818182
},
"2": {
"results": {
"1": 13,
"2": 5,
"3": 1,
"4": 2,
"5": 1
},
"roi": 0.26852551067922953,
"win": 0.717948717948718
}
}
}
My models
class GroupResponse: Mappable {
var stats: [String: [String: StatsMonthResponse]]?
func mapping(map: Map) {
stats <- map["stats"]
}
}
class StatsMonthResponse: Mappable {
var tips: [String: Int]?
var roi: Double?
var win: Double?
func mapping(map: Map) {
tips <- map["results"]
roi <- map["roi"]
win <- map["win"]
}
}
What I get
The response I get has the stats property in my GroupResponse class, as nil.
What other approach could I do to accomplish this, or change in my implementation to get this done?
Solution
I solved my problem by mapping the JSON manually.
class GroupResponse: Mappable {
var stats: [String: StatsYear]?
func mapping(map: Map) {
stats <- map["stats"]
}
}
class StatsYear: Mappable {
var months: [String: StatsMonth] = [:]
override func mapping(map: Map) {
for (monthKey, monthValue) in map.JSON as! [String: [String: Any]] {
let month = StatsMonth()
for (monthKeyType, valueKeyType) in monthValue {
if monthKeyType == "results" {
let tipResultDict = valueKeyType as! [String: Int]
for (result, tipsForResult) in tipResultDict {
month.tips[result] = tipsForResult
}
}
else if monthKeyType == "roi" {
month.roi = valueKeyType as? Double
}
else if monthKeyType == "win" {
month.win = valueKeyType as? Double
}
}
months[monthKey] = month
}
}
}
class StatsMonth {
var tips: [String: Int] = [:]
var roi: Double?
var win: Double?
}
There's probably a better solution to this problem but this is what I'm sticking with for now.
Hopefully this helps!
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With