Swift中使用ObjectMapper解析JSON时的空数组解析异常问题
解决ObjectMapper解析含空数组的JSON返回nil的问题
看起来你遇到的是JSON字段类型与模型属性类型不匹配导致的解析失败问题——服务器在无数据时把本该返回对象的字段(比如myKpiMonth/myKpiWeek)返回成了空数组[],而ObjectMapper无法自动将空数组映射到对象类型的属性,最终导致整个模型初始化失败返回nil。
下面给你两种实用的解决方案:
方案一:自定义类型转换器(复用性强)
先写一个通用转换器,把空数组转换成nil,这样ObjectMapper遇到空数组时会自动把对应属性设为nil,而不是解析失败:
class EmptyArrayToNilTransform<T: Mappable>: TransformType { typealias Object = T? typealias JSON = Any func transformFromJSON(_ value: Any?) -> T? { guard let value = value else { return nil } // 检测到空数组,直接返回nil if let emptyArray = value as? [Any], emptyArray.isEmpty { return nil } // 正常情况映射为目标对象 return Mapper<T>().map(JSONObject: value) } func transformToJSON(_ value: T?) -> Any? { return value?.toJSON() } }
然后在你的模型类里,给有问题的属性绑定这个转换器:
class GetTodayMyKpiResponse: Mappable{ var status: String? var myKpiMonth: MyKpiMonthResponse? var myKpiWeek: MyKpiWeekResponse? required init?(map: Map){ } func mapping(map: Map) { status <- map["status"] // 给myKpiMonth和myKpiWeek绑定转换器 myKpiMonth <- (map["myKpiMonth"], EmptyArrayToNilTransform<MyKpiMonthResponse>()) myKpiWeek <- (map["myKpiWeek"], EmptyArrayToNilTransform<MyKpiWeekResponse>()) } }
方案二:在mapping方法里手动处理(快速解决)
如果不想写通用转换器,也可以直接在mapping方法里判断字段类型,手动处理空数组的情况:
class GetTodayMyKpiResponse: Mappable{ var status: String? var myKpiMonth: MyKpiMonthResponse? var myKpiWeek: MyKpiWeekResponse? required init?(map: Map){ } func mapping(map: Map) { status <- map["status"] // 处理myKpiMonth字段 if let rawValue = map["myKpiMonth"].currentValue { if let emptyArray = rawValue as? [Any], emptyArray.isEmpty { myKpiMonth = nil } else { myKpiMonth <- map["myKpiMonth"] } } else { myKpiMonth <- map["myKpiMonth"] } // 同理处理myKpiWeek字段 if let rawValue = map["myKpiWeek"].currentValue { if let emptyArray = rawValue as? [Any], emptyArray.isEmpty { myKpiWeek = nil } else { myKpiWeek <- map["myKpiWeek"] } } else { myKpiWeek <- map["myKpiWeek"] } } }
这两种方法都能解决你的问题:当服务器返回空数组时,模型对应的属性会被设为nil,而不是整个模型解析失败返回nil。如果是MyKpiMonthResponse或MyKpiWeekResponse内部的数组字段遇到空数组,只要你把这些数组属性定义为可选类型(比如var kpiItems: [KpiItem]?)或者非可选空数组(var kpiItems: [KpiItem] = []),ObjectMapper都能正常解析,不需要额外处理。
内容的提问来源于stack exchange,提问作者Rahul Gupta
相关产品推荐
相关产品推荐

