2017-06-15 49 views
0

我想使用URL斯威夫特 - 如何使用ObjectMapper閱讀Flickr的JSON

https://api.flickr.com/services/feeds/photos_public.gne?nojsoncallback=1&format=json

我試圖用Alamofire消耗JSON消耗從來自Flickr的公開可用的飼料JSON然後使用ObjectMapper將JSON映射到基本的照片數據模型。

我遇到的問題是,我無法得到它的解析JSON,然後映射。

objects = Mapper<Photo>().mapArray(JSONArray: json)!

返回:

Cannot convert value of type 'JSON' to expected argument type '[[String : Any]]'

我的代碼如下:

FlickrAPI.executeRequestURL(url, parameters: parameters) { (success, error, response) in 
      if (success) { 
       //print ("Response: \(response)") 

       if let jsonObject = response?.result.value { 
        let json = JSON(jsonObject) 

        objects = Mapper<Photo>().mapArray(JSONArray: json)! 

       } 

      } 
      else { 
       print ("** Error -- \(error?.localizedDescription) **") 
       taskCallback(false, error) 
      } 
     } 
// Execute URL request code: 
static func executeRequestURL(_ requestURL: URL, parameters:[String: String], taskCallback: @escaping (Bool, Error?, DataResponse<Any>?) ->()) 
    { 
     print ("Attempting URL -- \(requestURL)") 

     Alamofire.request(requestURL, parameters:["nojsoncallback": "1", "format": "json"]) 
      .validate(statusCode: 200..<300) 
      .validate(contentType: ["application/json"]) 
      .responseJSON { response in 

       switch(response.result) { 
       case .success(_): 
        taskCallback(true, nil, response) 
        break 

       case .failure(_): 
        print("Error while fetching url: \(response.result.error)") 
        taskCallback(false, response.result.error, nil) 
        break 
       } 
     } 
    } 

// Photo model 

final class Photo: Object, Mappable { 
    private(set) dynamic var uuid: String = UUID().uuidString 

    dynamic var name: String = "" 
    dynamic var author_id: String = "" 
    dynamic var title: String = "" 

override public static func primaryKey() -> String? { 
     return "uuid" 
    } 

    required convenience public init?(map: Map) { 
     self.init() 
    } 

    // MARK: - ObjectMapper protocol methods 

    public func mapping(map: Map) { 
     self.name <- map["name"] 
     self.author_id <- map["author_id"] 
     self.title <- map["title"] 
    } 

在審查照片公共URL我注意到響應在一個陣列整理在一起攝物體稱爲"items":

我讀,我可以使用AlamofireObjectMapper幫助;但我對如何實際使用它感到困惑。

反正我的查詢是具體我怎麼消耗Flickr的公開照片內的items陣列使用ObjectMapper飼料?

非常感謝

回答

0

我能解決這個使用AlamofireObjectMapper

首先,創建一個類來抱回來的響應。其次確保這個類符合映射;

// Required to help integrate Alamofire with Objectmapper (via AlamofireObjectMapper) 
final class PhotoResponse: Mappable { 

    var items: [Photo]? 

    required init?(map: Map){ 

    } 

    func mapping(map: Map) { 
     items <- map["items"] 
    } 
} 

然後,當我調用執行URL時,我稍微改變它,以便它符合這個類;

static func executeRequestURL(_ requestURL: URL, parameters:[String: String], taskCallback: @escaping (Bool, Error?, DataResponse<PhotoResponse>?) ->()) 
    { 
     print ("Attempting URL -- \(requestURL)\n") 

     Alamofire.request(requestURL, parameters:["nojsoncallback": "1", "format": "json"]) 
      .validate(statusCode: 200..<300) 
      .validate(contentType: ["application/json"]) 
      .responseObject { (response: DataResponse<PhotoResponse>) in 

       switch(response.result) { 
       case .success(_): 
        taskCallback(true, nil, response) 
        break 

       case .failure(_): 
        print("** Error while fetching url: \(response.result.error) **") 
        taskCallback(false, response.result.error, nil) 
        break 
       } 
     } 
    } 

這裏的關鍵部分是response: DataResponse<PhotoResponse>) in行。

最後,當我們通過我fetchPublicPhotos函數中調用它,我可以查詢結果回來

let photoResponse = response?.result.value 

if let items = photoResponse?.items { 
    print ("Items found: #\(items.count)") 
    // do something with items here 
}