Created
July 12, 2016 19:23
-
-
Save fikeminkel/d0dc22c3189864ad34a359074daa28ac to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
struct API { | |
typealias Result = () throws -> JSON | |
enum Error: ErrorType { | |
case ConnectionError(NSError?) | |
case ServerError(statusCode: Int, message: String?) | |
case JSONError(NSError?) | |
} | |
} | |
class APIManager: APIManagerAdapter { | |
static let memoryCacheSize = 2 * 1024 * 1024 | |
static let diskCacheSize = 100 * 1024 * 1024 | |
static let cache = NSURLCache(memoryCapacity: memoryCacheSize, diskCapacity: diskCacheSize, diskPath: nil) | |
let manager: Alamofire.Manager | |
init() { | |
manager = Alamofire.Manager.sharedInstance | |
NSURLCache.setSharedURLCache(APIManager.cache) | |
} | |
func fetchItem(path: String, parameters: [String: AnyObject]? = nil, bypassCache: Bool, handler: API.Result -> Void) -> APIRequest? { | |
let request = requestFor(path: path, parameters: parameters, bypassCache: bypassCache) | |
let afRequest = manager.request(request).responseJSON(completionHandler: responseHandlerFor(handler)) | |
return APIRequestImpl(request: afRequest) | |
} | |
private func requestHeaders(forPath path: String) -> [String: String] { | |
var headers = ["X-Timezone": timeZoneProvider.localTimeZoneName] | |
headers["Authorization"] = { | |
if let sharedHeader = API.sharedAuthorizationHeader { | |
return sharedHeader | |
} | |
let token = authToken(forPath: path) | |
return "SNI1-JWT-SHA256 Application=ITK JWT=\(token)" | |
}() | |
return headers | |
} | |
private func requestFor(path path: String, parameters: [String: AnyObject]? = nil, bypassCache: Bool = false) -> NSMutableURLRequest { | |
let URL = NSURL(string: urlStringFor(path))! | |
let cachePolicy: NSURLRequestCachePolicy = { | |
if bypassCache { | |
return NSURLRequestCachePolicy.ReloadIgnoringLocalCacheData | |
} | |
return NSURLRequestCachePolicy.UseProtocolCachePolicy | |
}() | |
logManager.logMessage("sending request for: \(URL))") | |
let URLRequest = NSMutableURLRequest(URL: URL, cachePolicy: cachePolicy, timeoutInterval: 30) | |
URLRequest.allHTTPHeaderFields = requestHeaders(forPath: path) | |
let encoding = Alamofire.ParameterEncoding.URL | |
return encoding.encode(URLRequest, parameters: parameters).0 | |
} | |
private func responseHandlerFor(resultHandler: API.Result -> Void) -> ResponseHandler { | |
return {[weak self] response in | |
guard let strongSelf = self else { | |
return | |
} | |
let requestURLString = response.request?.URL?.absoluteString ?? "??" | |
guard let serverResponse = response.response else { | |
strongSelf.logManager.logMessage("Connection Error: \(response.result.error) requesting \(requestURLString)") | |
resultHandler { throw API.Error.ConnectionError(response.result.error) } | |
return | |
} | |
guard serverResponse.statusCode >= 200 && serverResponse.statusCode < 300 else { | |
debugPrint("Server Error: \(serverResponse.statusCode) requesting \(response.request?.URL)") | |
var message: String? = nil | |
if let value = response.result.value { | |
message = JSON(value)["display_message"].string | |
} | |
resultHandler { throw API.Error.ServerError(statusCode: serverResponse.statusCode, message: message) } | |
return | |
} | |
guard let value = response.result.value else { | |
strongSelf.logManager.logMessage("JSON Error: \(response.result.error) requesting \(requestURLString)") | |
resultHandler { throw API.Error.JSONError(response.result.error) } | |
return | |
} | |
resultHandler { return JSON(value) } | |
} | |
} | |
} | |
class APIRequestImpl: APIRequest { | |
let request: Alamofire.Request | |
init(request: Alamofire.Request) { | |
self.request = request | |
} | |
func cancel() { | |
request.cancel() | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment