【问题标题】:Upload Stream Requests and UIProgressView, Swift 3上传流请求和 UIProgressView,Swift 3
【发布时间】:2017-03-13 14:34:52
【问题描述】:

我想使用 UIProgressView 跟踪通过流请求上传的视频的进度。不幸的是,我没有使用 Alamofire,所以我不确定 URLSession 是否有这个能力。以下是我的应用程序中的相关代码。

func urlSession(_ session: URLSession, task: URLSessionTask, didSendBodyData bytesSent: Int64, totalBytesSent: Int64, totalBytesExpectedToSend: Int64) {

    let uploadProgress:Float = Float(totalBytesSent) / Float(totalBytesExpectedToSend)
    let uploadCell = contentTableView.cellForRow(at: IndexPath(row: 0, section: 0)) as! NewContentCell
    uploadCell.uploadProgressView.progress = uploadProgress


}

func urlSession(_ session: URLSession, task: URLSessionTask, didCompleteWithError error: Error?) {
    let uploadCell = contentTableView.cellForRow(at: IndexPath(row: 0, section: 0)) as! NewContentCell
    uploadCell.uploadProgressView.progress = 1.0
}

didCompleteWithError 正确设置 UIProgressView 以指示上传完成,但是,didSendBodyData 通过uploadProgress 计算返回大于 1 的值。

这是我第一次使用流请求,所以我希望我只是掩盖了一些你可以帮助指出的东西。这是我的请求的结构以及供参考。

let request = NSMutableURLRequest(url: NSURL(string: "\(requestUrl)")! as URL,
                                          cachePolicy: .useProtocolCachePolicy,
                                          timeoutInterval: 10.0)
        request.httpMethod = "POST"
        request.allHTTPHeaderFields = headers
        request.httpBodyStream = InputStream(data: body as Data)

        let configuration = URLSessionConfiguration.default
        let session = URLSession(configuration: configuration, delegate: self, delegateQueue: OperationQueue.main)
        let dataTask = session.uploadTask(withStreamedRequest: request as URLRequest)
        dataTask.resume()

非常感谢您的意见和帮助。

【问题讨论】:

    标签: swift3 nsurlsession uiprogressview


    【解决方案1】:

    实施

    public func urlSession(_ session: URLSession, task: URLSessionTask, didSendBodyData bytesSent: Int64, totalBytesSent: Int64, totalBytesExpectedToSend: Int64)
    

    是跟踪流请求进程的正确方法。

    但是如果你想现在totalBytesExpectedToSend,你必须告诉服务器。所以不要忘记在您的请求中设置正确的Content-Length 标头!

    这是我创建请求的方式:

    var request = URLRequest(url: url)
    request.setValue("application/octet-stream", forHTTPHeaderField: "Content-Type")
    request.addValue(String(dataToUpload.count), forHTTPHeaderField: "Content-Length") // <-- here!
    request.httpBodyStream = InputStream(data: dataToUpload)
    var task = session.uploadTask(withStreamedRequest: request)
    task?.resume()
    

    【讨论】:

      【解决方案2】:

      进一步阅读文档,发现流对象不支持totalBytesExpectedToSend。这可能是一个 hack,但仅使用文件的 NSData.length 功能就可以进行正确的进度跟踪。因此对于使用 URLSession 的流请求,可以使用didSendBodyData 跟踪进度,使用let uploadProgress: Float = Float(totalBytesSent) / Float(mediaSize),其中mediaSizeNSData.length

      【讨论】:

      • 您是如何跟踪直播进度的? func urlSession(_ session: URLSession, task: URLSessionTask, didSendBodyData bytesSent: Int64, totalBytesSent: Int64, totalBytesExpectedToSend: Int64) 永远不会在流任务上调用!
      • 哎呀。我只是忘了打电话给streamTask.resume()
      猜你喜欢
      • 1970-01-01
      • 2013-03-11
      • 1970-01-01
      • 2018-03-25
      • 2017-11-15
      • 1970-01-01
      • 2020-11-09
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多