在Swift中测量HTTP HEAD请求的响应时间

3

我正在尝试在Swift中构建一个函数,向指定的URL发送http HEAD请求,并测量来自服务器的响应时间。 我不关心解析响应,只需要从服务器获得200即可。 我可以使用Python的requests模块完成此操作:

import requests
def get_latency():
    r = requests.head("http://example.com")
    return r.elapsed.total_seconds()

我认为我需要使用NSURL来实现这个功能,虽然已经有了一些进展,但是我还无法确定最佳的方法来发送请求...

let url = NSURL (string: "http://example.com")
let request = NSURLRequest(URL: url!)
let started = NSDate()
  <<<Send http HEAD request, verify response>>>  <- need help here
let interval = NSDate().timeIntervalSinceDate(started)

我今天回答了这个问题:https://dev59.com/cZTfa4cB1Zd3GeqPS5cb#35720670 这是你需要的吗? - Eric Aya
我在沙盒中尝试了一下,但好像没有任何反应... 当我调用这个类时什么也没发生。 - John Sasser
要在Playground中使用异步代码,您需要导入XCPlayground并声明XCPlaygroundPage.currentPage.needsIndefiniteExecution = true。 :) - Eric Aya
好的,那行!你有任何想法在哪里开始/停止我的计时器吗? - John Sasser
哎呀,这太令人困惑了。类函数和isOK的东西真的让我感到很困扰。我只需要传递一个URL列表,构建并发送头请求,验证200,测量并返回响应时间。你有任何想法我该如何实现吗? - John Sasser
显示剩余2条评论
1个回答

4

根据以上评论,我编写了这个版本。我决定将其设计为URL类的扩展。我已经使用Swift 4测试了这段代码。

extension URL {

    /** Request the http status of the URL resource by sending a "HEAD" request over the network. A nil response means an error occurred. */
    public func requestHTTPStatus(completion: @escaping (_ status: Int?) -> Void) {
        // Adapted from https://dev59.com/cZTfa4cB1Zd3GeqPS5cb#35720670
        var request = URLRequest(url: self)
        request.httpMethod = "HEAD"
        let task = URLSession.shared.dataTask(with: request) { (data, response, error) in
            if let httpResponse = response as? HTTPURLResponse, error == nil {
                completion(httpResponse.statusCode)
            } else {
                completion(nil)
            }
        }
        task.resume()
    }

    /** Measure the response time in seconds of an http "HEAD" request to the URL resource. A nil response means an error occurred. */
    public func responseTime(completion: @escaping (TimeInterval?) -> Void) {
        let startTime = DispatchTime.now().uptimeNanoseconds
        requestHTTPStatus { (status) in
            if status != nil {
                let elapsedNanoseconds = DispatchTime.now().uptimeNanoseconds - startTime
                completion(TimeInterval(elapsedNanoseconds)/1e9)
            }
            else {
                completion(nil)
            }
        }
    }
}

使用方法:

let testURL = URL(string: "https://www.example.com")
testURL?.responseTime { (time) in
    if let responseTime = time {
        print("Response time: \(responseTime)")
    }
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接