JSON Parsing With Codable

AlamofireCodable: An extension to Alamofire which automatically converts JSON response data into swift objects using Codable. This project is heavily inspired by the popular AlamofireObjectMapper.

image

Installation

AlamofireCodable can be added to your project using CocoaPods by adding the following line to your Podfile:

pod 'AlamofireCodable'
Example

To run the example project, clone the repo, and run pod install from the Example directory first.

Requirements

Xcode 9+ , Swift 4+

Usage

Given a URL which returns weather data in the following form:

{  
   "data":{  
      "location":"Toronto, Canada",
      "three_day_forecast":[  
         {  
            "conditions":"Partly cloudy",
            "day":"Monday",
            "temperature":20
         },
         {  
            "conditions":"Showers",
            "day":"Tuesday",
            "temperature":22
         },
         {  
            "conditions":"Sunny",
            "day":"Wednesday",
            "temperature":28
         }
      ]
   }
}复制代码

You can use the extension as the follows:

import AlamofireCodable

    let form = WeatherForm()
    Alamofire.request(
            form.url,
            method: HTTPMethod.get,
            parameters: form.parameters(),
            encoding: form.encoding(),
            headers: form.headers()
        )
        .responseObject(keyPath: "data",completionHandler: { (response: DataResponse<Weather>) in
            switch response.result {
            case .success(let object):
                debugPrint("?", object.location)
            case .failure(let error):
                debugPrint("?", error.localizedDescription)
            }
        })复制代码

The Weather object in the completion handler is a custom object which you define. The only requirement is that the object must conform to Codable protocol. In the above example, the Weather object looks like the following:

{  
   "data":{  
      "location":"Toronto, Canada",
      "three_day_forecast":[  
         {  
            "conditions":"Partly cloudy",
            "day":"Monday",
            "temperature":20
         },
         {  
            "conditions":"Showers",
            "day":"Tuesday",
            "temperature":22
         },
         {  
            "conditions":"Sunny",
            "day":"Wednesday",
            "temperature":28
         }
      ]
   }
}复制代码

The extension uses Generics to allow you to create your own custom response objects. Below is the responseObject function definition. Just replace T in the completionHandler with your custom response object and the extension handles the rest:

public func responseObject(queue: DispatchQueue? = nil, keyPath: String? = nil, completionHandler: @escaping (DataResponse) -> Void) -> Self
The responseObject function has 2 optional parameters and a required completionHandler:

queue: The queue on which the completion handler is dispatched.
keyPath: The key path of the JSON where object mapping should be performed
completionHandler: A closure to be executed once the request has finished and the data has been decoded by JSONDecoder.
Easy decode of Nested Objects

AlamofireCodable supports dot notation within keys for easy mapping of nested objects. Given the following JSON String:

{  
   "data":{  
      "location":"Toronto, Canada",
      "three_day_forecast":[  
         {  
            "conditions":"Partly cloudy",
            "day":"Monday",
            "temperature":20
         },
         {  
            "conditions":"Showers",
            "day":"Tuesday",
            "temperature":22
         },
         {  
            "conditions":"Sunny",
            "day":"Wednesday",
            "temperature":28
         }
      ]
   }
}复制代码

You can access the nested objects as follows:

  let form = WeatherForm()
    Alamofire.request(
        form.url,
        method: HTTPMethod.get,
        parameters: form.parameters(),
        encoding: form.encoding(),
        headers: form.headers()
        )
        .responseObject(completionHandler: { (response: DataResponse<RootModel>) in
            switch response.result {
            case .success(let root):
                debugPrint("?", root)
            case .failure(let error):
                debugPrint("?", error.localizedDescription)
            }
        })复制代码

KeyPath

The keyPath variable is used to drill down into a JSON response and only map the data found at that keyPath. It supports nested values such as data.three_day_forecast to drill down several levels in a JSON response.

let form = WeatherForm()
        Alamofire.request(
                form.url,
                method: HTTPMethod.get,
                parameters: form.parameters(),
                encoding: form.encoding(),
                headers: form.headers()
            )
            .responseArray(keyPath: "data.three_day_forecast", completionHandler: { (response: DataResponse<[Forecast]>) in
                switch response.result {
                case .success(let array):
                    debugPrint("?", array)
                case .failure(let error):
                    debugPrint("?", error.localizedDescription)
                }
            })复制代码

Array Responses

If you have an endpoint that returns data in Array form you can map it with the following function:

public func responseArray(queue: DispatchQueue? = nil, keyPath: String? = nil, completionHandler: @escaping (DataResponse<[T]>) -> Void) -> Self
For example, if your endpoint returns the following:

[
    { 
        "conditions": "Partly cloudy",
        "day" : "Monday",
        "temperature": 20 
    },
    { 
        "conditions": "Showers",
        "day" : "Tuesday",
        "temperature": 22 
    },
    { 
        "conditions": "Sunny",
        "day" : "Wednesday",
        "temperature": 28 
    }
]复制代码

You can request and map it as follows:

        let form = WeatherForm()
        Alamofire.request(
                form.url,
                method: HTTPMethod.get,
                parameters: form.parameters(),
                encoding: form.encoding(),
                headers: form.headers()
            )
            .responseArray(keyPath: "data.three_day_forecast", completionHandler: { (response: DataResponse<[Forecast]>) in
                switch response.result {
                case .success(let array):
                    debugPrint("?", array)
                case .failure(let error):
                    debugPrint("?", error.localizedDescription)
                }
            })复制代码

Author

wangchengqvan@gmail.com, chengquan.wang@ele.me

License

AlamofireCodable is available under the MIT license. See the LICENSE file for more info.

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值