在webservice之后执行segue

时间:2018-03-21 08:06:22

标签: ios swift segue

您好我不熟悉iOS开发并想知道iOS中是否有相同的asynctask?我希望我的Web服务完成,然后我想将我的Web服务的内容传递给nextview controller

@IBAction func searchAction(_ sender: Any) {

    let airportName: String = airportCode.text!
    let minutesBefore: String = minutesBehind.text!
    let minutesAfter: String = minutesAhead.text!

    //web service request

    self.data = FlightWebService().getFlightData(airportCode: airportName, minutesBehind: minutesBefore, minutesAhead: minutesAfter)
    print(self.data)


    //how to pass data to the next view controller
    performSegue(withIdentifier: "goToSearch", sender: self)
}

3 个答案:

答案 0 :(得分:1)

您可以使用ios 7.0及更高版本中提供的URLSession。

在您的方法中,您可以运行异步任务

func searchAction() {
    let defaultSessionConfiguration = URLSessionConfiguration.default
    let defaultSession = URLSession(configuration: defaultSessionConfiguration)

    let url = URL(string: "typeHereYourURL")
    var urlRequest = URLRequest(url: url!)

    let params = ""// json or something else
    let data = params.data(using: .utf8)

    urlRequest.httpMethod = "POST"
    urlRequest.httpBody = data

    let dataTask = defaultSession.dataTask(with: urlRequest) { (data, response, error) in
        performSegue(withIdentifier: "YourVCIdentifier", sender: self)
    }

    dataTask.resume()
}

或者您可以创建串行队列并在另一个线程中运行FlightWebService请求

func searchAction() {
    let newQueue = DispatchQueue(label: "queue_label")
    newQueue.async {
        self.data = FlightWebService().getFlightData(airportCode: airportName, minutesBehind: minutesBefore, minutesAhead: minutesAfter)
        print(self.data)

        DispatchQueue.main.async {
            performSegue(withIdentifier: "YourVCIdentifier", sender: self)
        }
    }
}

并覆盖它以将参数发送到下一个ViewController

override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
    if segue.identifier == "YourVCIdentifier" {
        if let destinationVC = segue.destination as? YourVC {
            destinationVC.exampleStringProperty = //send data here recived earlier
        }
    }
}

答案 1 :(得分:0)

根据@ SH_Khan的要求,我已将URLRequest来电置于FlightWebService课程内。这应该可以解决问题。

class FlightWebService {

    // Change the method's signature to accept a completion block
    static func getFlightData(airportCode: String, minutesBehind: String, minutesAhead: String, completion: (Data?, Response?, Error?) -> Void) {
        let defaultSessionConfiguration = URLSessionConfiguration.default
        let defaultSession = URLSession(configuration: defaultSessionConfiguration)

        let url = URL(string: "typeHereYourURL")
        var urlRequest = URLRequest(url: url!)

        let params = ""// json or something else
        let data = params.data(using: .utf8)

        urlRequest.httpMethod = "POST"
        urlRequest.httpBody = data

        // Launch the task **IN BACKGROUND** with the provided completion handler block
        DispatchQueue.global(qos: .background).async {
            let dataTask = defaultSession.dataTask(with: urlRequest, completionHandler: completion) 
            dataTask.resume()
        }
    }
}

@IBAction func searchAction(_ sender: Any) {

    let airportName: String = airportCode.text!
    let minutesBefore: String = minutesBehind.text!
    let minutesAfter: String = minutesAhead.text!

    //web service request
    FlightWebService().getFlightData(airportCode: airportName, minutesBehind: minutesBefore, minutesAhead: minutesAfter) { (data, response, error) in
        self.data = data
        print(self.data)
        // Always perform view-related stuff on the main thread
        DispatchQueue.main.async {
            performSegue(withIdentifier: "goToSearch", sender: self)
        }
    }
}

答案 2 :(得分:0)

您的FlightService函数需要执行异步任务,并使用completionHandlers将响应传递回调用代码。

请参阅以下代码

// model
class Flight {}

// flight service
class FlightService: NSObject
{
    func getFlightData(airportCode: String, minutesBehind: Int, minutesAhead: Int, completion: @escaping (Bool, [Flight]?) -> Void) {
        // main thread still
        let url = NSURL(string: "http://..........")!
        let request = NSMutableURLRequest(url: url as URL)
        request.httpMethod = "Get"

        // This always runs in the background, so no need to specifically put it there
        let task = URLSession.shared.dataTask(with: request as URLRequest){ data,response,error in
            guard error == nil else {
                completion(false, nil)
                return
            }

            // parse response data instead I'll create blank array
            var parsedFlights = [Flight]()
            completion(true, parsedFlights)
        }

        task.resume()
    }
}

// USAGE

@IBAction func searchAction(_ sender: Any) {

    let airportName: String = "airportCode.text!"
    let minutesBefore: String = "minutesBehind.text!"
    let minutesAfter: String = "minutesAhead.text!"

    FlightWebService().getFlightData(airportCode: airportName, minutesBehind: minutesBefore, minutesAhead: minutesAfter) { [weak self] success, flights in
        // we are still in a background thread here and would need to Dispatch to the main thread to update any UI
        guard let strongSelf = self, success else { return }

        print(flights.count)
        strongSelf.flightSearchResults = flights
        strongSelf.performSegue(withIdentifier: "goToSearch", sender: self)
    }
}

NSURLSession总是在后台线程中运行,因此无需手动调度。

在searchFunction中,一旦completionHandler返回,我们仍然在后台线程中运行,但我们已经解析了我们的响应数据并传回了飞行数据,如果我们需要从这里更新任何UI,我们需要发送到主线程。

注意:您通常也应该在闭包中使用weak self,因为在异步任务期间,我们可能已经丢失了对调用类(self)的引用。