Skip to content

Instantly share code, notes, and snippets.

@Sonictherocketman
Last active May 24, 2016 23:13
Show Gist options
  • Save Sonictherocketman/a228bf37914c3cb4f80a3bad47fd615c to your computer and use it in GitHub Desktop.
Save Sonictherocketman/a228bf37914c3cb4f80a3bad47fd615c to your computer and use it in GitHub Desktop.
A service for managing remote models fetched via a Django REST API.
// NetworkService.swift
import Alamofire
import AlamofireObjectMapper
import ObjectMapper
/*!
* A service that abstracts the underlying network calls and stores data
* to the data store, or returns them in the completion handler.
*/
struct NetworkService {
static var endpoints: Dictionary<String, String>?
init(apiRootUrl: String) {
Alamofire.request(.GET, apiRootUrl, parameters: nil, encoding: .URL, headers: nil).responseJSON { (response: Response<AnyObject, NSError>) in
if let data = response.data {
do {
let json = try NSJSONSerialization.JSONObjectWithData(data, options: NSJSONReadingOptions.AllowFragments)
NetworkService.endpoints = json as? Dictionary<String, String>
} catch {
//Failed to fetch API endpoints.
fatalError("Failed to fetch intial endpoints.")
}
}
}
}
// MARK: Private Methods
/*!
* Fetch a results list from the given API endpoint.
*/
private static func getResults<T: RemoteResultProtocol>(url: String, params: Dictionary<String, String>?, headers: Dictionary<String, String>?,
completionHandler: (results: [T]) -> ()) {
let queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0)
let request = Alamofire.request(.GET, url, parameters: params, encoding: .URL, headers: headers)
request.responseArray(queue: queue, keyPath: "results") { (results: Response<[T], NSError>) in
if let value = results.result.value {
completionHandler(results: value)
}
}
}
/*!
* Fetch a single item from the given API endpoint.
*/
private static func getObject<T: RemoteResultProtocol>(url: String, params: Dictionary<String, String>?, headers: Dictionary<String, String>?,
completionHandler: (result: T) -> ()) {
let queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0)
let request = Alamofire.request(.GET, url, parameters: params, encoding: .URL, headers: headers)
request.responseObject(queue: queue, keyPath: "") { (result: Response<T, NSError>) in
if let value = result.result.value {
completionHandler(result: value)
}
}
}
/*!
* Update a given item at the given API endpoint.
*/
private static func putObject<T: RemoteResultProtocol>(object: T, url: String, params: Dictionary<String, String>?,
headers: Dictionary<String, String>?, completionHandler: (response: Response<AnyObject, NSError>) -> ()) {
let queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0)
let request = Alamofire.request(.PUT, url, parameters: params, encoding: .URLEncodedInURL, headers: headers)
request.responseJSON(queue: queue, completionHandler: completionHandler)
}
/*!
* Delete a given item from the given API endpoint.
*/
private static func deleteObject<T: RemoteResultProtocol>(object: T, url: String, params: Dictionary<String, String>?,
headers: Dictionary<String, String>?, completionHandler: (Response<AnyObject, NSError>) -> ()) {
let queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0)
let request = Alamofire.request(.DELETE, url, parameters: params, encoding: .URLEncodedInURL, headers: headers)
request.responseJSON(queue: queue, completionHandler: completionHandler)
}
}
protocol RemoteResultProtocol: Mappable {
static var serializedIdentifier: String { get set }
var url: String { get set }
}
extension RemoteResultProtocol {
/*!
* Fetch a single object from the remote API.
*/
static func getSingle<T: RemoteResultProtocol>(completionHandler: (_: T) -> ()) {
let endpoint = NetworkService.endpoints![serializedIdentifier]
NetworkService.getObject(endpoint!, params: nil, headers: nil, completionHandler: completionHandler)
}
/*!
* Fetch a result set from the remote API.
*/
static func getResultSet<T: RemoteResultProtocol>(completionHandler: (_: [T]) -> ()) {
let endpoint = NetworkService.endpoints![serializedIdentifier]
NetworkService.getResults(endpoint!, params: nil, headers: nil, completionHandler: completionHandler)
}
/*!
* Search for a result set from the remote API.
*/
static func search<T: RemoteResultProtocol>(params: Dictionary<String, String>?, completionHandler: (_: [T]) -> ()) {
let endpoint = NetworkService.endpoints![serializedIdentifier]
NetworkService.getResults(endpoint!, params: params, headers: nil, completionHandler: completionHandler)
}
/*!
* Given a model, persist it to the remote API.
*/
func save(headers: Dictionary<String, String>?, completionHandler: (response: Response<AnyObject, NSError>) -> ()) {
NetworkService.putObject(self, url: self.url, params: nil, headers: nil, completionHandler: completionHandler)
}
/*!
* Deletes a given model from the remote API.
*/
func delete(headers: Dictionary<String, String>?, completionHandler: (response: Response<AnyObject, NSError>) -> ()) {
NetworkService.deleteObject(self, url: self.url, params: nil, headers: headers, completionHandler: completionHandler)
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment