Mobile Api and Caching

Post on 04-Dec-2014

1,952 views 1 download

description

Presentation from Pierre-Luc Simard, CTO of Mirego.

transcript

MOBILE API AND CACHINGMaking the most of your APIs

PERFORMANCE MATTERS.

MOBILE APPLICATIONAVERAGE API RESPONSE TIME.

1.24seconds

source: New Relic

TIME SPENT.

SERVER 20%

NETWORK 80%

BASIC MATHEMATICS.

session durationrequest duration = requests

per session

WILDLY INACCURATE TESTS.Check my balance43 requests in 70 seconds

Check-in46 requests in 30 seconds

Open a message 24 requests in 40 seconds

AVERAGE:

0.92second

THE HARD STUFF.

•INCREASE SESSION TIME. •REDUCE REQUEST TIME.

DOING MORE.

session durationrequest duration = requests

per session

MAKE FEWER REQUESTS PER ACTION.

BE SPECIFIC.

WEB BROWSER CACHES EVERYTHINGUNLESS TOLD OTHERWISE.

MOBILE APPLICATIONCACHES NOTHINGUNLESS TOLD OTHERWISE.

BASIC REQUIREMENT.

ONE =objectONE

URI

FOLLOWING JSON API GUIDELINES HELPS ENSURE OBJECT TO URI EQUIVALENCY.http://jsonapi.org

HTTP, FOR YOU IT WORKS.

GET /collections/12 HTTP/1.1 Host: flipbit.dev !HTTP/1.1 200 OK Date: Thu, 17 Oct 2013 01:42:00 GMT Accept-Ranges: bytes Content-Type: application/vnd.api+json Content-Length: 42 Connection: keep-alive Location: http://flipbit.dev/collections/12

GET /collections/12 HTTP/1.1 Host: flipbit.dev !HTTP/1.1 200 OK Date: Thu, 17 Oct 2013 01:42:00 GMT Last-Modified: Thu, 17 Oct 2013 01:38:57 GMT ETag: "b79f914dde3ab5e3095372de46591b46" Expires: Thu, 24 Oct 2013 01:38:57 GMT Cache-Control: max-age=604800, private Accept-Ranges: bytes Content-Type: application/vnd.api+json Content-Length: 42 Connection: keep-alive Location: http://flipbit.dev/collections/12

GET /collections/12 HTTP/1.1 Host: flipbit.dev If-Modified-Since: Thu, 10 Oct 2013 20:14:48 GMT If-None-Match: "a1846ac92492d2347c6235b4d2611184" !HTTP/1.1 200 OK Date: Thu, 17 Oct 2013 01:42:00 GMT Last-Modified: Thu, 17 Oct 2013 01:38:57 GMT ETag: "b79f914dde3ab5e3095372de46591b46" Expires: Thu, 24 Oct 2013 01:38:57 GMT Cache-Control: max-age=604800, private Accept-Ranges: bytes Content-Type: application/vnd.api+json Content-Length: 42 Connection: keep-alive Location: http://flipbit.dev/collections/12

CACHE-CONTROL ON AMAZON S3.

GET /buket.mycompany.com/welcome.json HTTP/1.1 Host: s3.amazonaws.com !HTTP/1.1 200 OK x-amz-id-2: UleVE3wbOPZa2EW+RpWj834yy5OOMLNmi/w… x-amz-request-id: 4ADBB2EBF80F5D46 Date: Thu, 17 Oct 2013 01:42:00 GMT Last-Modified: Thu, 17 Oct 2013 01:38:57 GMT ETag: "b79f914dde3ab5e3095372de46591b46" Accept-Ranges: bytes Content-Type: application/octet-stream Content-Length: 23 Connection: keep-alive Server: AmazonS3

GET /buket.mycompany.com/welcome.json HTTP/1.1 Host: s3.amazonaws.com !HTTP/1.1 200 OK x-amz-id-2: UleVE3wbOPZa2EW+RpWj834yy5OOMLNmi/w… x-amz-request-id: 4ADBB2EBF80F5D46 Date: Thu, 17 Oct 2013 01:42:00 GMT Last-Modified: Thu, 17 Oct 2013 01:38:57 GMT ETag: “b79f914dde3ab5e3095372de46591b46" Cache-Control: ??? Expires: ??? Accept-Ranges: bytes Content-Type: application/octet-stream Content-Length: 23 Connection: keep-alive Server: AmazonS3

CACHING IS UNCERTAIN.

•There’s no cache-control header so it’s left to the client to decide.

•iOS most likely will cache between 6 hours and 1 day and will always revalidate.

•Android it depends, but most likely won’t cache.

DON’T LET THE CLIENT DECIDE.

•Add the x-amz-meta-Cache-Control header when doing a PUT to S3.

•It’s recommended to use a max-age of at least one month.

•Don’t use x-amz-meta-Expires. The object will not be cached after its expiry date.

CACHE-CONTROL WITH RUBY ON RAILS.

GET /collections/12 HTTP/1.1 Host: app.mycompany.com !Cache-Control: max-age=0, private, must-revalidate Content-Type: application/json; charset=utf-8 ETag: "4a200c9d8fb14925e7461d63b59f4e82" Server: nginx/1.2.3 + Phusion Passenger 3.0.17 (mod_rails/mod_rack) Set-Cookie: request_method=GET; path=/ Status: 200 Content-Length: 144 Connection: Close

FIXING CACHE-CONTROL.class FlipsController < ApplicationController respond_to :json ! def index # ... ! # Last-Modified and ETag flipbit_etag = Digest::MD5.digest(@flipbit.to_s).to_s fresh_when last_modified: DateTime.now, etag: flipbit_etag ! # Cache-Control expires_in 3.day, :must_revalidate => false, :public => true # ... end end

GET /collections/12 HTTP/1.1 Host: app.mycompany.com !Cache-Control: max-age=86400, public Content-Type: application/json; charset=utf-8 ETag: "4a200c9d8fb14925e7461d63b59f4e82" Server: nginx/1.2.3 + Phusion Passenger 3.0.17 (mod_rails/mod_rack) Set-Cookie: request_method=GET; path=/ Status: 200 Content-Length: 144 Connection: Close

CACHING IS BETTER.

•iOS will honour the cache-control header as long as there’s cache space.

•Android apache’s HttpClient does not handle caching, android-query does.

CACHING ON THE DEVICE.

NEVER HARD CODE CACHE LOGIC.

MAKE SURE YOU HAVE ENOUGH STORAGE.

CACHE ON iOS.- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions { NSUInteger mb = 1024*1024; ! // Configure NSURLCache with larger storage [NSURLCache setSharedURLCache: [[NSURLCache alloc] initWithMemoryCapacity:(50*mb) diskCapacity:(100*mb) diskPath:nil] ]; ! // ... // ... return YES; }

MAKE EVERY ROUND-TRIP COUNT.

BONUS MATERIAL.Amazon S3 performance.

S3 GET PERFORMANCE.

•Make sure you set your Cache-Control headers using x-amz-meta-Cache-Control.

•Intensive objects benefit from CloudFront by a factor of 2 or more.

S3 PUT PERFORMANCE.

•Avoid sequential keys. S3 stores key names in alphabetical order; key name dictates which partition the key is stored in.http://bit.ly/s3performance

AVOID DATES AS PREFIX.examplebucket/2013-26-05-15-00-00/cust1234234/photo1.jpg examplebucket/2013-26-05-15-00-00/cust3857422/photo2.jpg examplebucket/2013-26-05-15-00-00/cust1248473/photo2.jpg examplebucket/2013-26-05-15-00-00/cust8474937/photo2.jpg examplebucket/2013-26-05-15-00-00/cust1248473/photo3.jpg ... examplebucket/2013-26-05-15-00-01/cust1248473/photo4.jpg examplebucket/2013-26-05-15-00-01/cust1248473/photo5.jpg examplebucket/2013-26-05-15-00-01/cust1248473/photo6.jpg examplebucket/2013-26-05-15-00-01/cust1248473/photo7.jpg ...

USE HASH AS PREFIX.examplebucket/232a-2013-26-05-15-00-00/cust1234234/photo1.jpg examplebucket/7b54-2013-26-05-15-00-00/cust3857422/photo2.jpg examplebucket/921c-2013-26-05-15-00-00/cust1248473/photo2.jpg examplebucket/ba65-2013-26-05-15-00-00/cust8474937/photo2.jpg examplebucket/8761-2013-26-05-15-00-00/cust1248473/photo3.jpg examplebucket/2e4f-2013-26-05-15-00-01/cust1248473/photo4.jpg examplebucket/9810-2013-26-05-15-00-01/cust1248473/photo5.jpg examplebucket/7e34-2013-26-05-15-00-01/cust1248473/photo6.jpg examplebucket/c34a-2013-26-05-15-00-01/cust1248473/photo7.jpg ...

SHARING A BUCKET?examplebucket/my_beautiful_app/40434b70/avatar.jpg examplebucket/my_beautiful_app/4ee66b70/avatar.jpg examplebucket/my_beautiful_app/753da383/avatar.jpg examplebucket/my_beautiful_app/91255df0/avatar.jpg examplebucket/my_beautiful_app/98e26030/avatar.jpg examplebucket/my_very_nice_app/a2cb3fdb/video.mpg examplebucket/my_very_nice_app/cf763412/video.mpg examplebucket/my_very_nice_app/d6e93451/video.mpg examplebucket/my_very_nice_app/e68f7670/video.mpg ...

USE SHORT FIXED PREFIX!examplebucket/mba/40434b70/avatar.jpg examplebucket/mba/4ee66b70/avatar.jpg examplebucket/mba/753da383/avatar.jpg examplebucket/mba/91255df0/avatar.jpg examplebucket/mba/98e26030/avatar.jpg examplebucket/mvna/a2cb3fdb/video.mpg examplebucket/mvna/cf763412/video.mpg examplebucket/mvna/d6e93451/video.mpg examplebucket/mvna/e68f7670/video.mpg ...