AMD - Why, What and How
Upcoming SlideShare
Loading in...5
×
 

Like this? Share it with your network

Share

AMD - Why, What and How

on

  • 5,884 views

AMD was put together by the JavaScript developer community in response to the wild west of coding styles and lack of standards.

AMD was put together by the JavaScript developer community in response to the wild west of coding styles and lack of standards.

Statistics

Views

Total Views
5,884
Views on SlideShare
4,644
Embed Views
1,240

Actions

Likes
2
Downloads
93
Comments
0

8 Embeds 1,240

http://clubajax.org 915
http://blog.amt.in 308
http://www.scoop.it 7
http://posterous.com 6
http://dashboard.bloglines.com 1
http://us-w1.rockmelt.com 1
http://a0.twimg.com 1
http://amtindia.tumblr.com 1
More...

Accessibility

Categories

Upload Details

Uploaded via as Apple Keynote

Usage Rights

© All Rights Reserved

Report content

Flagged as inappropriate Flag as inappropriate
Flag as inappropriate

Select your reason for flagging this presentation as inappropriate.

Cancel
  • Full Name Full Name Comment goes here.
    Are you sure you want to
    Your message goes here
    Processing…
Post Comment
Edit your comment
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n
  • \n

AMD - Why, What and How Presentation Transcript

  • 1. AMD - WHY, WHAT, AND HOWMike Wilcox - January2012Tweets: @clubajaxBlogs: clubajax.org
  • 2. The Problem
  • 3. The ProblemToday’s complex Web Apps have created theneed for:
  • 4. The ProblemToday’s complex Web Apps have created theneed for: Structure Some sort of framework, to aid in rapid development
  • 5. The ProblemToday’s complex Web Apps have created theneed for: Structure Some sort of framework, to aid in rapid development Object orientation To “black box” complex code
  • 6. The ProblemToday’s complex Web Apps have created theneed for: Structure Some sort of framework, to aid in rapid development Object orientation To “black box” complex code Modules and packages RE: The 2,500 best jQuery plugins...
  • 7. The ProblemToday’s complex Web Apps have created theneed for: Structure Some sort of framework, to aid in rapid development Object orientation To “black box” complex code Modules and packages RE: The 2,500 best jQuery plugins... Dependencies (includes, requires, imports, what-ev)
  • 8. The ProblemToday’s complex Web Apps have created theneed for: Structure Some sort of framework, to aid in rapid development Object orientation To “black box” complex code Modules and packages RE: The 2,500 best jQuery plugins... Dependencies (includes, requires, imports, what-ev) Reusable code Scope-isolated, clean API, portable Globals are bad!
  • 9. Single Files
  • 10. Single Files The “old fashioned way” to write JavaScript was to do it all in a single file.
  • 11. Single Files The “old fashioned way” to write JavaScript was to do it all in a single file. // define library ! var!noop = function(){ ! ! }, ! ! isEmpty = function(it){ ! ! ! for(var p in it){ ! ! ! ! return 0; ! ! ! } ! ! ! return 1; ! ! }, ! ! toString = {}.toString, ! ! isFunction = function(it){ ! ! ! return toString.call(it) == "[object Function]"; ! ! }, ! ! isString = function(it){ ! ! ! return toString.call(it) == "[object String]";
  • 12. Single Files ! ! ! ! ! ! ! ! ! computeMapProg = function(map, dest, packName){ ! ! dest.splice(0, dest.length); var p, i, item, reverseName = 0; The “old fashioned way” to write JavaScript was to do ! ! ! ! for(p in map){ ! ! ! ! ! dest.push([p, map[p]]); it all in a single file. ! ! ! ! ! if(map[p]==packName){ ! ! ! ! ! ! reverseName = p; ! ! ! ! ! } ! ! ! ! } ! ! ! ! dest.sort(function(lhs, rhs){ ! ! ! ! ! return rhs[0].length - lhs[0].length; ! ! ! ! }); ! ! ! ! for(i = 0; i < dest.length;){ ! ! ! ! ! item = dest[i++]; ! ! ! ! ! item[2] = new RegExp("^" + item[0].replace(/([.$?*|{} ()[]/+^])/g, function(c){ return "" + c; }) + "(/|$)"); ! ! ! ! ! item[3] = item[0].length + 1; ! ! ! ! } ! ! ! ! return reverseName; ! ! ! }, ! ! ! fixupPackageInfo = function(packageInfo, baseUrl){ ! ! ! ! // calculate the precise (name, baseUrl, main, mappings) for a package ! ! ! ! var name = packageInfo.name; ! ! ! ! if(!name){
  • 13. Single File - pros & cons
  • 14. Single File - pros & cons Pros Fewer resources means faster load times.
  • 15. Single File - pros & cons Pros Fewer resources means faster load times. No “build step” necessary.
  • 16. Single File - pros & cons Pros Fewer resources means faster load times. No “build step” necessary.Cons Difficult to maintain and edit a file thousands of lines long. GOTO Line #
  • 17. Single File - pros & cons Pros Fewer resources means faster load times. No “build step” necessary.Cons Difficult to maintain and edit a file thousands of lines long. GOTO Line # Code reusability is dirt poor. Copy and paste?
  • 18. Single File - pros & cons Pros Fewer resources means faster load times. No “build step” necessary.Cons Difficult to maintain and edit a file thousands of lines long. GOTO Line # Code reusability is dirt poor. Copy and paste? Makes team development near impossible. GITMERGETOOL
  • 19. Multiple Files
  • 20. Multiple FilesMultiple files which follow an object oriented ornamespaced approach are easier to maintain becausethe brain more easily maps files to ideas.
  • 21. Multiple FilesMultiple files which follow an object oriented ornamespaced approach are easier to maintain becausethe brain more easily maps files to ideas. [dom.js] [lang.js] library.dom = { library.lang = { // code // code } } [events.js] [string.js] library.events = library.string = { { // code // code } }
  • 22. Multi File - pros & cons
  • 23. Multi File - pros & cons Pros One-to-one, file-to-class makes organization easier.
  • 24. Multi File - pros & cons Pros One-to-one, file-to-class makes organization easier. The brain more easily maps files to concepts (objects).
  • 25. Multi File - pros & cons Pros One-to-one, file-to-class makes organization easier. The brain more easily maps files to concepts (objects). More team friendly.
  • 26. Multi File - pros & cons Pros One-to-one, file-to-class makes organization easier. The brain more easily maps files to concepts (objects). More team friendly.Cons The files (and server requests) will add up fast and that will slow down the page.
  • 27. Multi File - pros & cons Pros One-to-one, file-to-class makes organization easier. The brain more easily maps files to concepts (objects). More team friendly.Cons The files (and server requests) will add up fast and that will slow down the page. Lots of <script> tags. BLEAH.
  • 28. Multi File - pros & cons Pros One-to-one, file-to-class makes organization easier. The brain more easily maps files to concepts (objects). More team friendly.Cons The files (and server requests) will add up fast and that will slow down the page. Lots of <script> tags. BLEAH. The system to track all these files and their order is YOU.
  • 29. Web App with <script> tags
  • 30. Web App with <script> tags
  • 31. Web App with <script> tags
  • 32. Build solution for <script> tags
  • 33. Build solution for <script> tags Result can be fed into Google Closure Combiner, Dojo Shrinksafe, UglifyJS, etc, etc.
  • 34. Dependency Matters
  • 35. Dependency Matters Scripts load in this order[dom.js] [events.js]library.dom = { // code [lang.js] library.events =} { [string.js] library.lang = { // code } // code } library.string = { // code }
  • 36. Dependency Matters Scripts load in this order A change is made to dom.js Adds events to node on create.[dom.js] [events.js]library.dom = { // code [lang.js] library.events =} { [string.js] library.lang = { // code } // code } library.string = { // code }
  • 37. Dependency Matters Scripts load in this order A change is made to dom.js Adds events to node on create.[dom.js] [events.js]library.dom = { // code [lang.js] library.events =} { [string.js] dom.js is trying to access library.lang = { // code } // code events.js but it’s not loaded } library.string = yet { // code }
  • 38. Dependency Management[dom.js] [events.js]library.dom = { // code [lang.js] library.events =} { [string.js] library.lang = { // code } // code } library.string = { // code }
  • 39. Dependency Management [player.html][dom.js] [events.js]library.dom = { // code [admin.html] [lang.js] library.events =} { [string.js] library.lang = { // code } // code } library.string = { // code } [test.html]Now script order needsto be changed in all your
  • 40. I thought Dojo had a build tool with dependency
  • 41. Dojo’s <1.7 Solution
  • 42. Dojo’s <1.7 Solution“provide” registers this page of code as “a class” (butactually just an object). dojo.provide(“dijit.Dialog”);
  • 43. Dojo’s <1.7 Solution“provide” registers this page of code as “a class” (butactually just an object). dojo.provide(“dijit.Dialog”); dojo.require(“dijit.form.Button”); “require” tells Dojo that the provided code depends upon the required code. Dojo guarantees that the required code is loaded before the provided code is executed.
  • 44. How Dojo <1.7 Worked
  • 45. How Dojo <1.7 Worked Script files were pulled in as text with XHR. -= XHR =-[dom.js]codecodecoderequire(‘event’)library.dom = { // code}
  • 46. How Dojo <1.7 Worked Script files were pulled in as text with XHR. One at a time, each text file is eval’d into JavaScript. synchronously! -= XHR =- -= EVAL =-[dom.js] [dom.js] [dom.js]code code codecode code codecode code coderequire(‘event’) require(‘event’) require(‘event’)library.dom = { library.dom = { library.dom = { // code // code // code} } }
  • 47. Dojo <1.7 Problems
  • 48. Dojo <1.7 Problems XHR load has same-origin restrictions
  • 49. Dojo <1.7 Problems XHR load has same-origin restrictions Special, complex, XD loader was needed
  • 50. Dojo <1.7 Problems XHR load has same-origin restrictions Special, complex, XD loader was needed Eval’d code totally fubar’d syntax-error line numbers
  • 51. Dojo <1.7 Problems XHR load has same-origin restrictions Special, complex, XD loader was needed Eval’d code totally fubar’d syntax-error line numbers Synchronous XHR is very slow
  • 52. Dojo <1.7 Problems XHR load has same-origin restrictions Special, complex, XD loader was needed Eval’d code totally fubar’d syntax-error line numbers Synchronous XHR is very slow Some environments do not allow eval (like Adobe AIR)
  • 53. Dojo <1.7 Problems XHR load has same-origin restrictions Special, complex, XD loader was needed Eval’d code totally fubar’d syntax-error line numbers Synchronous XHR is very slow Some environments do not allow eval (like Adobe AIR) eval executes differently across browsers
  • 54. Dojo <1.7 Problems XHR load has same-origin restrictions Special, complex, XD loader was needed Eval’d code totally fubar’d syntax-error line numbers Synchronous XHR is very slow Some environments do not allow eval (like Adobe AIR) eval executes differently across browsers Developers are taught that eval is evil
  • 55. ALTERNATIVE LOADER TECHNIQUES
  • 56. Async
  • 57. Async var Employee = require("Employee"); function Manager () { } Manager.prototype = new Employee(); [ ERROR ]
  • 58. Async var Employee = require("Employee"); function Manager () { } Manager.prototype = new Employee(); [ ERROR ]The Employee code is loaded async, so it happens inthe background while Manager is invoked, whichmeans Employee is not ready and an error occurs.
  • 59. document.write
  • 60. document.write write(‘<script src=”Store.js” />’); write(‘<script src=”Employee.js” />’);
  • 61. document.write write(‘<script src=”Store.js” />’); write(‘<script src=”Employee.js” />’); No access to the script’s dependencies
  • 62. document.write write(‘<script src=”Store.js” />’); write(‘<script src=”Employee.js” />’); No access to the script’s dependencies Does not work after page load
  • 63. document.write write(‘<script src=”Store.js” />’); write(‘<script src=”Employee.js” />’); No access to the script’s dependencies Does not work after page load Blocks page rendering
  • 64. appendChild(‘script’);
  • 65. appendChild(‘script’); head = document.getElementsByTagName(head)[0]; script = document.createElement(script); script.src = url; head.appendChild(script); No access to the script’s dependencies
  • 66. appendChild(‘script’); head = document.getElementsByTagName(head)[0]; script = document.createElement(script); script.src = url; head.appendChild(script); No access to the script’s dependencies Has same async issues
  • 67. THE SOLUTION
  • 68. Function Wrapping
  • 69. Function Wrapping dependency dependency dependency code_for_loader_to_execute = function(){ return code_to_be_converted_to_module_later }
  • 70. Function Wrapping dependency dependency dependency code_for_loader_to_execute = function(){ return code_to_be_converted_to_module_later } Wrapping code in function allows the loader to control when invocation needs to occur
  • 71. Function Wrapping dependency dependency dependency code_for_loader_to_execute = function(){ return code_to_be_converted_to_module_later } Wrapping code in function allows the loader to control when invocation needs to occur All code can defer until after all dependencies are determined and loaded
  • 72. AMD’s Methods
  • 73. AMD’s Methods“define” registers this page of code as “a class”. define();
  • 74. AMD’s Methods“define” registers this page of code as “a class”. define(); require(); “require” loads in the requested modules and provides them in a callback function.
  • 75. Anatomy of AMD - define()
  • 76. Anatomy of AMD - define() define( [ “./depA”, “./depB” ], function(depA, depB){ var myModule = {}; return myModule; } ); * There are other argument options, but these are the most common.
  • 77. Anatomy of AMD - define()One of twoglobals used inthe spec define( [ “./depA”, “./depB” ], function(depA, depB){ var myModule = {}; return myModule; } ); * There are other argument options, but these are the most common.
  • 78. Anatomy of AMD - define()One of two Dependencies list definedglobals used in as an array in the firstthe spec argument define( [ “./depA”, “./depB” ], function(depA, depB){ var myModule = {}; return myModule; } ); * There are other argument options, but these are the most common.
  • 79. Anatomy of AMD - define()One of two Dependencies list definedglobals used in as an array in the firstthe spec argument The second define( [ argument is the “./depA”, Factory which is “./depB” consumed when ], function(depA, depB){ module is requested var myModule = {}; return myModule; } ); * There are other argument options, but these are the most common.
  • 80. Anatomy of AMD - define()One of two Dependencies list definedglobals used in as an array in the firstthe spec argument The second define( [ argument is the “./depA”, Factory which is “./depB” consumed when ], function(depA, depB){ module is requested var myModule = {}; Dependencies return myModule; passed as factory’s } arguments ); * There are other argument options, but these are the most common.
  • 81. Anatomy of AMD - define()One of two Dependencies list definedglobals used in as an array in the firstthe spec argument The second define( [ argument is the “./depA”, Factory which is “./depB” consumed when ], function(depA, depB){ module is requested var myModule = {}; Dependencies return myModule; passed as factory’s } arguments All of your module ); magic happens here, complete with scope isolation * There are other argument options, but these are the most common.
  • 82. Anatomy of AMD - define()One of two Dependencies list definedglobals used in as an array in the firstthe spec argument The second define( [ argument is the “./depA”, Factory which is “./depB” consumed when ], function(depA, depB){ module is requested var myModule = {}; Dependencies return myModule; passed as factory’s } arguments All of your module); magic happens here, complete with scope isolationLooks like a class, smellslike a class... * There are other argument options, but these are the most common.
  • 83. Anatomy of AMD - require()
  • 84. Anatomy of AMD - require() require( [ “library/depA”, “library/depB” ], function(depA, depB){ depA.doSomething(); depB.someMore(); } ); * There are other argument options, but these are the most common.
  • 85. Anatomy of AMD - require()The other global require( [ “library/depA”, “library/depB” ], function(depA, depB){ depA.doSomething(); depB.someMore(); } ); * There are other argument options, but these are the most common.
  • 86. Anatomy of AMD - require() Modules, or “Imports” listThe other global defined as an array in the first argument require( [ “library/depA”, “library/depB” ], function(depA, depB){ depA.doSomething(); depB.someMore(); } ); * There are other argument options, but these are the most common.
  • 87. Anatomy of AMD - require() Modules, or “Imports” listThe other global defined as an array in the first argument require( Callback fires when [ modules are loaded “library/depA”, “library/depB” and ready ], function(depA, depB){ depA.doSomething(); depB.someMore(); } ); * There are other argument options, but these are the most common.
  • 88. Anatomy of AMD - require() Modules, or “Imports” listThe other global defined as an array in the first argument require( Callback fires when [ modules are loaded “library/depA”, “library/depB” and ready ], function(depA, depB){ depA.doSomething(); Modules passed as depB.someMore(); callback’s } arguments ); * There are other argument options, but these are the most common.
  • 89. Anatomy of AMD - require() Modules, or “Imports” listThe other global defined as an array in the first argument require( Callback fires when [ modules are loaded “library/depA”, “library/depB” and ready ], function(depA, depB){ depA.doSomething(); Modules passed as depB.someMore(); callback’s } arguments ); Modules are ready to access here * There are other argument options, but these are the most common.
  • 90. Anatomy of AMD - require() Modules, or “Imports” listThe other global defined as an array in the first argument require( Callback fires when [ modules are loaded “library/depA”, “library/depB” and ready ], function(depA, depB){ depA.doSomething(); Modules passed as depB.someMore(); callback’s } arguments ); Modules are ready to access hereLooks like “define”! Simple! * There are other argument options, but these are the most common.
  • 91. Why is ASYNC fast anyway?
  • 92. Why is ASYNC fast anyway?In this context, “async” refers to allowing the browserto load the scripts natively. It can load many scripts atonce, concurrently.
  • 93. Why is ASYNC fast anyway?The “sync” loader needed to block all other processeswhile a script was loaded.
  • 94. EXTENDING AMD
  • 95. Plugins
  • 96. PluginsThe bang! symbol represents a plugin thatperforms a special task. require(["dojo", "dojo/domReady!"], function(dojo){ ! doDomStuff(); }); define([ “dijit/Widget”, “dojo/text!myTemplate.html” ], function(Widget, template){ // build a widget });
  • 97. PluginsThe bang! symbol represents a plugin thatperforms a special task. domReady! is a common plugin that prevents the callback from firing until the DOM is in fact... ready. require(["dojo", "dojo/domReady!"], function(dojo){ ! doDomStuff(); }); define([ “dijit/Widget”, “dojo/text!myTemplate.html” ], function(Widget, template){ // build a widget });
  • 98. PluginsThe bang! symbol represents a plugin thatperforms a special task. domReady! is a common plugin that prevents the callback from firing until the DOM is in fact... ready. require(["dojo", "dojo/domReady!"], function(dojo){ ! doDomStuff(); }); define([ “dijit/Widget”, “dojo/text!myTemplate.html” ], function(Widget, template){ // build a widget }); text! knows that it is reading text or HTML and possibly applies transforms to it.
  • 99. Build Tools
  • 100. Build ToolsA “profile” is the description file the Dojo Builder uses.The AMD structure works well as individual files or asone combined file. var profile = { ! releaseDir:"../clubajax-deploy", ! packages:[ ! ! { ! ! ! name:"clubajax", ! ! ! location:"." ! ! },{ ! ! ! name:"plugin", ! ! ! location:"../plugin" ! ! } ! ], ! layers:{ ! ! "clubajax/layer":{ ! ! ! include:[ custom/main, plugin/main ] ! ! } ! } };
  • 101. Packages
  • 102. PackagesA package.json file will help describe your code, itsexternal dependencies, and how it should be used. { "name": "clubajax.js", "description": "Club AJAX Base Library", "licenses": [{ "type": "AFLv2.1", "url": "http://dojo/LICENSE" }], "bugs": "", "keywords": [], "homepage": "http://clubajax.org/", "dependencies": {}, "dojoBuild": "clubajax.profile.js", "main": "./main"
  • 103. PackagesA package.json file will help describe your code, itsexternal dependencies, and how it should be used. { "name": "clubajax.js", "description": "Club AJAX Base Library", "licenses": [{ "type": "AFLv2.1", "url": "http://dojo/LICENSE" }], "bugs": "", "keywords": [], "homepage": "http://clubajax.org/", "dependencies": {}, "dojoBuild": "clubajax.profile.js", "main": "./main"“dojoBuild” points to the profile, and “main” points tothe master file that knows of all the files in thepackage.
  • 104. RESOURCES
  • 105. AMD Authors
  • 106. AMD Authors James Burke Original Dojo Loader author Developed RequireJS and spearheaded AMD
  • 107. AMD Authors
  • 108. AMD Authors Kevin Dangoor Authored blog post: “What Server Side JavaScript Needs” Founded CommonJS Expressed the need for JS modules and packages RequireJS based on CommonJS module spec
  • 109. AMD Authors
  • 110. AMD Authors Rawld Gill Wrote the Dojo 1.7 loader and Node.js build tool key contributor to AMD spec Authored all AMD plugins (text, i18n, domReady, ready) dojo bootstrap (kernel and base load) dojos has.js implementation (enhanced from standard version)
  • 111. AMD Authors
  • 112. AMD Authors Kris Zyp Of course he helped. What is there that Kris Zyp DOESN’T do??
  • 113. AMD LibrariesThe following libraries are either AMD-compliant or AMD loaders jQuery 1.7 Dojo 1.7 MooTools 2.0 EmbedJS curl.js
  • 114. More AMD Info https://github.com/amdjs/amdjs-api/wiki/AMD http://www.commonjs.org/ http://www.commonjs.org/specs/ http://dojotoolkit.org/reference-guide/loader/ index.html#loader-index http://dojotoolkit.org/reference-guide/loader/amd.html#loader- amd http://arstechnica.com/web/news/2009/12/commonjs-effort- sets-javascript-on-path-for-world-domination.ars http://requirejs.org/docs/history.html http://www.commonjs.org/history/ https://groups.google.com/group/amd-implement?pli=1✴ Special credit to Rawld Gill of Alto Visio for his in depth explanations of Dojo Loader and Build Tool✴ And a very special credit to James Burke - since most of the information in this presentation came from the RequireJS pages.
  • 115. Description