Upgrade to Pro — share decks privately, control downloads, hide ads and more …

iOS 8 Networking

iOS 8 Networking

A talk on iOS Networking, HTTP, Caching. Continually evolving.

Ben Scheirman

November 15, 2014
Tweet

More Decks by Ben Scheirman

Other Decks in Programming

Transcript

  1. var session = NSURLSession(configuration: config) or#with#a#delegate... var delegate: NSURLSessionDelegate =

    self var session = NSURLSession(configuration: config, delegate: delegate, delegateQueue: NSOperationQueue.mainQueue())
  2. What%Cons*tutes%an%Error? • Connec'on(failed • Timeouts • Host(invalid • Bad(URL •

    Too(many(redirects • ...(dozens(more((check(URL(Loading(System(Error(Codes)
  3. var config = NSURLSessionConfiguration.defaultSessionConfiguration() var session = NSURLSession(configuration: config) var

    url = NSURL(string: "https://www.nsscreencast.com/api/episodes.json") var task = session.dataTaskWithURL(url) { (let data, let response, let error) in // ... }
  4. var config = NSURLSessionConfiguration.defaultSessionConfiguration() var session = NSURLSession(configuration: config) var

    url = NSURL(string: "https://www.nsscreencast.com/api/episodes.json") var task = session.dataTaskWithURL(url) { (let data, let response, let error) in // ... } // don't forget to trigger the request task.resume()
  5. Have%you%ever%seen%this? NSURL *imageUrl = [NSURL URLWithString:@”http://i.imgur.com/kwpjYwQ.jpg”]; NSData *imageData = [NSData

    dataWithContentsOfURL:imageUrl]; UIImage *image = [UIImage imageWithData:imageData]; [imageView setImage:image];
  6. What%is%wrong%here? NSURL *imageUrl = [NSURL URLWithString:@”http://i.imgur.com/kwpjYwQ.jpg”]; NSData *imageData = [NSData

    dataWithContentsOfURL:imageUrl]; UIImage *image = [UIImage imageWithData:imageData]; [imageView setImage:image];
  7. import UIKit import ObjectiveC extension UIImageView { func loadImageFromURL(url: NSURL,

    placeholderImage: UIImage? = nil) { var session = ... // where do we store this? } }
  8. Get$/$set$value$associated$with$the$class$ instance var session: NSURLSession? { get { return objc_getAssociatedObject(UIImageView.self,

    &sessionKey) as NSURLSession? } set { objc_setAssociatedObject(UIImageView.self, &sessionKey, newValue, UInt(OBJC_ASSOCIATION_RETAIN)) } }
  9. Tracking)the)task)for)each)cell)object var imageTask: NSURLSessionTask? { get { return objc_getAssociatedObject(self, &taskKey)

    as NSURLSessionTask? } set { objc_setAssociatedObject(self, &taskKey, newValue, UInt(OBJC_ASSOCIATION_RETAIN)) } }
  10. func loadImageFromURL(url: NSURL, placeholderImage: UIImage? = nil) { if session

    == nil { session = NSURLSession(configuration: NSURLSessionConfiguration.defaultSessionConfiguration()) } // cancel any previous in-flight request imageTask?.cancel() // show the placeholder while we're loading image = placeholder // ... }
  11. imageTask = session?.dataTaskWithURL(url) { (data, response, error) in if error

    == nil { // handle success case } else { println("error with \(url): \(error)") } self.imageTask = nil } imageTask?.resume()
  12. let http = response as NSHTTPURLResponse if http.statusCode == 200

    { // have we started loading a different image yet? if self.imageTask?.state == NSURLSessionTaskState.Canceling { return } let image = UIImage(data: data) dispatch_async(dispatch_get_main_queue()) { self.image = image } } else { println("\(url) received HTTP \(http.statusCode)") }
  13. def show @band = Band.find(params[:id]) fresh_when(:etag => @band, :last_modified =>

    @band, :public => true) expires_in 10.minutes, :public => true end
  14. Tuning&the&built,in&cache let MB = 1024 * 1024 var cache =

    NSURLCache(memoryCapacity: 10 * MB, diskCapacity: 50 * MB, diskPath: nil) sessionConfiguration.URLCache = cache
  15. let url = NSURL(string: "http://cache-tester.herokuapp.com/contacts.json") let request = NSURLRequest(URL: url)

    if let cachedResponse = config.URLCache.cachedResponseForRequest(request) { // update UI processData(cachedResponse.data) } var task = session.dataTaskWithRequest(request) task.resume()
  16. New$in$iOS$8:$getCachedResponseForTask: • Provides*asynchronous*cache*fetch: let url = NSURL(string: "http://localhost:3000/contacts.json") let request

    = NSURLRequest(URL: url) var task = session.dataTaskWithRequest(request) config.URLCache.getCachedResponseForDataTask(task) { (let cachedResponse: NSCachedURLResponse?) in if cachedResponse != nil { self.processData(cachedResponse!.data) } task.resume() }