在swift中下载和解析json

时间:2014-06-05 16:31:10

标签: json parsing swift

我试图从网站获取JSON并在将其放入iOS视图之前对其进行解析。

这是我的代码;

func startConnection(){
        let urlPath: String = "http://binaenaleyh.net/dusor/"
        var url: NSURL = NSURL(string: urlPath)
        var request: NSURLRequest = NSURLRequest(URL: url)
        var connection: NSURLConnection = NSURLConnection(request: request, delegate: self, startImmediately: false)
        connection.start()
    }

    func connection(connection: NSURLConnection!, didReceiveData data: NSData!){
        self.data.appendData(data)
    }

    func buttonAction(sender: UIButton!){
        startConnection()
    }

    func connectionDidFinishLoading(connection: NSURLConnection!) {
        var err: NSError
        // throwing an error on the line below (can't figure out where the error message is)
        var jsonResult: NSDictionary = NSJSONSerialization.JSONObjectWithData(data, options: NSJSONReadingOptions.MutableContainers, error: nil) as NSDictionary
    }

这是JSON的链接;

http://binaenaleyh.net/dusor/

我在这里做错了什么?

9 个答案:

答案 0 :(得分:34)

这两个功能对我有用:

    func getJSON(urlToRequest: String) -> NSData{
        return NSData(contentsOfURL: NSURL(string: urlToRequest))
    }

    func parseJSON(inputData: NSData) -> NSDictionary{
        var error: NSError?
        var boardsDictionary: NSDictionary = NSJSONSerialization.JSONObjectWithData(inputData, options: NSJSONReadingOptions.MutableContainers, error: &error) as NSDictionary

        return boardsDictionary
    }

答案 1 :(得分:23)

这段代码对我来说很好。只需使用data = NSMutableData()初始化数据属性并在此处写入NSURLConnectionDelegate class ViewController: UIViewController, NSURLConnectionDelegate

import UIKit

class ViewController: UIViewController, NSURLConnectionDelegate {

    @lazy var data = NSMutableData()

    override func viewDidLoad() {
        super.viewDidLoad()
    }

    override func viewWillAppear(animated: Bool) {
        super.viewWillAppear(animated)
        startConnection()
    }

    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
    }

    func startConnection(){
        let urlPath: String = "http://binaenaleyh.net/dusor/"
        var url: NSURL = NSURL(string: urlPath)
        var request: NSURLRequest = NSURLRequest(URL: url)
        var connection: NSURLConnection = NSURLConnection(request: request, delegate: self, startImmediately: false)
        connection.start()
    }

    func connection(connection: NSURLConnection!, didReceiveData data: NSData!){
        self.data.appendData(data)
    }

    func buttonAction(sender: UIButton!){
        startConnection()
    }

    func connectionDidFinishLoading(connection: NSURLConnection!) {
        var err: NSError
        // throwing an error on the line below (can't figure out where the error message is)
        var jsonResult: NSDictionary = NSJSONSerialization.JSONObjectWithData(data, options: NSJSONReadingOptions.MutableContainers, error: nil) as NSDictionary
        println(jsonResult)
    }
}

这里是输出:

{
    "ders sayisi" = 15;
    dersler =     (
                {
            0 = "2013-2014";
            1 = BAHAR;
            10 = TeacherHold;
            11 = 2;
            12 = "";
            2 = 2;
            3 = "CEE 102";
            4 = "Logic Circuits";
            5 = 3;
            6 = "6.00";
            7 = "YRD.DO\U00c7.DR.INDRIT MYDERRIZI";
            8 = 0;
            9 = IA;
        },
                {
            0 = "2013-2014";
            1 = BAHAR;
            10 = TeacherHold;
            11 = 1;
            12 = "";
            2 = 2;
            3 = "CIP 102";
            4 = "Civic Involment Projects";
            5 = 0;
            6 = "2.00";
            7 = "SE\U00c7\U0130L AVCI/BA\U015eAK CANSU AK\U00c7EL\U0130K/\U00c7A\U011eLA UNGUN";
            8 = 0;
            9 = P;
        },
                {
            0 = "2013-2014";
            1 = BAHAR;
            10 = TeacherHold;
            11 = 2;
            12 = "";
            2 = 2;
            3 = "COME 108";
            4 = "Algorithms and Programming II";
            5 = 3;
            6 = "6.00";
            7 = "\U00d6\U011eR.G\U00d6R.DR.B\U0130RSEN G\U00dcLDEN \U00d6ZDEM\U0130R";
            8 = 41;
            9 = C;
        },
                {
            0 = "2013-2014";
            1 = BAHAR;
            10 = TeacherHold;
            11 = 1;
            12 = "";
            2 = 2;
            3 = "COME 335";
            4 = "Mobile Application Development";
            5 = 3;
            6 = "5.00";
            7 = "\U00d6\U011eR.G\U00d6R.OZAN UYSAL";
            8 = TeacherHold;
            9 = TeacherHold;
        },
                {
            0 = "2013-2014";
            1 = BAHAR;
            10 = TeacherHold;
            11 = 1;
            12 = "";
            2 = 2;
            3 = "ENG 112";
            4 = "Advanced English For Engineering and Natural Sciences I";
            5 = 2;
            6 = "3.00";
            7 = "OKT.ERIC BEECHER";
            8 = 48;
            9 = F;
        },
                {
            0 = "2013-2014";
            1 = BAHAR;
            10 = TeacherHold;
            11 = 1;
            12 = "";
            2 = 2;
            3 = "PHYS 102";
            4 = "Physics II";
            5 = 4;
            6 = "5.00";
            7 = "YRD.DO\U00c7.DR.\U00d6ZG\U00dcL KURTULU\U015e \U00d6ZT\U00dcRK";
            8 = "-1";
            9 = F;
        },
                {
            0 = "2013-2014";
            1 = BAHAR;
            10 = TeacherHold;
            11 = 2;
            12 = "";
            2 = 2;
            3 = "T\U00dcRK 102";
            4 = "T\U00fcrk Dili II";
            5 = 2;
            6 = "2.00";
            7 = "\U00d6\U011eR.G\U00d6R.\U015eER\U0130FE GEZG\U0130N";
            8 = 10;
            9 = F;
        },
                {
            0 = "2013-2014";
            1 = "G\U00dcZ";
            10 = TeacherHold;
            11 = 2;
            12 = "";
            2 = 1;
            3 = "CHEM 101";
            4 = Chemistry;
            5 = 3;
            6 = "5.00";
            7 = "YRD.DO\U00c7.DR.AY\U015eEN TULPAR";
            8 = TeacherHold;
            9 = F;
        },
                {
            0 = "2013-2014";
            1 = "G\U00dcZ";
            10 = TeacherHold;
            11 = 1;
            12 = "";
            2 = 1;
            3 = "CIP 101";
            4 = "Civic Involment Projects";
            5 = 0;
            6 = "1.00";
            7 = "YRD.DO\U00c7.DR.FATMA G\U00dcL AYGEN/Staff CIP1/SE\U00c7\U0130L AVCI/D\U0130LAYDA EM\U0130R/BA\U015eAK CANSU AK\U00c7EL\U0130K/\U00c7A\U011eLA UNGUN";
            8 = TeacherHold;
            9 = P;
        },
                {
            0 = "2013-2014";
            1 = "G\U00dcZ";
            10 = TeacherHold;
            11 = 3;
            12 = "";
            2 = 1;
            3 = "COME 107";
            4 = "Algorithms and Programming I";
            5 = 4;
            6 = "5.00";
            7 = "PROF.DR.M\U0130TAT UYSAL";
            8 = TeacherHold;
            9 = "C+";
        },
                {
            0 = "2013-2014";
            1 = "G\U00dcZ";
            10 = TeacherHold;
            11 = 2;
            12 = "";
            2 = 1;
            3 = "ENG 101";
            4 = "Advanced English";
            5 = 2;
            6 = "3.00";
            7 = "OKT.EZG\U0130 ARGUN";
            8 = TeacherHold;
            9 = B;
        },
                {
            0 = "2013-2014";
            1 = "G\U00dcZ";
            10 = TeacherHold;
            11 = 1;
            12 = "";
            2 = 1;
            3 = "IUL 100";
            4 = "Introduction to University Life";
            5 = 0;
            6 = "1.00";
            7 = "YRD.DO\U00c7.DR.FATMA G\U00dcL AYGEN";
            8 = TeacherHold;
            9 = F;
        },
                {
            0 = "2013-2014";
            1 = "G\U00dcZ";
            10 = TeacherHold;
            11 = 2;
            12 = "";
            2 = 1;
            3 = "MATH 111";
            4 = "Calculus I";
            5 = 4;
            6 = "5.00";
            7 = "DO\U00c7.DR.G\U00dcRSEL YE\U015e\U0130LOT";
            8 = TeacherHold;
            9 = F;
        },
                {
            0 = "2013-2014";
            1 = "G\U00dcZ";
            10 = TeacherHold;
            11 = 4;
            12 = "";
            2 = 1;
            3 = "PHYS 101";
            4 = "Physics I [CNE]";
            5 = 4;
            6 = "5.00";
            7 = "YRD.DO\U00c7.DR.AR\U0130F \U00d6ZBAY";
            8 = TeacherHold;
            9 = F;
        },
                {
            0 = "2013-2014";
            1 = "G\U00dcZ";
            10 = TeacherHold;
            11 = 9;
            12 = "";
            2 = 1;
            3 = "T\U00dcRK 101";
            4 = "T\U00fcrk Dili I [CNE]";
            5 = 2;
            6 = "2.00";
            7 = "\U00d6\U011eR.G\U00d6R.ARZU AYG\U00dcN";
            8 = TeacherHold;
            9 = F;
        }
    );
}

答案 2 :(得分:19)

更新:Swift 4

// Asynchronous Http call to your api url, using URLSession:
URLSession.shared.dataTask(with: URL(string: "http://api.site.com/json")!) { (data, response, error) -> Void in
    // Check if data was received successfully
    if error == nil && data != nil {
        do {
            // Convert to dictionary where keys are of type String, and values are of any type
            let json = try JSONSerialization.jsonObject(with: data!, options: .mutableContainers) as! [String: Any]
            // Access specific key with value of type String
            let str = json["key"] as! String
        } catch {
            // Something went wrong
        }
    }
}.resume()

以下是使用Swift 2和NSURLSession的方法:

// Asynchronous Http call to your api url, using NSURLSession:
NSURLSession.sharedSession().dataTaskWithURL(NSURL(string: "http://api.site.com/json")!, completionHandler: { (data, response, error) -> Void in
    // Check if data was received successfully
    if error == nil && data != nil {
        do {
            // Convert NSData to Dictionary where keys are of type String, and values are of any type
            let json = try NSJSONSerialization.JSONObjectWithData(data!, options: NSJSONReadingOptions.MutableContainers) as! [String:AnyObject]
            // Access specific key with value of type String
            let str = json["key"] as! String
        } catch {
            // Something went wrong
        }
    }
}).resume()

答案 3 :(得分:7)

如果原始JSON是一个数组,请尝试这个。

func parseJSON(inputData: NSData) -> Array<NSDictionary>{
    var error: NSError?
    var boardsDictionary = NSJSONSerialization.JSONObjectWithData(inputData, options: NSJSONReadingOptions.MutableContainers, error: &error) as Array<NSDictionary>

    return boardsDictionary
}

答案 4 :(得分:4)

以下示例发送获取股票信息的请求 - 它更全面,但有更多的清理和结构:

import Foundation

private let kSNStockInfoFetchRequestPath:String = "http://dev.markitondemand.com/Api/v2/Quote/json"

private func SNStockInfoFetchRequestURL(symbol:String) -> NSURL? {
  if let components:NSURLComponents = NSURLComponents(string:kSNStockInfoFetchRequestPath) {
    components.queryItems = [NSURLQueryItem(name:"symbol", value:symbol)]
    return components.URL
  }
  return nil
}

private func SNStockInfoFetchRequestURLRequest(symbol:String) ->  NSURLRequest? {
  if let requestURL:NSURL = SNStockInfoFetchRequestURL(symbol) {
    var request:NSMutableURLRequest = NSMutableURLRequest(URL:requestURL)
    request.HTTPMethod = "GET"
    return request
  }
  return nil
}

private func SNStockInfoFetchRequestParseData(receivedData:NSData, error:NSErrorPointer) -> NSDictionary? {
  return NSJSONSerialization.JSONObjectWithData(receivedData, options:NSJSONReadingOptions.MutableContainers, error:error) as? NSDictionary
}

class SNStockInfoFetchRequest: NSObject,
NSURLConnectionDataDelegate
{
  private let symbol:String
  private (set) var fetching:Bool
  private lazy var receivedData = NSMutableData()

  init(symbol:String) {
    self.symbol = symbol
    self.fetching = false
  }

  func start() {
    assert(!fetching, "Should not start a request that has already started!")
    fetching = true
    if let request:NSURLRequest = SNStockInfoFetchRequestURLRequest(symbol) {
      var connection:NSURLConnection = NSURLConnection(request:request, delegate:self, startImmediately:true)!
      connection.start()
    }
  }

  // MARK: NSURLConnectionDataDelegate

  func connection(connection:NSURLConnection, didReceiveData data:NSData) {
    assert(fetching, "Should only receive data while activly fetching!")
    self.receivedData.appendData(data)
  }

  func connectionDidFinishLoading(connection:NSURLConnection) {
    var error:NSError?
    if let result:NSDictionary = SNStockInfoFetchRequestParseData(receivedData, &error) {
      println(result)
    } else {
      println(error)
    }

  }
}

我们现在可以使用这样的请求:

let fetcher:SNStockInfoFetchRequest = SNStockInfoFetchRequest(symbol:"MSFT")
fetcher.start()

这应该在成功时输出JSON,或者在出现故障时输出错误。希望这可以帮助!如果使用相同的结构,请确保使用委托来返回已解析的JSON(甚至更好,一个不可变的值对象)或指示失败。

答案 5 :(得分:3)

@ david72的答案对我来说非常合适。为方便起见,Swift 3和URLSession中也是如此。还有一些添加的错误打印,以便于调试。

func getHttpData(urlAddress : String)
{
    // Asynchronous Http call to your api url, using NSURLSession:
    guard let url = URL(string: urlAddress) else
    {
        print("Url conversion issue.")
        return
    }
    URLSession.shared.dataTask(with: url, completionHandler: { (data, response, error) -> Void in
        // Check if data was received successfully
        if error == nil && data != nil {
            do {
                // Convert NSData to Dictionary where keys are of type String, and values are of any type
                let json = try JSONSerialization.jsonObject(with: data!, options: JSONSerialization.ReadingOptions.mutableContainers) as! [String:AnyObject]
                print(json)
                // Access specific key with value of type String
                // let str = json["key"] as! String
            } catch {
                print(error)
                // Something went wrong
            }
        }
        else if error != nil
        {
            print(error)
        }
    }).resume()
}

答案 6 :(得分:3)

这是swift 3.1代码

URLSession.shared.dataTask(with: NSURL(string: "http://pastebin.com/raw/wgkJgazE")! as URL, completionHandler: { (data, response, error) -> Void in
        // Check if data was received successfully
        if error == nil && data != nil {
            do {
                // Convert NSData to Dictionary where keys are of type String, and values are of any type
                let json = try JSONSerialization.jsonObject(with: data!, options: JSONSerialization.ReadingOptions.mutableContainers) as! [String:AnyObject]
                // Access specific key with value of type String
                let str = json["key"] as! String
            } catch {
                // Something went wrong
            }
        }
    }).resume()

答案 7 :(得分:2)

//
//  ViewController.swift
//  Test2
//
//  Created by fingent on 11/08/15.
//  Copyright (c) 2015 fingent. All rights reserved.
//

import UIKit

class ViewController: UIViewController,NSURLConnectionDelegate

{
lazy var data = NSMutableData()

    @IBAction func t1(sender: AnyObject) {
    }

    override func viewDidLoad() {
        super.viewDidLoad()
        // Do any additional setup after loading the view, typically from a nib.
        startConnection()

    }

    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
        // Dispose of any resources that can be recreated.
    }

    func startConnection(){
        let urlPath: String = "https://api.github.com/users/mralexgray"
        var url: NSURL = NSURL(string: urlPath)!
        var request: NSURLRequest = NSURLRequest(URL: url)
        var connection: NSURLConnection = NSURLConnection(request: request, delegate: self, startImmediately: false)!
        connection.start()
    }

    func connection(connection: NSURLConnection!, didReceiveData data: NSData!){
        self.data.appendData(data)
    }

    func buttonAction(sender: UIButton!){
        startConnection()
    }

    func connectionDidFinishLoading(connection: NSURLConnection!) {
        var err: NSError
        // throwing an error on the line below (can't figure out where the error message is)
        var jsonResult: NSDictionary = NSJSONSerialization.JSONObjectWithData(data, options: NSJSONReadingOptions.MutableContainers, error: nil) as NSDictionary
        println(jsonResult)
    }


}

答案 8 :(得分:-1)

在iOS Swift中请求api REST-GET

我展示了一个非常简单的App,其中通过GET方法使用了休息服务,并且在我们的主视图中展示了所获得的信息。

  • 注意: 此项目是使用CocoaPods构建的,有关更多信息,请访问https://cocoapods.org
  • PodFile结构:
# Uncomment the next line to define a global platform for your project
# platform :ios, '8.0'

target 'ExampleRestApi' do
  # Comment the next line if you don't want to use dynamic frameworks
  #use_frameworks!
  
  # Pods for ExampleRestApi
  use_modular_headers!
  pod 'Alamofire', '~> 5.0'
  pod 'AFNetworking', '~> 2.6'
  pod 'ORStackView', '~> 3.0'

end

步骤

  • HelperNetwork.swift :复制HelperNetwork文件,该文件包含通过Alamofire使用服务的方法。
//
//  HelperNetwork.swift
//  ExampleRestApi
//
//  Created by MacBook Pro on 20/11/20.
//

import Foundation
import Alamofire

public var  URL_API = "https://icenparty.pythonanywhere.com/icenPartyWeb/api/v1/"
public var  GET_STORE = "doStore"
public var  METHOD_GET: HTTPMethod = .get

class HelperNetwork{
    
    //Example get json for method GET
    func doRequest(urlString : String,
                   parameters : Parameters,
                   method : HTTPMethod,
                   completion: @escaping (AFDataResponse <Any>)->()) {
        
        let url = URL.init(string: URL_API + urlString)
        AF.request(url!, method: method, parameters: parameters, encoding: URLEncoding.default, headers: nil).responseJSON {
            response in  completion(response)
        }
    }
    
}
  • BaseResponse.swift :复制BaseResponse文件,其中包含与服务响应中获得的信息相对应的模型。
//
//  BaseResponse.swift
//  ExampleRestApi
//
//  Created by MacBook Pro on 20/11/20.
//
/*
 BaseResponse is used to create all the models that
 we need for the service response.
 */

import Foundation

public struct Store : Codable{
    var pk: Int
    var fields: Fields
}

public struct Fields : Codable {
    var file_img_home: String
    var file_img_2: String
    var file_img_3: String
    var title: String
    var subTitle: String
    var description: String
    var value: Int
    var material: String
    var color: String
    var sizes_list: String
    var brand: String
}

public struct JSONResponseStore: Codable {
    var success:  Bool
    var message:  String
    var stores :  [Store]
}
  • ViewController.swift :在我们的viewController文件中,调用我们的doRequest方法 向其传递必要的参数以获得json。
@IBOutlet weak var lblResponse: UILabel!
var helperNetwork = HelperNetwork()
    
/**
     Get info from server for method GET
     */
    func getJsonRequestGET(){
        
        //Set text lbl
        lblResponse.text = "Consultando información...."
        
        //parameters for get , we need tag typeStore
        let parameters: Parameters = [ "typeStore" : "Hombre",]
        
        self.helperNetwork.doRequest(urlString: GET_STORE,
                                     parameters: parameters,
                                     method: METHOD_GET) { (response) -> () in
            // do stuff with the result
            switch response.result
            {
            case .success( _):
                do {
                    
                    //Decode data From model JSONResponseStore , can be changed to any model
                    let JSONData = try JSONDecoder().decode(JSONResponseStore.self, from: response.data!)
                    
                    if(JSONData.success){
                        self.lblResponse.text = "Respuesta: \(JSONData.stores)"
                    }else{
                        self.lblResponse.text = "Respuesta: \(JSONData.message)"
                    }
                    
                } catch let jsonError {
                    self.lblResponse.text = "Respuesta: \(jsonError)"
                }
                
            case .failure(let error):
                self.lblResponse.text = "Respuesta: \(error)"
            }
        }
        
    }

我仍然关注所有问题, 干杯