ajax to the moon

87
Ajax to the Moon Dave Johnson CTO and Co-founder Nitobi www.nitobi.com

Upload: davejohnson

Post on 01-Nov-2014

18 views

Category:

Technology


1 download

DESCRIPTION

CommunityOne presentation about offline Ajax, Ajax push, and Ajax performance issues.

TRANSCRIPT

Page 1: Ajax to the Moon

Ajax to the Moon

Dave Johnson

CTO and Co-founderNitobiwww.nitobi.com

Page 2: Ajax to the Moon

2007 CommunityOne 2

Agenda

1. Who I Am

2. Offline Ajax

3. Pushing Ajax

4. Ajax Performance

5. Summary

Page 3: Ajax to the Moon

2007 CommunityOne 3

Who I Am

• Nitobi Enterprise Ajax Podcast• Enterprise Ajax book (Prentice Hall)• blogs.nitobi.com/dave

Page 4: Ajax to the Moon

2007 CommunityOne 4

What Do I Do?

• Nitobi co-founder• Located in Vancouver, Canada• Ajax user-interface components

for the enterprise

Page 5: Ajax to the Moon

2007 CommunityOne 5

Page 6: Ajax to the Moon

2007 CommunityOne 6

Clients

Page 7: Ajax to the Moon

2007 CommunityOne 7

Agenda

1. Who I Am

2. Offline Ajax

3. Pushing Ajax

4. Ajax Performance

5. Summary

Page 8: Ajax to the Moon

2007 CommunityOne 8

Offline Ajax

http://www.flickr.com/photos/natearcher/378519540/

Page 9: Ajax to the Moon

2007 CommunityOne 9

Know your users

Page 10: Ajax to the Moon

2007 CommunityOne 10

Why Offline

• Hard at work• Get on a plane• Keep on working

Page 11: Ajax to the Moon

2007 CommunityOne 11

http://www.flickr.com/photos/plakboek/339017053/

Page 12: Ajax to the Moon

2007 CommunityOne 12

Why Offline

• Hard at work• Get on a plane• Keep on working• Get Internet connection and sync data

• More common than you may think!

Page 13: Ajax to the Moon

2007 CommunityOne 13

Page 14: Ajax to the Moon

2007 CommunityOne 14

Page 15: Ajax to the Moon

2007 CommunityOne 15

But Seriously

• Internet connections do not grow on trees• Try going to Sun HQ and getting on their network!

Page 16: Ajax to the Moon

2007 CommunityOne 16

How Does it Work?

• Work offline• Store data locally when browser is closed• Send data back to server when connected

Page 17: Ajax to the Moon

2007 CommunityOne 17

Page 18: Ajax to the Moon

2007 CommunityOne 18

Storage

• Cookies• Firefox / Internet Explorer only• Flash• Install software

Page 19: Ajax to the Moon

2007 CommunityOne 19

Cookies

• 4Kb of storage per domain• Easily deleted – probably suspected as Spyware

Page 20: Ajax to the Moon

2007 CommunityOne 20

Firefox 2.0 Offline Storage

• Cookies on steroids• Data not available across sessions• 5Mb of storage by default• A bit buggy at the moment but Firefox 3 should

have global storage across sessions

Page 21: Ajax to the Moon

2007 CommunityOne 21

<html> <head> <script type=”text/javascript”>function saveSession(myparam,myvalue) { // will save the attribute myparam with value myvalue sessionStorage[myparam] = myvalue;}function loadSession(myparam) { // will retrieve myparam from sessionStorage var myresult = sessionStorage[myparam]; return myresult;} </script> </head> <body> <form id="myform" name="myform"> <input type="text" id="myvalue" name="myvalue"> <input type="button" value="Save" onclick="saveSession('myattribute',myform.myvalue.value)"> <input type="button" value="Load" onclick="alert(loadSession('myattribute'))"> </form> </body></html>

Page 22: Ajax to the Moon

2007 CommunityOne 22

Internet Explorer userData Behavior

• Access data across sessions• 128Kb limit for Internet (512Kb for Intranet)• Relies on Internet Explorer Behaviors• What about HTML Applications?

Page 23: Ajax to the Moon

2007 CommunityOne 23

<html> <head> <script type=”text/javascript”>function save(myparam,myvalue) { $(“storageInput”).setAttribute(myparam, myvalue).save("mydata");}function load(myparam) { return $(“storageInput”).load("mydata").getAttribute(myparam);} </script> <style>.storage { behavior:url(#default#userData); display:none;} </style> </head> <body> <form id="myform" name="myform"> <input type="text" id="myvalue" name="myvalue"> <input type="button" value="Save"

onclick="save('myattr',myform.myvalue.value)"> <input type="button" value="Load" onclick="alert(load('myattribute'))"> <div id=”storageInput” class=”storage”></div> </form> </body></html>

Page 24: Ajax to the Moon

2007 CommunityOne 24

Flash SharedObject Storage

• Access data across sessions• User definable storage limit (default of 100Kb)• Back to Flash 6 (98% adoption)

Page 25: Ajax to the Moon

2007 CommunityOne 25

Flash Movie

import flash.external.ExternalInterface;

function saveAttribute(datastore, paramname, paramvalue) { mySharedObject = SharedObject.getLocal(datastore); mySharedObject.data[paramname] = paramvalue; mySharedObject.flush();}

function loadAttribute(datastore,paramname) { return SharedObject.getLocal(datastore).data[paramname]; }

ExternalInterface.addCallback("saveAttribute", this, saveAttribute); ExternalInterface.addCallback("loadAttribute", this, loadAttribute);

Page 26: Ajax to the Moon

2007 CommunityOne 26

<html> <head> <script>function thisMovie(movieName) { if (navigator.appName.indexOf("Microsoft") != -1) return window[movieName]; else return document[movieName];}function saveData(store, param, pvalue) { thisMovie(‘myStorage’).saveAttribute(store,param,pvalue);}function loadData(store, param) { return(thisMovie(‘myStorage’).loadAttribute(store,param));} </script> </head> <body> <object classid="clsid:d27cdb6e-ae6d-11cf-96b8-444553540000“ codebase="…" width="1" height="1" id="myStorage" align="middle"> <param name="movie" value="localstore.swf" /> <param nam="allowScriptAccess" value="always"> <embed src="localstore.swf" allowScriptAccess="always" width="1" height="1"

name="myStorage“ type="application/x-shockwave-flash"

pluginspage="http://www.macromedia.com/go/getflashplayer" /> </object> </body></html>

Page 27: Ajax to the Moon

2007 CommunityOne 27

<html> <head> <script>function thisMovie(movieName) { if (navigator.appName.indexOf("Microsoft") != -1) return window[movieName]; else return document[movieName];}function saveData(store, param, pvalue) { thisMovie(‘myStorage’).saveAttribute(store,param,pvalue);}function loadData(store, param) { return(thisMovie(‘myStorage’).loadAttribute(store,param));} </script> </head> <body> <object classid="clsid:d27cdb6e-ae6d-11cf-96b8-444553540000“ codebase="…" width="1" height="1" id="myStorage" align="middle"> <param name="movie" value="localstore.swf" /> <param nam="allowScriptAccess" value="always"> <embed src="localstore.swf" allowScriptAccess="always" width="1" height="1"

name="myStorage“ type="application/x-shockwave-flash"

pluginspage="http://www.macromedia.com/go/getflashplayer" /> </object> </body></html>

Page 28: Ajax to the Moon

2007 CommunityOne 28

Apollo

• Adobe’s new runtime – currently Alpha• Offline capable, runs from your computer• A lot more than just offline!

• Flex + WebKit (i.e. Safari) in one

Page 29: Ajax to the Moon

2007 CommunityOne 29

Web Proxy

• Proxy auto-config – browser proxy settings• JavaScript file with FindProxyForURL• Forward requests to a local proxy for interested

domains• Used by the Dojo Toolkit

Page 30: Ajax to the Moon

2007 CommunityOne 30

Salesforce.com

Local Proxy

Page 31: Ajax to the Moon

2007 CommunityOne 31

Whole Hog

• Web server• Database• Run locally• Zimbra uses this approach

Page 32: Ajax to the Moon

2007 CommunityOne 32

Issues

• Performance• Concurrency

• Your own data or shared?

• End user requirements• Are they a captive user?

• Penetration

Page 33: Ajax to the Moon

2007 CommunityOne 33

End user reqs / Penetration Performance Concurrency

Cookies

Browser Specific

Flash

Proxy

Whole Hog

Page 34: Ajax to the Moon

2007 CommunityOne 34

End user reqs / Penetration Performance Concurrency

Cookies

Browser Specific

Flash

Proxy

Whole Hog

Page 35: Ajax to the Moon

2007 CommunityOne 35

End user reqs / Penetration Performance Concurrency

Cookies

Browser Specific

Flash

Proxy

Whole Hog

Page 36: Ajax to the Moon

2007 CommunityOne 36

End user reqs / Penetration Performance Concurrency

Cookies

Browser Specific

Flash

Proxy

Whole Hog

Page 37: Ajax to the Moon

2007 CommunityOne 37

End user reqs / Penetration Performance Concurrency

Cookies

Browser Specific

Flash

Proxy

Whole Hog

Page 38: Ajax to the Moon

2007 CommunityOne 38

Agenda

1. Who I Am

2. Offline Ajax

3. Pushing Ajax

4. Ajax Performance

5. Summary

Page 39: Ajax to the Moon

2007 CommunityOne 39

Pushing Ajax

http://www.flickr.com/photos/vidiot/69075298/

Page 40: Ajax to the Moon

2007 CommunityOne 40

Watch out for your thumb

Page 41: Ajax to the Moon

2007 CommunityOne 41

Why Push?

• Keep client up to date• Collaboration

• Documents• Communication

• Time sensitive data

Page 42: Ajax to the Moon

2007 CommunityOne 42

How Does it Work?

Big scary InternetInnocent MySpace user MySpace Evil EmpireTM

Page 43: Ajax to the Moon

2007 CommunityOne 43

Polling

• Means to the same end• Easy to build

• Request update from server every N seconds• Support thousands of concurrent users?

users / pollTime = requests per second

Page 44: Ajax to the Moon

2007 CommunityOne 44http://www.flickr.com/photos/roadhunter/68017710/

Page 45: Ajax to the Moon

2007 CommunityOne 45

How Does it Work?

Big scary InternetInnocent MySpace user MySpace Evil EmpireTM

thumb twiddling …

Page 46: Ajax to the Moon

2007 CommunityOne 46

Push

• Keep connection to server open• Server writes to stream when ready• Support thousands of concurrent users?

numConnections ≡ numServerThreads

Page 47: Ajax to the Moon

2007 CommunityOne 47

http://www.flickr.com/photos/rev_bri/112249215/

Page 48: Ajax to the Moon

2007 CommunityOne 48

Asynchronous Servlets

• Sun – Grizzly HTTP Connector• BEA – AbstractAsyncServlet• Tomcat 6.x – CometServlet• Jetty – Continuations

• No standards here

Page 49: Ajax to the Moon

2007 CommunityOne 49

Cometd / Bayeux

• Cometd reference implementation• Bayeux pub/sub on top of Comet

• Think JMS for JavaScript

Page 50: Ajax to the Moon

2007 CommunityOne 50

DEMO

• http://localhost:8080/examples/magnets/

Page 51: Ajax to the Moon

2007 CommunityOne 51

Piggyback

• The middle of the road• Send data to client with any other responses

Page 52: Ajax to the Moon

2007 CommunityOne 52

Other Approaches to Push

• LiveCycle Data Services• LightStreamer

Page 53: Ajax to the Moon

2007 CommunityOne 53

Issues

• Server load• Internet Explorer

Page 54: Ajax to the Moon

2007 CommunityOne 54

Agenda

1. Who I Am

2. Offline Ajax

3. Pushing Ajax

4. Ajax Performance

5. Summary

Page 55: Ajax to the Moon

2007 CommunityOne 55

Ajax Performance

http://www.flickr.com/photos/edfladung/451378444/

Ajax Performance

Page 56: Ajax to the Moon

2007 CommunityOne 56

Ask questions first, optimize second

Page 57: Ajax to the Moon

2007 CommunityOne 57

What is the Bottleneck?

• Situation dependent• How much data?• What type of data?• How many server hits?• What are the common workflows?• What browsers are you targeting?• What is the existing infrastructure?

Page 58: Ajax to the Moon

2007 CommunityOne 58

Lifecycle

Page 59: Ajax to the Moon

2007 CommunityOne 59

Data Formats

• XML• <xml>You know this</xml>

• JSON• {“json”:[“maybe”,”you”,don’t”],”know”:”this”}

• HTML• <html>Looks familiar</html>

• Text• Images

Page 60: Ajax to the Moon

2007 CommunityOne 60

Server

• HTML• Whatever you use today

• XML• Standard support for object serialization• Similar to HTML

• JSON• Easy to add on

Page 61: Ajax to the Moon

2007 CommunityOne 61

Bandwidth

• HTML• <div style=“color: red;”>Napoleon</div>

• XML• <customer><name>Napoleon</name></customer>• <c n=“Napoleon”/>

• JSON• {“customer”:[{“Name”:”Napoleon”}]}• {“c”:[{“n”:”Napoleon”}]}

• Polling, code size etc

Page 62: Ajax to the Moon

2007 CommunityOne 62

JavaScript

• HTML• Nothing to do

• XML• Transform with XSLT (browser dependent)• Iterate over XML DOM nodes and string build• Iterate over XML DOM nodes and create HTML DOM nodes

• JSON• eval() the block of JSON to a JavaScript object• Transform with JSON Templates• Iterate through JavaScript arrays and string build• Iterate through JavaScript arrays and create HTML DOM nodes

Page 63: Ajax to the Moon

2007 CommunityOne 63

Internet Explorer

Page 64: Ajax to the Moon

2007 CommunityOne 64

Firefox

Page 65: Ajax to the Moon

2007 CommunityOne 65

http://www.jamesward.org/census/

Firefox

Internet Explorer

Page 66: Ajax to the Moon

2007 CommunityOne 66

XSLT Cross Browser Performance

0

5

10

15

20

25

30

35

40

45

0 100 200 300 400 500

Table Cells

Tim

e (m

s)

Firefox 1.5

IE 6

Page 67: Ajax to the Moon

2007 CommunityOne 67

Don’t Lose your Keys

<xsl:key name=“sales-by-customer” match=“customer” use=“@name” />

<xsl:value-of select="key(‘sales-by-customer', $CustomerName)">

Page 68: Ajax to the Moon

2007 CommunityOne 68

XSLT Performance

0

5

10

15

20

25

30

35

40

45

0 100 200 300 400 500

Table Cells

Tim

e (m

s)

IE 6 (with key)

IE 6 (w/o key)

Page 69: Ajax to the Moon

2007 CommunityOne 69

JSON with Padding (JSONP)

• Most apps use XHR• Using XHR for JSON necessitates eval()• eval() is slow

• Instead dynamically insert a <script> tag and have the returned JavaScript call a function …

• http://localhost/javaone/

Page 70: Ajax to the Moon

2007 CommunityOne 70

The Fast, Server Dependent Wayfunction getPostsSi() { var elem = document.createElement("script"); elem.src = "http://del.icio.us/feeds/json/davyjones?

callback=buildHtml"; document.body.appendChild(elem);}

function buildHtml(obj) { var s = []; for (var i=0; i<obj.length; i++) { s.push("<div><a href='"+obj[i].u+"'>" + obj[i].d +

"</a></div>"); } $("container").innerHTML = s.join("");}

Page 71: Ajax to the Moon

2007 CommunityOne 71

The Slow, Server Agnostic Way

function getPostsXhr() { var xhr = new nitobi.ajax.HttpRequest(); xhr.handler =

"http://localhost/feeds/json/davyjones"; xhr.onComplete.subscribe(xhrDataReady); xhr.send();}

function xhrDataReady(evtArgs) { var obj = eval("("+evtArgs+")"); buildHtml(obj);}

Page 72: Ajax to the Moon

2007 CommunityOne 72

HTML DOM

• HTML• $(“myNode”).innerHTML = “<div>Napoleon</div>”;

• XML• innerHTML• DOM manipulations

• createElement(“div”), appendChild(node), etc

• JSON• innerHTML• DOM manipulations

• Interactivity

Page 73: Ajax to the Moon

2007 CommunityOne 73

General DOM Function

Page 74: Ajax to the Moon

2007 CommunityOne 74

Most Wanted

• innerHTML – consider HTML tags, floats, events• offsetTop / Left• getBoundingClientRect / getBoxObjectFor• Stylesheets

Page 75: Ajax to the Moon

2007 CommunityOne 75

Watch Out for Memory Leaks

• Circular loops between the DOM and JavaScript

• Use Drip to find them

<script type=“text/javascript”>var domNode = $(“myDomNode”);domNode.foo = domNode;</script>

expando

Page 76: Ajax to the Moon

2007 CommunityOne 76

JavaScript Compression

• Removing comments• Removing whitespace• Removing new-line characters• Replacing variables with shorter names

Page 77: Ajax to the Moon

2007 CommunityOne 77

Simple Example

var _a = function(a){var b=0;var c=a.length;for(var d=0;d<c;d++){b+=a[d];}return b/c;}var calcAverage=_a;

/** * @private */var _calcAverage = function(aNumber) { var nTotal = 0; var iLength = aNumber.length; for (var iIndex = 0; i<iLength; i++) { nTotal += aNumber[iIndex]; } return nTotal/iLength;}/** * Calculates the average of an array of numbers. * @param {Array} Array of numbers to average. */var calcAverage = _calcAverage;

Page 78: Ajax to the Moon

2007 CommunityOne 78

Rhino Minification / Obfuscation

<target name="obfuscateJS" description="compress and obfuscate code">

<java classname="org.mozilla.javascript.tools.shell.Main“dir="${basedir}\build\rhino\bin\"fork="true"output="${basedir}\output\src_obfuscated.js">

<arg line="-c ${basedir}\input\src.js" /> <classpath> <pathelement path="${basedir}\build\rhino\bin\js.jar"/> </classpath> </java></target>

Page 79: Ajax to the Moon

2007 CommunityOne 79

Compression

• Request• Accept-Encoding: gzip,deflate

• Response• Content-Encoding: gzip || deflate

• IIS and Apache dynamically GZip / Deflate content and cache it

• All modern browsers support compressed content• Internet Explorer 6 SP1 had some problems

• IE, Firefox, Opera accept compressed content _without_ Content-Encoding header

Page 80: Ajax to the Moon

2007 CommunityOne 80

Apache Compression

# Compress everything unless excluded below.

SetOutputFilter DEFLATE

SetInputFilter DEFLATE

SetEnvIfNoCase Request_URI \.(?:gif|jpe?g|png)$ no-gzip dont-vary

SetEnvIfNoCase Request_URI \.(?:exe|t?gz|zip|bz2|rar)$ no-gzip dont-vary

SetEnvIfNoCase Request_URI \.(?:pdf|avi|mov|mp3|rm)$ no-gzip dont-vary

# Explicity compress certain file types

AddOutputFilterByType DEFLATE text/html text/plain text/xml

Page 81: Ajax to the Moon

2007 CommunityOne 81

Size (Kb)

Original 9.3

Minify 3.9

GZip / Deflate 2.8

Minify + GZip / Deflate 1.3

Size Reduction 86%

How Small is It?Expected Results for JavaScript Compression

Page 82: Ajax to the Moon

2007 CommunityOne 82

Content Merging

• Reduce download overhead by merging resources• JavaScript• Cascading Stylesheets• Images

• Careful with caching though!

Page 83: Ajax to the Moon

2007 CommunityOne 83

Image Merging

Page 84: Ajax to the Moon

2007 CommunityOne 84

Image Merging

<html> <head> <style type="text/css" media="screen"> .colour {clip: rect(0px 135px 125px 0px);} .grayscale { left:-135px; clip: rect(0px 270px 125px 135px); } .grayscale, .colour { position:absolute; width: 270px;height: 125px; background: url(images/nitobi.jpg); } .container { height:125px;width:135px; position:relative; } </style> </head> <body> <div class="container"><div class="colour"></div></div> <div class="container"><div class="grayscale"></div></div> </body></html>

clip: rect(0px 135px 125px 0px);

clip: rect(0px 270px 125px 135px);

background: url(images/nitobi.jpg);

Page 85: Ajax to the Moon

2007 CommunityOne 85

Agenda

1. Who I Am

2. Offline Ajax

3. Pushing Ajax

4. Ajax Performance

5. Summary

Page 86: Ajax to the Moon

2007 CommunityOne 86

Summary

• “Work Offline” – know your users• Browser specific, Flash or Install• Usability

• Push – watch out for your thumb• Real-time collaboration• Usability

• Performance – ask questions first, optimize later• Be careful but not too careful• Usability

Page 87: Ajax to the Moon

87

Q&ADave Johnson

www.nitobi.com

[email protected]

http://blogs.nitobi.com/dave