无法从Dark Sky API

时间:2017-05-05 12:48:48

标签: ios json swift api

我尝试从Dark Sky API获取有关每小时天气的信息,但代码停止工作在if let data = hourly [" data"]为? [String:AnyObject]行(在每行后用打印内容检查)。我想知道我的代码有什么问题。我认为这可能是"数据"让,但我不确定。

 let Task2 = URLSession.shared.dataTask(with: urlRequestDark) { (data, response, error) in
        if error == nil {
            do {
                let json = try JSONSerialization.jsonObject(with: data!, options: .mutableContainers) as! [String : AnyObject]

                if let hourly = json["hourly"] as? [String : AnyObject] {
                    if let data = hourly["data"] as? [String : AnyObject]{


                        if let hourNum = data["14"] as? [String : AnyObject] {
                            if let chanceRain = hourNum["precipProbability"] as? Float{
                                self.chanceHour1 = String(chanceRain)
                            }
                            DispatchQueue.main.sync {
                                self.ChanceRainLabel.text = self.chanceHour1
                            }
                        }
                    }

                }

            } catch let jsonError {
                print(jsonError.localizedDescription)
            }
        }
    }
    Task2.resume() test

奇怪的是,这确实有效:

let urlRequestDark = URLRequest(url: URL (string: "https://api.darksky.net/forecast/(API Key)/(coordinates)")!)

    let Task = URLSession.shared.dataTask(with: urlRequestDark) { (data, response, error) in
        if error == nil {
            do{
                let json = try JSONSerialization.jsonObject(with: data!, options: .mutableContainers) as! [String : AnyObject]


                if let currently = json["currently"] as? [String : AnyObject] {

                    if let chance2 = currently["precipProbability"] as? Float{
                        print(String(chance2))
                        self.chance = String(Int(chance2 * 100)) + "%"
                        self.PreType = currently["precipType"] as? String
                    }

                        if let _ = json["error"]{
                    }

                    DispatchQueue.main.sync{
                        self.TypeLabel.text = self.PreType
                        self.ChanceLabel.text = self.chance
                    }
                }


            }catch let jsonError{
                print(jsonError.localizedDescription)
            }
        }
    }
    Task.resume()

2 个答案:

答案 0 :(得分:1)

你犯了几个错误。

首先,"data"是一个字典数组,因此它应该转换为[[String:AnyObject]]。

其次,您尝试按字符串下标数组,而不是Int。

第三,在转义闭包时使用self可能会产生保留周期。

让我给你一些固定和调整过的代码。

let task2 = URLSession.shared.dataTask(with: urlRequestDark) { [weak self] (data, response, error) in
    guard error == nil else { return }
    do {
        if let json = try JSONSerialization.jsonObject(with: data!, options: .mutableContainers) as? [String : AnyObject],
            let hourly = json["hourly"] as? [String : AnyObject],
            let data = hourly["data"] as? [[String : AnyObject]],
            data.count > 14,
            let chanceRain = data[14]["precipProbability"] as? Float {
                self?.chanceHour1 = String(chanceRain)
                DispatchQueue.main.sync {
                    self?.ChanceRainLabel.text = self?.chanceHour1
                }
        }
    } catch let jsonError {
        print(jsonError.localizedDescription)
    }
}
task2.resume()

答案 1 :(得分:0)

试试这个

import UIKit

class WebService: NSObject {

    var session = URLSession()

    public class var sharedInstance: WebService {
        struct Singleton {
            static let instance = WebService()
        }
        return Singleton.instance
    }

    override init() {
        let configuration = URLSessionConfiguration.default
        configuration.timeoutIntervalForRequest = 30.0
        configuration.timeoutIntervalForResource = 60.0
        session = URLSession(configuration: configuration)

    }


 public func weatherData(coordinate:String,APIkey:String,completion:@escaping (_ responsedata:NSDictionary?,_ error:NSError?) -> Void) {

            var Baseurl = "https://api.darksky.net/forecast/\(APIkey)/\(coordinate)"
            Baseurl = Baseurl.addingPercentEncoding(withAllowedCharacters: .urlQueryAllowed)!
            let weatherRequestUrl = URL(string: Baseurl)
            let request = NSMutableURLRequest(url: weatherRequestUrl!)
            let task = session.dataTask(with: request as URLRequest) { (data, response, error) in

                guard error == nil && data != nil else {

                    return
                }
                if let httpStatus = response as? HTTPURLResponse{
                    if httpStatus.statusCode != 200 {

                        print("Something is wrong")
                    }
                }
                do {
                    let WindlocationData = try JSONSerialization.jsonObject(with: data! as Data, options:.allowFragments) as! NSDictionary

                    print(WindlocationData)
                    completion(WindlocationData,nil)
                }
                catch let error as NSError {

                    completion(nil,error)
                }
            }
            task.resume()

        }
}

并像这样调用API!

func callAPI(latlong:String,APIkeyParm:String){

WebService.sharedInstance.weatherData(coordinate: latlong,APIkey: APIkeyParm) { (responsData, error) in

    if error == nil{

        print("Response data is-\(responsData)")
    }
}

}

像这样调用方法

let latlongStr = "\(latitude),\(longitude)"
self.callAPI(latlong: latlongStr,APIkeyParm: "APIKeyString")

您需要像这种格式传递latlong一样重要的事情23.022504999999999,72.571362100000002