In my iOS app, I create a URLSession with default configuration:
// Part #1
let urlSession = URLSession(configuration: .default)
The user logs in, the cookies are set and all API requests are Authorized and work fine. Now with the same cookies, I want to create a background URLSession for downloading large files from the same server.
// Part #2
lazy var downloadsSession: URLSession = {
let configuration = URLSessionConfiguration.background(withIdentifier:"x.bgSession")
// Use cookies from shared storage
configuration.httpCookieStorage = HTTPCookieStorage.shared
return URLSession(configuration: configuration, delegate: self, delegateQueue: nil)
}()
The download request fails and the server returns Unauthorized . Using mitmproxy when I intercept this request, I notice that for downloadsSession , cookies are not set while making the HTTP download request.
However, now when I create a new ephemeral session, the Authorization works fine.
// Part #3
let sessionConfiguration = URLSessionConfiguration.ephemeral
sessionConfiguration.httpCookieStorage = HTTPCookieStorage.shared
session_ = URLSession(configuration: sessionConfiguration, delegate: self, delegateQueue: nil);
What is the difference between Part #2 & Part #3 in terms of Authorization (setting cookies)? Why Part #3 succeeds while Part #2 fails?
for your part #1, #2, #3 add following line to request
request.httpShouldHandleCookies=true
If it still give you the same error consult your backend developer and check download permissions for file your trying to download
for complete help you may check following code
let mainUrl = "your request url"
request.httpMethod = serviceType
request.httpShouldHandleCookies=true
let cookie = HTTPCookie.requestHeaderFields(with: HTTPCookieStorage.shared.cookies(for: mainUrl as URL)!)
request = setAccessToken_Cookie(request: request)
request.allHTTPHeaderFields = cookie
var session = URLSession(configuration: URLSessionConfiguration.default)
session = NetworkManager().configureURLSessionMethodWithDelegate(session: session)
if downloadable
{
Downloader.downloadFile(url: mainUrl as URL, session: session, request:request, completion: {
})
}
import Foundation
import UIKit
class Downloader:NSObject, URLSessionDownloadDelegate
{
class func downloadFile(url: URL,session:URLSession, request:NSMutableURLRequest, completion: @escaping () -> ()) {
var delegateSession = Downloader().configureURLSessionMethodDelegate(session: session)
let downloads = delegateSession.downloadTask(with: request as URLRequest)
downloads.resume()
}
func configureURLSessionMethodDelegate( session:URLSession) -> URLSession {
var sessionWithDelegate = session
sessionWithDelegate = URLSession(configuration: URLSessionConfiguration.default, delegate: self, delegateQueue:OperationQueue.main)
return sessionWithDelegate
}
func urlSession(_ session: URLSession, downloadTask: URLSessionDownloadTask, didFinishDownloadingTo location: URL) {
guard let httpResponse = downloadTask.response as? HTTPURLResponse,
(200...299).contains(httpResponse.statusCode) else {
print ("error : \(error according to your response code)")
return
}
do {
let documentsURL = try
FileManager.default.url(for: .documentDirectory,
in: .userDomainMask,
appropriateFor: nil,
create: false)
let savedURL = documentsURL.appendingPathComponent(downloadTask.response?.suggestedFilename ?? "noname")
print(location)
print(savedURL)
if FileManager.default.fileExists(atPath: savedURL.path)
{
AppUtility?.displayAlert(title: appName, messageText: "A file with same name already exist", delegate: nil)
}
else{
try FileManager.default.copyItem(at: location, to: savedURL)
}
} catch {
print ("file error: \(error)")
}
}
func urlSession(_ session: URLSession, downloadTask: URLSessionDownloadTask, didWriteData bytesWritten: Int64, totalBytesWritten: Int64, totalBytesExpectedToWrite: Int64)
{
guard let httpResponse = downloadTask.response as? HTTPURLResponse,
(200...299).contains(httpResponse.statusCode) else {
print ("server error")
return
}
}
func urlSession(_ session: URLSession, task: URLSessionTask, didCompleteWithError error: Error?) {
DispatchQueue.main.async(execute: { () -> Void in
if(error != nil)
{
//handle the error
print("Download completed with error: \(error!.localizedDescription)");
}
})
}
}
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.