<?xml version='1.0' encoding='UTF-8'?><?xml-stylesheet href="http://www.blogger.com/styles/atom.css" type="text/css"?><feed xmlns='http://www.w3.org/2005/Atom' xmlns:openSearch='http://a9.com/-/spec/opensearchrss/1.0/' xmlns:georss='http://www.georss.org/georss' xmlns:gd='http://schemas.google.com/g/2005' xmlns:thr='http://purl.org/syndication/thread/1.0'><id>tag:blogger.com,1999:blog-34454975</id><updated>2012-01-30T08:30:13.664+01:00</updated><category term='VBScript'/><category term='cipher'/><category term='Visual Studio'/><category term='protocol'/><category term='solution'/><category term='super'/><category term='literal'/><category term='bug'/><category term='140'/><category term='crystal'/><category term='ArrayObject'/><category term='CommonJS'/><category term='String'/><category term='on'/><category term='conversion'/><category term='new'/><category term='revisited'/><category term='proposal'/><category term='hghlight'/><category term='ElseIf'/><category term='require'/><category term='getElementsByClassName'/><category term='Apple'/><category term='upgrade'/><category term='JavaScript.XML'/><category term='Code'/><category term='make'/><category term='detection'/><category term='with'/><category term='N510'/><category term='not'/><category term='thoughts'/><category term='FatalError'/><category term='SPL'/><category term='Yahtzee'/><category term='defects'/><category term='mini'/><category term='Laptop'/><category term='write'/><category term='evil'/><category term='Apache'/><category term='xhtml'/><category term='setImmediate'/><category term='closures'/><category term='minifier'/><category term='friendly'/><category term='opera'/><category term='sort'/><category term='scripting'/><category term='recycle'/><category term='gif'/><category term='distributed'/><category term='type'/><category term='Shaders'/><category term='XSL'/><category term='Fart'/><category term='Hunspell'/><category term='CSS'/><category term='talk'/><category term='Unit Test'/><category term='in'/><category term='delirium'/><category term='Christmas'/><category term='leak'/><category term='hybrid'/><category term='effect'/><category term='exposed'/><category term='trim'/><category term='yal.js'/><category term='experiment'/><category term='OSX'/><category term='UK'/><category term='writable'/><category term='Elsewhere'/><category term='Dash'/><category term='anonymous'/><category term='bytes'/><category term='JavaScirpt'/><category term='Array'/><category term='LAB.js'/><category term='JSON.hpack'/><category term='obtrusive'/><category term='JSONH'/><category term='2.0'/><category term='power'/><category term='lightweight'/><category term='design'/><category term='Internet Explorer'/><category term='ubuntu'/><category term='CDN'/><category term='notification'/><category term='convertion'/><category term='Sizzle'/><category term='prevent'/><category term='compiler'/><category term='BJSpell'/><category term='this'/><category term='Aptana'/><category term='Internet Epxlorer'/><category term='Microsoft'/><category term='best'/><category term='ES6'/><category term='sessionStorage'/><category term='debugger'/><category term='W3C'/><category term='serialization'/><category term='jQuery UI'/><category term='SWF'/><category term='FX'/><category term='Harmony'/><category term='PAMPA-J'/><category term='define'/><category term='ctypes'/><category term='node'/><category term='response'/><category term='indexOf'/><category term='frameworks'/><category term='Chrome'/><category term='plugin'/><category term='Framework'/><category term='defineHybridProperty'/><category term='compressed'/><category term='new year'/><category term='Batch'/><category term='transitions'/><category term='transformer'/><category term='_super'/><category term='toISOString'/><category term='automator'/><category term='focus'/><category term='Object'/><category term='common'/><category term='cross'/><category term='tricks'/><category term='falsy'/><category term='JXON'/><category term='arrow'/><category term='IE6'/><category term='wru'/><category term='silverlight'/><category term='check'/><category term='constant'/><category term='fromCharCode'/><category term='area'/><category term='ASCII'/><category term='engine'/><category term='performances'/><category term='files'/><category term='size'/><category term='button'/><category term='ball'/><category term='readyState'/><category term='create'/><category term='Roundtable'/><category term='properties'/><category term='private'/><category term='JSLint'/><category term='Options'/><category term='PHP'/><category term='meta'/><category term='Mousetrap'/><category term='CoffeeShit'/><category term='interaction'/><category term='unload'/><category term='Ext JS'/><category term='CSS3'/><category term='Ruby'/><category term='getPrototypeOf'/><category term='log'/><category term='callee'/><category term='devpro.it'/><category term='outerHTML'/><category term='Frame'/><category term='Samsung'/><category term='jSmile'/><category term='intenret'/><category term='Sandbox'/><category term='expando'/><category term='assignment'/><category term='decimal'/><category term='Informations'/><category term='Pascal'/><category term='WorkerLocation'/><category term='btoa'/><category term='Unite'/><category term='mobile'/><category term='natural'/><category term='documentation'/><category term='html5'/><category term='characters'/><category term='Image'/><category term='C'/><category term='good'/><category term='imrovements'/><category term='relation'/><category term='method'/><category term='WebKit'/><category term='grant'/><category term='apply'/><category term='getElementsByTagName'/><category term='library'/><category term='convention'/><category term='Sprotector'/><category term='ES3'/><category term='IE10'/><category term='side'/><category term='base64'/><category term='Flash'/><category term='devices'/><category term='Trends'/><category term='save as'/><category term='standard'/><category term='Rhino'/><category term='function'/><category term='List'/><category term='isFunction'/><category term='injection'/><category term='EventEmitter'/><category term='swine flu'/><category term='limit'/><category term='banner'/><category term='safari'/><category term='broken'/><category term='Builder'/><category term='defineProperty'/><category term='jQuery'/><category term='defineProperties'/><category term='merits'/><category term='bad'/><category term='lightning'/><category term='attribute'/><category term='overload'/><category term='isCallable'/><category term='driven'/><category term='Revolution'/><category term='VS9'/><category term='scope'/><category term='MDC'/><category term='onload'/><category term='toolbar'/><category term='parody'/><category term='XML'/><category term='unpacked'/><category term='improvement'/><category term='dataset'/><category term='language'/><category term='Ten Grand'/><category term='advanced'/><category term='slickspeed'/><category term='filter'/><category term='correct'/><category term='Else'/><category term='javascript 2'/><category term='Listener'/><category term='style'/><category term='var_export'/><category term='Map'/><category term='emulation'/><category term='for in'/><category term='Observer'/><category term='region'/><category term='polyfills'/><category term='tuscany'/><category term='software'/><category term='errors'/><category term='ie7'/><category term='Multiton'/><category term='begetObject'/><category term='ES5'/><category term='bit.ly'/><category term='Levenshtein'/><category term='Io'/><category term='postable'/><category term='compressor'/><category term='prototype'/><category term='recursion'/><category term='implicit cast'/><category term='node.js'/><category term='Twitter'/><category term='unobtrusive'/><category term='GWT'/><category term='technologies'/><category term='inline'/><category term='YAGNI'/><category term='connection'/><category term='restaurant'/><category term='2011'/><category term='outline'/><category term='Date'/><category term='getAttribute'/><category term='fast'/><category term='UPDATE'/><category term='benchmark'/><category term='gzip'/><category term='Formaldehyde'/><category term='ambiguity'/><category term='User'/><category term='TechHub'/><category term='Jam'/><category term='console'/><category term='js-ctypes'/><category term='download'/><category term='TaskSpeed'/><category term='8601'/><category term='CPU'/><category term='browser'/><category term='EventListener'/><category term='monitor'/><category term='class'/><category term='Macro'/><category term='script'/><category term='Object.create'/><category term='background'/><category term='debug_backtrace'/><category term='file'/><category term='JavaScriptCore'/><category term='default'/><category term='Application'/><category term='tesla'/><category term='fatal'/><category term='debug'/><category term='use strict'/><category term='crash'/><category term='batman'/><category term='unserialize'/><category term='gzipped'/><category term='process'/><category term='patterns'/><category term='HTMLCollection'/><category term='stream'/><category term='essential'/><category term='random'/><category term='chain'/><category term='broadband'/><category term='reset'/><category term='PC Pro'/><category term='translator'/><category term='2010'/><category term='instance'/><category term='YUI'/><category term='API'/><category term='removeAttribute'/><category term='constructor'/><category term='enumerable'/><category term='C#'/><category term='source'/><category term='Algorithm'/><category term='tests'/><category term='blogger'/><category term='TreePanel'/><category term='Mootools'/><category term='RegExp'/><category term='fixed'/><category term='call'/><category term='Agent'/><category term='shared'/><category term='basis'/><category term='upload'/><category term='runtime'/><category term='Singleton'/><category term='structure'/><category term='features'/><category term='vice-versa'/><category term='yuno'/><category term='pattern'/><category term='VBClass'/><category term='maps'/><category term='Dart'/><category term='StringBuilder'/><category term='way'/><category term='valueOf'/><category term='scree'/><category term='avoid'/><category term='resize'/><category term='JSObject'/><category term='live'/><category term='arguments'/><category term='development'/><category term='privileged'/><category term='watch'/><category term='Ajaxian'/><category term='floor'/><category term='Berlin'/><category term='self'/><category term='Math'/><category term='events'/><category term='parsing'/><category term='Windows'/><category term='resolution'/><category term='partial'/><category term='buzz'/><category term='conflicts'/><category term='inheritance'/><category term='module'/><category term='Relator'/><category term='JsonTV'/><category term='O3D'/><category term='bookmarklet'/><category term='stand alone'/><category term='spam'/><category term='Expressions'/><category term='jsc'/><category term='prototypal'/><category term='deflate'/><category term='WebReflection'/><category term='italia.it'/><category term='draft 76'/><category term='transform'/><category term='loader'/><category term='ExtJS'/><category term='trimRight'/><category term='LiveMonitor'/><category term='font-face'/><category term='bridge'/><category term='example'/><category term='UX'/><category term='DELAYED'/><category term='setAttribute'/><category term='Subclass'/><category term='memory'/><category term='lambda'/><category term='NWMatcher'/><category term='native'/><category term='record'/><category term='server side'/><category term='beta'/><category term='JavaScript Hijacking'/><category term='read'/><category term='execution'/><category term='dojo'/><category term='iPhone'/><category term='text'/><category term='build'/><category term='280'/><category term='holidays'/><category term='practices'/><category term='optimization'/><category term='OOP'/><category term='responsive'/><category term='circle'/><category term='NHS'/><category term='Widget'/><category term='navigator'/><category term='grab'/><category term='epic'/><category term='binary safe'/><category term='project'/><category term='content'/><category term='Event'/><category term='Python'/><category term='es4'/><category term='operator'/><category term='slice'/><category term='challenge'/><category term='no flash'/><category term='support'/><category term='client'/><category term='bin'/><category term='magic'/><category term='ISO'/><category term='JSConf'/><category term='XMLHttpRequest'/><category term='ActionScript'/><category term='eval'/><category term='input'/><category term='tag'/><category term='Portable'/><category term='London'/><category term='PyramiDOM'/><category term='Pure DOM'/><category term='instanceof'/><category term='png'/><category term='Libraries'/><category term='Object.createStatic'/><category term='PAMPA'/><category term='Spectrum'/><category term='Tokens'/><category term='Composite'/><category term='overloading'/><category term='no swf'/><category term='AMD'/><category term='access'/><category term='canvas'/><category term='textarea'/><category term='statement'/><category term='configurable'/><category term='classical'/><category term='Storage'/><category term='blocked'/><category term='Components'/><category term='Comet'/><category term='JSON'/><category term='comments'/><category term='Ad 2.0'/><category term='Factory'/><category term='URLs'/><category term='promotion'/><category term='Satay'/><category term='recovery'/><category term='embedded'/><category term='Konami'/><category term='speed'/><category term='sourceIndex'/><category term='MyMin'/><category term='$super'/><category term='homogeneous'/><category term='recruiters'/><category term='hpack'/><category term='tweetcode'/><category term='deployment'/><category term='5.3.5'/><category term='ellipse'/><category term='steal'/><category term='Stack'/><category term='post'/><category term='packed'/><category term='Google'/><category term='ie'/><category term='Set'/><category term='replace'/><category term='coercion'/><category term='Internet Explorer 8'/><category term='setInterval'/><category term='JavaScript.document'/><category term='host objects'/><category term='JsonReader'/><category term='closure'/><category term='WebGL'/><category term='extras'/><category term='server'/><category term='If'/><category term='questions'/><category term='AMF'/><category term='Serializable'/><category term='haxe'/><category term='problem'/><category term='Rebecca Murphey'/><category term='Adapter'/><category term='JS.next'/><category term='IE9'/><category term='fireEvent'/><category term='Strict'/><category term='3site.it'/><category term='INSERT'/><category term='parent'/><category term='getter'/><category term='isNative'/><category term='packed.it'/><category term='syntax'/><category term='sub'/><category term='JavaScript.PHP'/><category term='Web'/><category term='firefox'/><category term='test'/><category term='values'/><category term='KISS'/><category term='DOM'/><category term='window'/><category term='tips'/><category term='link'/><category term='advertisement'/><category term='JScript'/><category term='bind'/><category term='multiple'/><category term='future'/><category term='buttons'/><category term='Lion'/><category term='MySQL'/><category term='XSLT'/><category term='WebSocket'/><category term='Nokia'/><category term='security'/><category term='mistakes'/><category term='look'/><category term='Douglas Crockford'/><category term='extend'/><category term='Xpath'/><category term='__noSuchMethod__'/><category term='fuckn.es'/><category term='Collection'/><category term='nested'/><category term='editor'/><category term='YUICompressor'/><category term='protected'/><category term='custom'/><category term='JSONP'/><category term='CoffeeScript'/><category term='View'/><category term='bar'/><category term='Mouse'/><category term='escape'/><category term='Regular'/><category term='Tree'/><category term='base'/><category term='IE8'/><category term='Jaxer'/><category term='html'/><category term='EU'/><category term='scroll'/><category term='let'/><category term='quality'/><category term='selector'/><category term='fun'/><category term='trimLeft'/><category term='methods'/><category term='Phico'/><category term='encode'/><category term='JavaScript'/><category term='serialize'/><category term='request'/><category term='zlib'/><category term='uri'/><category term='ft2010'/><category term='out of order'/><category term='myth'/><category term='GeoLocation'/><category term='Template'/><category term='proxy'/><category term='asynchronous'/><category term='Sniff'/><category term='mock'/><category term='ECMAScript'/><category term='mjst'/><category term='load'/><category term='environment'/><category term='all'/><category term='unshared'/><category term='export'/><category term='Front'/><category term='cheat'/><category term='easy'/><category term='Ajax'/><category term='form'/><category term='compression'/><category term='LLVM'/><category term='bing'/><category term='toy'/><category term='is_a'/><category term='setter'/><category term='cross-browser'/><category term='__sleep'/><category term='domain'/><category term='impression'/><category term='spell'/><category term='Android'/><category term='Caja'/><category term='const'/><category term='subclassed'/><category term='setTimeout'/><category term='wrong'/><category term='minification'/><category term='element'/><category term='guide'/><category term='Cookie'/><category term='override'/><category term='convert'/><category term='RC4'/><category term='document'/><category term='programming'/><category term='static'/><category term='usable'/><category term='objects'/><category term='safe'/><category term='name'/><category term='single'/><category term='WeakMap'/><category term='__wakeup'/><category term='expression'/><category term='JsonML'/><category term='first'/><category term='book'/><category term='blog'/><category term='Web 2.0'/><category term='Phomet'/><category term='Liquid'/><category term='position'/><category term='cross-platform'/><category term='ECMAScript 5'/><category term='isPrototypeOf'/><category term='Callback'/><category term='mode'/><category term='Number'/><category term='implicit'/><category term='NekoVM'/><category term='handshake'/><category term='JHP'/><category term='languages'/><category term='RitaliaCamp1'/><category term='exit'/><category term='Netbook'/><category term='Rant'/><category term='fail'/><category term='snow'/><category term='data'/><category term='progress'/><category term='reader'/><title type='text'>Web Reflection</title><subtitle type='html'>behind the design</subtitle><link rel='http://schemas.google.com/g/2005#feed' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/posts/default'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default?max-results=100'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/'/><link rel='hub' href='http://pubsubhubbub.appspot.com/'/><link rel='next' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default?start-index=101&amp;max-results=100'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><generator version='7.00' uri='http://www.blogger.com'>Blogger</generator><openSearch:totalResults>464</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><openSearch:itemsPerPage>100</openSearch:itemsPerPage><entry><id>tag:blogger.com,1999:blog-34454975.post-5734794714467497042</id><published>2012-01-18T01:10:00.003+01:00</published><updated>2012-01-18T01:12:30.236+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Map'/><category scheme='http://www.blogger.com/atom/ns#' term='Harmony'/><category scheme='http://www.blogger.com/atom/ns#' term='ES6'/><category scheme='http://www.blogger.com/atom/ns#' term='Set'/><category scheme='http://www.blogger.com/atom/ns#' term='WeakMap'/><category scheme='http://www.blogger.com/atom/ns#' term='Rhino'/><category scheme='http://www.blogger.com/atom/ns#' term='node.js'/><category scheme='http://www.blogger.com/atom/ns#' term='polyfills'/><category scheme='http://www.blogger.com/atom/ns#' term='browser'/><title type='text'>ES6 Harmony Collections Fast Polyfill</title><content type='html'>Well, just in case you read RSS and you missed my tweet ... everything you need to know in &lt;a href="https://github.com/WebReflection/es6-collections#readme"&gt;github repository&lt;/a&gt;.&lt;br /&gt;Have fun with Harmony Collections&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-5734794714467497042?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/5734794714467497042/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=5734794714467497042' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/5734794714467497042'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/5734794714467497042'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2012/01/es6-harmony-collections-fast-polyfill.html' title='ES6 Harmony Collections Fast Polyfill'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-150497766504525989</id><published>2012-01-16T17:51:00.010+01:00</published><updated>2012-01-16T18:33:30.945+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='EventListener'/><category scheme='http://www.blogger.com/atom/ns#' term='API'/><category scheme='http://www.blogger.com/atom/ns#' term='node.js'/><category scheme='http://www.blogger.com/atom/ns#' term='DOM'/><category scheme='http://www.blogger.com/atom/ns#' term='EventEmitter'/><title type='text'>On EventEmitter In node.js</title><content type='html'>Today I had a whole &lt;a href="http://nodejs.org/"&gt;node.js&lt;/a&gt; session and I have spent a bit of time looking at current EventEmitter implementation.&lt;br /&gt;I have twitted already that it sucks as it is, and while it's really trivial to implement the &lt;a href="https://github.com/WebReflection/yuno/blob/master/src/events/EventEmitter.js"&gt;same for any browser&lt;/a&gt;, I believe many mistakes have been made about the &lt;a href="http://nodejs.org/docs/latest/api/events.html"&gt;API&lt;/a&gt;. Here the list:&lt;br /&gt;&lt;ol&gt;&lt;li&gt;&lt;strong&gt;on()&lt;/strong&gt; is a shortcut for addListener but there is &lt;strong&gt;no off()&lt;/strong&gt; as removeListener's shortcut (inconsistent)&lt;/li&gt;&lt;li&gt;&lt;strong&gt;add/removeListener&lt;/strong&gt; is not DOM friendly, we cannot reuse an EventEmitter in the browser without double checking if those methods exist&lt;/li&gt;&lt;li&gt;&lt;strong&gt;removeAllListeners()&lt;/strong&gt; accepts no arguments and cleans up the whole emitter but there is no way to retrieve all listeners via &lt;strong&gt;listeners()&lt;/strong&gt; passing no arguments (again, inconsistent)&lt;/li&gt;&lt;li&gt;there's no possibility to use &lt;strong&gt;handleEvent&lt;/strong&gt; property, as already defined in the &lt;a href="http://www.w3.org/TR/DOM-Level-2-Events/events.html#Events-EventListener"&gt;EventListener&lt;/a&gt;, once again objects are not reusable between client and server&lt;/li&gt;&lt;li&gt;&lt;strong&gt;no duplicated checks&lt;/strong&gt; for both addListener and removeListener, this is totally inconsistent against DOM &lt;a href="http://www.w3.org/TR/DOM-Level-2-Events/events.html#Events-EventTarget"&gt;EventTarget&lt;/a&gt; plus I found it kinda hilarious since there is also a max number of listeners allowed defined via &lt;strong&gt; setMaxListeners&lt;/strong&gt; method ... if we add same listener twice, it's fired twice ... a non-sense for those coming from the web. We also need to &lt;em&gt;removeListener&lt;/em&gt; twice or more 'cause we have no idea if same listeners has been added by mistake twice so ... it's just screwed up, removing a specific listener may be not enough and there is no easy way to check if the listener has been removed or not&lt;/li&gt;&lt;li&gt;there is no interface to define events plus the single argument is not a DOM Event like, not even an object with data property and at least a type that points to the event name ... once again, not possible to reuse anything on DOM world&lt;/li&gt;&lt;/ol&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Why All Of This Is Bad&lt;/h3&gt;node.js is bringing a lot of non JavaScripters and non browser friendly JS developers into its community and this is the good part. What is absolutely bad is that if node.js won't be minimally aligned with the rest of the code in the browsers out there our life as "&lt;i&gt;one language everywhere&lt;/i&gt;" will become harder than ever.&lt;br /&gt;I have personally created &lt;a href="https://github.com/WebReflection/wru"&gt;wru&lt;/a&gt; which runs in all browsers and many server side JS environments but what I would like to avoid is to write twice any sort of test because of weirdly implemented APIs.&lt;br /&gt;If it's about shortcutting, as example, &lt;em&gt;on()&lt;/em&gt; and &lt;em&gt;off()&lt;/em&gt; are more than welcome but why on earth the long version should be &lt;em&gt;addListener&lt;/em&gt; rather than &lt;em&gt;addEventListener&lt;/em&gt;?&lt;br /&gt;Why events passed as objects since ever in client JS should be passed as string with optional extra data as second argument?&lt;br /&gt;Where are defaults control over events fired across more listeners?&lt;br /&gt;Why on earth &lt;em&gt;handleEvent&lt;/em&gt; is not supported and a listener can be only a function which most likely will require a bind to something else?&lt;br /&gt;Why is it possible to erase all listeners without even knowing "who set them where" but it's not possible to retrieve all of them so that at least we could act accordingly with the event name following some rule rather than "&lt;i&gt;just remove them all&lt;/i&gt;" ?&lt;br /&gt;&lt;br /&gt;I hope somebody will agree with me, considering flakey points I have already described and changing or improving ASAP this EventEmitter API ... it would be sooooooo coooool to be aligned in both worlds for at least the most used pattern/procedure ever in JS world, don't you say? Thanks for your attention.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-150497766504525989?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/150497766504525989/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=150497766504525989' title='7 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/150497766504525989'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/150497766504525989'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2012/01/on-eventemitter-in-nodejs.html' title='On EventEmitter In node.js'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>7</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-1441988846510145281</id><published>2012-01-15T16:40:00.006+01:00</published><updated>2012-01-15T19:11:33.863+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='yuno'/><category scheme='http://www.blogger.com/atom/ns#' term='loader'/><category scheme='http://www.blogger.com/atom/ns#' term='CommonJS'/><category scheme='http://www.blogger.com/atom/ns#' term='require'/><category scheme='http://www.blogger.com/atom/ns#' term='pattern'/><category scheme='http://www.blogger.com/atom/ns#' term='AMD'/><category scheme='http://www.blogger.com/atom/ns#' term='module'/><category scheme='http://www.blogger.com/atom/ns#' term='browser'/><title type='text'>Y U NO use libraries and add stuff</title><content type='html'>This is an early introduction to a project I have been thinking about for a while.&lt;br /&gt;The project is &lt;a href="https://github.com/WebReflection/yuno"&gt;already usable in github&lt;/a&gt; but the documentation is lacking all over the place so please be patient and I'll add everything necessary to understand and use &lt;strong&gt;yuno&lt;/strong&gt;.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Zero Stress Namespace And Dependencies Resolver&lt;/h3&gt;Let's face the reality: today there is still no standard way to include dependencies in a script.&lt;br /&gt;If we are using a generic JS loader, the aim is to simply download files and eventually wait for one or more dependency in order to be able to use everything we need.&lt;br /&gt;The &lt;strong&gt;require&lt;/strong&gt; logic introduced via &lt;em&gt;node.js&lt;/em&gt; does not scale in the browser due synchronous nature of the method itself plus the sandbox not that easy to emulate in a browser environment.&lt;br /&gt;The &lt;strong&gt;AMD&lt;/strong&gt; concept is kinda &lt;i&gt;OKish&lt;/i&gt; but once we load after dependencies, there is no way to implement a new one within the callback unless we are not exporting.&lt;br /&gt;I find AMD approach surely the most convenient but still not the best one:&lt;ol&gt;&lt;li&gt;we cannot implement a &lt;em&gt;provide&lt;/em&gt; like procedure, whenever this could be handy or not&lt;/li&gt;&lt;li&gt;it's not clear within the module code itself, what we are exporting exactly&lt;/li&gt;&lt;/ol&gt;&lt;br /&gt;Specially the last point means that AMD does not scale properly with already combined code because AMD relies in the module/folder structure itself ... so, cannot we do anything better than what we have so far?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The yuno Concept&lt;/h3&gt;&lt;img src="http://s3.amazonaws.com/ragefaces/fd910848b62298e03671f2e200c4c245.png" width="400" /&gt;&lt;br /&gt;Directly out of a well known meme, &lt;strong&gt;yuno&lt;/strong&gt; logic is quite straightforward:&lt;ul&gt;&lt;li&gt;automagically resolved path, you point once to &lt;em&gt;yuno.js&lt;/em&gt; file in your page and you are ready to go&lt;/li&gt;&lt;li&gt;compatible with already combined files (smart builder coming soon)&lt;/li&gt;&lt;li&gt;&lt;strong&gt;yuno.use()&lt;/strong&gt; semantic method to define dependencies, if necessary&lt;/li&gt;&lt;li&gt;&lt;strong&gt;yuno.use().and()&lt;/strong&gt; resolved callback to receive modules AMD style once everything has been loaded&lt;/li&gt;&lt;li&gt;&lt;strong&gt;yuno.add()&lt;/strong&gt; standard ES5 way to define new namespaces, objects, properties, or constructors ( so no extra note in the documentation is needed )&lt;/li&gt;&lt;li&gt;cross referenced dependencies automagically resolved: if two different scripts needs same library, this will be loaded once for both&lt;/li&gt;&lt;li&gt;external url compatible, because you may want to include a file from some known CDN rather than put all scripts in your own host ( speed up common libraries download across different libraries that depend on same core, e.g/ jQuery )&lt;/li&gt;&lt;li&gt;modules, namespaces, or global objects, cannot be reassigned twice, which means if we are adding twice same thing we are doing it wrong, but if we are not aware of other script that added same thing before we have a notification&lt;/li&gt;&lt;li&gt;something else I may decide to add after this post&lt;/li&gt;&lt;/ul&gt;Here some example:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// define a jQuery plugin&lt;br /&gt;yuno.use(&lt;br /&gt;  "jQuery",&lt;br /&gt;  "extraStuff"&lt;br /&gt;).and(function (jQuery, extraStuff) {&lt;br /&gt;  yuno.add(jQuery.fn, "myPlugin", {value:function () {&lt;br /&gt;    // your amazing code here&lt;br /&gt;  }});&lt;br /&gt;  // we may opt for just this line&lt;br /&gt;  jQuery.fn.myPlugin = function () {};&lt;br /&gt;  // in order to export our plugin&lt;br /&gt;  // however, the purpose of yuno is to have&lt;br /&gt;  // a common recognizable way to understand&lt;br /&gt;  // what the module is about&lt;br /&gt;  // plus the "add" method is safer&lt;br /&gt;});&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Let's imagine that &lt;i&gt;extraStuff&lt;/i&gt; contains similar code:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// define extraStuff&lt;br /&gt;yuno.use(&lt;br /&gt;  "jQuery"&lt;br /&gt;).and(function (jQuery) {&lt;br /&gt;  yuno.add(jQuery.fn, "extraStuff", {value:function () {&lt;br /&gt;    // your amazing code here&lt;br /&gt;  }});&lt;br /&gt;});&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Both plugin and extraStuff needs jQuery to be executed ... will jQuery be loaded twice? Nope, it's simply part of a queue of modules that needs to be resolved.&lt;br /&gt;As soon as it's loaded/added once, every module that depends on jQuery will be notified so that if the list of dependencies is fully loaded, the callback passed to &lt;em&gt;and&lt;/em&gt; will be executed.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Y U NO Add&lt;/h3&gt;Modules are only one part of the proposal since we may define a script where no external dependency is needed.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// note: no external dependency, just add&lt;br /&gt;yuno.add(this, "MyFreakingCoolConstructor", {value:&lt;br /&gt;  function MyFreakingCoolConstructor() {&lt;br /&gt;    // freaking cool stuff here&lt;br /&gt;  }&lt;br /&gt;});&lt;br /&gt;// this points to the global object so that ...&lt;br /&gt;MyFreakingCoolConstructor.prototype.doStuff = function () {&lt;br /&gt;  // freaking cool method&lt;br /&gt;};&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The &lt;em&gt;yuno.add&lt;/em&gt; method reflects &lt;em&gt;Object.defineProperty&lt;/em&gt; which means for ES5 compatible browsers getters, setters, and values, are all accepted and flagged as not enumerable, not writable, and not configurable by default.&lt;br /&gt;Of course we can re-define this behavior but most likely this is what we need/want as default in any case ... isn't it?&lt;br /&gt;For those browsers not there yet, the &lt;em&gt;Object.defineProperty&lt;/em&gt; method is partially shimmed where &lt;em&gt;__defineGetter/Setter__&lt;/em&gt; or simply the value property will be used instead.&lt;br /&gt;Bear in mind this shim may change accordingly with real needs but so far all mobile browsers should work as expected plus all Desktop browsers except IE less than 9 ... not so common targets for modern web sites.&lt;br /&gt;Last, but not least, &lt;em&gt;yuno&lt;/em&gt; logic does not necessarily need the &lt;em&gt;add&lt;/em&gt; call so feel free to simply define your global object or your namespace the way you want.&lt;br /&gt;However, as I have said before, the &lt;em&gt;add&lt;/em&gt; method is a simple call able to make things more robust, to speedup and ensure notifications, and to use a standard, recognizable pattern, to define our own objects/functions being sure nobody did before thanks to defaults descriptor behavior which is not writable and not configurable indeed.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;To DOs&lt;/h3&gt;This is just an initial idea of what the &lt;em&gt;yuno&lt;/em&gt; object is able to do but few things are in my mind. On top of the list we have the possibility to shortener CDN calls via prefixes such &lt;em&gt;"cdn:jQuery"&lt;/em&gt;, as example, in order to use most common CDNs to load widely shared libraries.&lt;br /&gt;Last, but not least, the reason I am writing this is because I am personally not that happy with any solution we have out there so if you are willing to contribute, please just leave a comment, thanks.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-1441988846510145281?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/1441988846510145281/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=1441988846510145281' title='5 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/1441988846510145281'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/1441988846510145281'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2012/01/y-u-no-use-libraries-and-add-stuff.html' title='Y U NO use libraries and add stuff'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>5</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-4319750001280541566</id><published>2012-01-10T00:29:00.004+01:00</published><updated>2012-01-10T13:57:51.679+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='DOM'/><category scheme='http://www.blogger.com/atom/ns#' term='bind'/><category scheme='http://www.blogger.com/atom/ns#' term='events'/><category scheme='http://www.blogger.com/atom/ns#' term='proposal'/><title type='text'>Introducing ObjectHandler</title><content type='html'>since the discussion about a better Function#bind will probably never end, and since a must have dependency would be the ES6 WeakMap which is in any existent shim leak prone due lack of control via ES5+, I have proposed another way to solve the problem.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;ObjectHandler IDL Like&lt;/h3&gt;&lt;pre class="code"&gt;&lt;br /&gt;/**&lt;br /&gt; *  interface ObjectHandler implements EventListener {&lt;br /&gt; *      void                handleEvent(in Event evt);&lt;br /&gt; *      void                remitEvent(in Event evt);&lt;br /&gt; *      attribute   Object  events;&lt;br /&gt; *  };&lt;br /&gt; *&lt;br /&gt; *  @link   http://www.w3.org/TR/DOM-Level-2-Events/events.html#Events-EventListener&lt;br /&gt; */&lt;br /&gt;var ObjectHandler = {&lt;br /&gt;  handleEvent: function handleEvent(e) {&lt;br /&gt;    var&lt;br /&gt;      events = this.events,&lt;br /&gt;      type = e.type&lt;br /&gt;    ;&lt;br /&gt;    if (events.hasOwnProperty(type)) {&lt;br /&gt;      events[type].call(this, e);&lt;br /&gt;    }&lt;br /&gt;  },&lt;br /&gt;  // it could be called removeEvent too, as you wish&lt;br /&gt;  remitEvent: function cancelEvent(e) {&lt;br /&gt;    e.currentTarget.removeEventListener(&lt;br /&gt;      e.type, this, e.eventPhase === e.CAPTURING_PHASE&lt;br /&gt;    );&lt;br /&gt;  }&lt;br /&gt;};&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Above object is an Abstract implementation. In JavaScript we can borrow methods so whatever "class" would like to implement above behavior should extend the object or borrow those two methods and specify an &lt;strong&gt;events&lt;/strong&gt; property.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Examples&lt;/h3&gt;Let's say we have a UI Class which aim is to react to certain events ... let's call it button:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;function UIButton(parentNode) {&lt;br /&gt;  // add the node&lt;br /&gt;  this.el = parentNode.appendChild(&lt;br /&gt;    parentNode.ownerDocument.createElement("button")&lt;br /&gt;  );&lt;br /&gt;  // add quickly events to the node&lt;br /&gt;  for (var key in this.events) {&lt;br /&gt;    // add the listener ... &lt;br /&gt;    // NOTE: nothing to bind, no duplicated entries either&lt;br /&gt;    this.el.addEventListener(key, this, false);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;// extends the class&lt;br /&gt;Object.defineProperties(&lt;br /&gt;  UIButton.prototype,&lt;br /&gt;  {&lt;br /&gt;    // implements ObjectHandler&lt;br /&gt;    handleEvent: {value: ObjectHandler.handleEvent},&lt;br /&gt;    remitEvent: {value: ObjectHandler.remitEvent},&lt;br /&gt;    events: {value: {&lt;br /&gt;      // only once thanks to remitEvent&lt;br /&gt;      click: function (evt) {&lt;br /&gt;        alert("only once");&lt;br /&gt;        this.remitEvent(evt);&lt;br /&gt;      },&lt;br /&gt;      // some decoration on actions&lt;br /&gt;      mousedown: function (evt) {&lt;br /&gt;        this.el.style.border = "1px solid black";&lt;br /&gt;      },&lt;br /&gt;      mouseup: function (evt) {&lt;br /&gt;        this.el.style.border = null;&lt;br /&gt;      },&lt;br /&gt;      // recicle mouseup behavior&lt;br /&gt;      mouseout: function (evt) {&lt;br /&gt;        this.events.mouseup.call(this, evt);&lt;br /&gt;      }&lt;br /&gt;    }}&lt;br /&gt;  }&lt;br /&gt;);&lt;br /&gt;&lt;br /&gt;// example on window load&lt;br /&gt;this.onload = function () {&lt;br /&gt;  new UIButton(document.body);&lt;br /&gt;};&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Got it? Events property is simply an object shared through the prototype with properties name that are exactly the equivalent of DOM events name ... easy!&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Pros&lt;/h3&gt;&lt;ul&gt;&lt;li&gt;memory safe, nothing to bind, trap as bound, and stuff like this ... all instances will share same logic and bind is not even needed, aka: problem solved&lt;/li&gt;&lt;li&gt;events are defined in a single place, easy to find, maintain, extend&lt;/li&gt;&lt;li&gt;events are recycled, as it was as example for mouseout, though the instance&lt;/li&gt;&lt;li&gt;most UI frameworks need the instance rather than the DOM node, to behave accordingly&lt;/li&gt;&lt;li&gt;ObjectHandler can be used same way for "ObjectTarget", those listeners/able JS implementations, in order to uniform an event driven approach&lt;/li&gt;&lt;li&gt;no risk to bind twice, no risk to remove the wrong callback, bound or not, it's the instance that makes the deal, not inline functions so it's less error prone&lt;/li&gt;&lt;li&gt;&lt;strong&gt;performances&lt;/strong&gt; in therms of both memory footprint and operation per each instance ... once again, no need to bind all methods to the instance itself ... what is in events is basically bound automatically through a single entry point, defined in ObjectHandler, for every single use case&lt;/li&gt;&lt;/ul&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Cons&lt;/h3&gt; ... no idea, I cannot find any and I just like this solution over the Function#bind improvements since it's both cross platform, whenever addEventListener is present, but it can be recycled for any other no DOM use case as long as the event will have a currentTarget property that points to the current instance ( I will write an example/proposal soon ... OK? )&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;The main problem with proposal is adoptions and I would like to know UI Framework users feedbacks. Ideally this way to handle events could become a de facto standard dropping the redundant and massive usage of Function#bind for cases where the focus should be for the instance and not for the callback.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-4319750001280541566?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/4319750001280541566/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=4319750001280541566' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/4319750001280541566'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/4319750001280541566'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2012/01/introducing-objecthandler.html' title='Introducing ObjectHandler'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-6460446763109846399</id><published>2012-01-04T23:09:00.014+01:00</published><updated>2012-01-05T17:55:04.349+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='function'/><category scheme='http://www.blogger.com/atom/ns#' term='improvement'/><category scheme='http://www.blogger.com/atom/ns#' term='bind'/><title type='text'>Improving Function.prototype.bind</title><content type='html'>There are a couple of things I have never liked that much about &lt;a href="https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Function/bind"&gt;Function#bind&lt;/a&gt; and this post is about proposing a pattern hopefully better than common one.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;At The End Of The Function&lt;/h3&gt;A common argument about parentheses around inline invoked functions is that developers can easily recognize them.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// considered ambiguous&lt;br /&gt;var someThing = function () {&lt;br /&gt;  return {};&lt;br /&gt;}();&lt;br /&gt;&lt;br /&gt;// considered not ambiguous&lt;br /&gt;var someThing = (function () { // note the parenthesis&lt;br /&gt;  return {};&lt;br /&gt;}()); // note the parenthesis&lt;br /&gt;&lt;br /&gt;// exact same behavior of latest one&lt;br /&gt;// but considered slightly ambiguous&lt;br /&gt;var someThing = (function () { // note the parenthesis&lt;br /&gt;  return {};&lt;br /&gt;})(); // note the parenthesis&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The parentheses version apparently wins but, specially when no assignment is needed, I believe these are even less ambiguous:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;-function(){&lt;br /&gt;  alert("OK");&lt;br /&gt;}();&lt;br /&gt;&lt;br /&gt;+function(){&lt;br /&gt;  alert("OK");&lt;br /&gt;}();&lt;br /&gt;&lt;br /&gt;!function(){&lt;br /&gt;  alert("OK");&lt;br /&gt;}();&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Of course if there is an operator that function will be executed, why on earth anyone would do that otherwise?&lt;br /&gt;Anyway, the problem with all of these human friendly syntax pattern recognition strategies, is that the context of the function, or the whole code behavior, could be polluted/changed via &lt;em&gt;bind&lt;/em&gt; or &lt;em&gt;call&lt;/em&gt; or &lt;em&gt;apply&lt;/em&gt; so we need in any case to scroll 'till the end to better understand what is going on inside the function and what is returned, exactly.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// ES3 example&lt;br /&gt;var something = (function(){&lt;br /&gt;   // this could be global object or something else&lt;br /&gt;   return this.doSomeStuff();&lt;br /&gt;}.bind(unexpectedObject)); // or call for other cases&lt;br /&gt;&lt;br /&gt;// ES5&lt;br /&gt;var something = (function(){"use strict";&lt;br /&gt;   // if there is a this reference&lt;br /&gt;   // we need to reach the end to understand&lt;br /&gt;   // what is it&lt;br /&gt;   return this.doSomeStuff();&lt;br /&gt;}.bind(unexpectedObject));&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The summary is that &lt;em&gt;bind&lt;/em&gt;, used inline, is more like a &lt;a href="http://united-coders.com/christian-harms/what-are-yoda-conditions"&gt;yoda condition&lt;/a&gt; rather than a developer friendly helper so the first point is that &lt;em&gt;bind&lt;/em&gt;, as it is, forces the developer to always check the end of the function to know if this has been executed inline or it has been bound to a different context, as well as yoda conditions forces the developer to read "&lt;i&gt;upside down&lt;/i&gt;" a statement.&lt;br /&gt;Last, but not least, of course if it's just about bind, parentheses are not helping at all ... still scroll 'till the end&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// perfectly valid, not even executed&lt;br /&gt;// but still important to know&lt;br /&gt;// what will be the context for future calls&lt;br /&gt;var something = function(){&lt;br /&gt;   return this.doSomeStuff();&lt;br /&gt;}.bind(unexpectedObject);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Team Speaking&lt;/h3&gt;Ok, agreed, a function bigger than 10 lines is not that good and should be split and &lt;i&gt;blah blah blah&lt;/i&gt; ... point is that sometimes function have to be big since these provide us a way to create private variables and methods ... ok?&lt;br /&gt;Also if that was "&lt;i&gt;the good part&lt;/i&gt;", I mean just putting parentheses around, there is some conflict with the fact that functions should not be that long ... I mean, how can we mistake whatever happened in 10 lines?&lt;br /&gt;The truly good part could be done by developers, specially those that work in a team.&lt;br /&gt;The first good rule is to write a bloody single line comment at the very first line, this would just solve everything:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var something = function () {&lt;br /&gt;  //! executed inline, returns object&lt;br /&gt;&lt;br /&gt;  ... the rest of the code ...&lt;br /&gt;}();&lt;br /&gt;&lt;br /&gt;var somethingElse = function () {&lt;br /&gt;  //! bound to variable obj&lt;br /&gt;&lt;br /&gt;  ... the rest of the code ...&lt;br /&gt;}.bind(obj);&lt;br /&gt;&lt;br /&gt;var somethingCrazy = function () {&lt;br /&gt;  //! bound to obj + executed inline&lt;br /&gt;&lt;br /&gt;  .. the rest of the code ...&lt;br /&gt;}.bind(obj)();&lt;br /&gt;&lt;br /&gt;-function(){&lt;br /&gt;  // bound to obj&lt;br /&gt;}.bind(obj)();&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Got it? Nobody would ever complain about these little helps ... isn't it? But since we are all lazy devs, the second helper is function declaration rather than function expression.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;function impossibruToConfuse(){}&lt;br /&gt;&lt;br /&gt;var something = impossibruToConfuse.bind(obj);&lt;br /&gt;var something = impossibruToConfuse();&lt;br /&gt;var something = impossibruToConfuse.call(obj);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;With a single line to read I believe the problem is solved ... isn't it? Still ways to improve.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Unable To Retrieve Same Bound Function&lt;/h3&gt;The second most annoying thing ever, something that leads inevitably to uncomfortable patterns, is the inability to retrieve an already bound function through the same object.&lt;br /&gt;In my humble opinion, was a freaking design mistake indeed to create a new bound object per each bind call since I believe nobody in this world ever used this "&lt;i&gt;feature&lt;/i&gt;".&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;function task(){}&lt;br /&gt;&lt;br /&gt;// Y U NO THE SAME !!!&lt;br /&gt;task.bind(window) === task.bind(window);&lt;br /&gt;// false .... &lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;If the function is the same it means it has same context, inner and outer scope of the other function bound to the same object.&lt;br /&gt;If we bind twice the same object we are doing it wrong 'cause most likely we never meant/need two different bound callbacks/objects for that task ... isn't it?&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;An Error Prone Logic&lt;/h4&gt;The most basic fail of this logic is about listeners, both DOM listeners or self implemented listeners, extremely common in an always more asynchronous driven language as JavaScript is.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;generic.addEventListener("stuff", stuff.bind(obj), false);&lt;br /&gt;&lt;br /&gt;// how many times have you seen this later on?&lt;br /&gt;generic.removeEventListener("stuff", stuff.bind(obj), false);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Above example won't work as expected ... of course it won't work as expected ... developers expect the same function/object, instead they have a new one.&lt;br /&gt;This approach forces developers to store temporarily the bloody bound function to some private, global, variable or property.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;obj._boundStuff = stuff.bind(obj);&lt;br /&gt;generic.addEventListener("stuff", obj._boundStuff, false);&lt;br /&gt;&lt;br /&gt;// ... later on ...&lt;br /&gt;if (obj._boundStuff) {&lt;br /&gt;  generic.removeEventListener("stuff", obj._boundStuff, false);&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Remember how lazy we are so that parentheses became one of the good parts of JavaScript since a line of comment was too boring? Now look again at latest example and think how many times you have done something similar ...&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;A Clever Object.prototype.boundTo&lt;/h3&gt;With ES5 we are so lucky to be able to pollute global constructors without influencing for/in and as long as our implementation is not obtrusive and, most important, makes sense.&lt;br /&gt;I came up with this proposal in order to solve at least latest problems described before: a &lt;strong&gt;lazy boundTo method&lt;/strong&gt;&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;!function (Object) {&lt;br /&gt;&lt;br /&gt;  // (C) WebReflection - Mit Style License&lt;br /&gt;&lt;br /&gt;  var // private scope shortcuts&lt;br /&gt;    BOUND_TO = "boundTo", // or maybe "asContextOf" ?&lt;br /&gt;    defineProperty = Object.defineProperty,&lt;br /&gt;    bind = defineProperty.bind || function (self) {&lt;br /&gt;      // simple partial shim for "not there yet" ES5 browsers&lt;br /&gt;      var callback = this;&lt;br /&gt;      return function bound() {&lt;br /&gt;        return callback.apply(self, arguments);&lt;br /&gt;      };&lt;br /&gt;    }&lt;br /&gt;  ;&lt;br /&gt;&lt;br /&gt;  defineProperty(&lt;br /&gt;    Object.prototype,&lt;br /&gt;    BOUND_TO, {&lt;br /&gt;      value: function (callback, remove) {&lt;br /&gt;        // only the very first time&lt;br /&gt;        // two private stacks are created&lt;br /&gt;        // and related to the current object&lt;br /&gt;        var&lt;br /&gt;          cbStack = [],&lt;br /&gt;          boundStack = [],&lt;br /&gt;          self = this&lt;br /&gt;        ;&lt;br /&gt;        // overwrite the inherited BOUND_TO method&lt;br /&gt;        // with the one we actually need&lt;br /&gt;        defineProperty(&lt;br /&gt;          self,&lt;br /&gt;          BOUND_TO, {&lt;br /&gt;            value: function boundTo(callback, remove) {&lt;br /&gt;              var&lt;br /&gt;                i = cbStack.indexOf(callback),&lt;br /&gt;                callback = i &lt; 0 ?&lt;br /&gt;                  boundStack[&lt;br /&gt;                    i = cbStack.push(callback) - 1&lt;br /&gt;                  ] = bind.call(callback, self)&lt;br /&gt;                  :&lt;br /&gt;                  boundStack[i]&lt;br /&gt;              ;&lt;br /&gt;              // falsy values accepted&lt;br /&gt;              // except null or undefined&lt;br /&gt;              // so it's true by default&lt;br /&gt;              if (remove == false) {&lt;br /&gt;                cbStack.splice(i, 1);&lt;br /&gt;                boundStack.splice(i, 1);&lt;br /&gt;              }&lt;br /&gt;              // returns bound callback in any case&lt;br /&gt;              // handy to remove listeners and clean stacks&lt;br /&gt;              // in one single operation&lt;br /&gt;              return callback;&lt;br /&gt;            }&lt;br /&gt;          }&lt;br /&gt;        );&lt;br /&gt;        // only the first time, invoe the overwritten method&lt;br /&gt;        // use directly latter one every other time&lt;br /&gt;        return self[BOUND_TO](callback, remove);&lt;br /&gt;      }&lt;br /&gt;    }&lt;br /&gt;  );&lt;br /&gt;}(Object);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;How above snippet is supposed to be used? Here a basic example:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;generic.addEventListener("stuff", obj.boundTo(stuff), false);&lt;br /&gt;&lt;br /&gt;// ... later on ...&lt;br /&gt;generic.removeEventListener("stuff", obj.boundTo(stuff, 0), false);&lt;br /&gt;&lt;br /&gt;// bear in mind that ...&lt;br /&gt;obj.boundTo(stuff) === obj.boundTo(stuff);&lt;br /&gt;// always ... unless we release explicitly the bound function/object&lt;br /&gt;obj.boundTo(stuff, false) !== obj.boundTo(stuff);&lt;br /&gt;// since once removed, the new obj.boundTo call will create a new one&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;h4&gt;Pros&lt;/h4&gt;No need to check, no need to store the bound version, memory leaks safe, no need to do anything extra except calling the method through, and this is needed, the same function.&lt;br /&gt;The semantic is straight forward and rather than a yoda condition we have a clear operation that means: return the function created to bind this object as context.&lt;br /&gt;Last, but not least, even if the function was not bound, everything should work as expected, as long as the &lt;em&gt;removeListener&lt;/em&gt; generic method has been implemented properly ( checking if the callback/object was attached already )&lt;br /&gt;&lt;h4&gt;Cons&lt;/h4&gt;Not really, but the function has to be the same. It must be said that two apparently identical functions could be just a copy and paste in two completely different outer scopes. This means that there is no bullet proof way to understand if a function written twice is similar to another one since it is not possible to understand surrounding scopes and it would be silly to do this even on the JS engine level. I am talking about another, unfortunately, common mistake:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// wrong examples ... does not work as expected&lt;br /&gt;&lt;br /&gt;generic.addListener("whatever", function () {&lt;br /&gt;  return this.whatever;&lt;br /&gt;}.bind(object), false);&lt;br /&gt;&lt;br /&gt;// followed by ...&lt;br /&gt;generic.removeListener("whatever", function () {&lt;br /&gt;  return this.whatever;&lt;br /&gt;}.bind(object), false);&lt;br /&gt;&lt;br /&gt;// or in this proposal case ...&lt;br /&gt;&lt;br /&gt;generic.addListener("whatever", object.boundTo(function () {&lt;br /&gt;  return this.whatever;&lt;br /&gt;}), false);&lt;br /&gt;&lt;br /&gt;// followed by ...&lt;br /&gt;generic.removeListener("whatever", object.boundTo(function () {&lt;br /&gt;  return this.whatever;&lt;br /&gt;}), false);&lt;br /&gt;&lt;br /&gt;// ... but this is not how JavaScript works ...&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Memory speaking, the very first time we use this strategy we create two extra arrays able to speed up operations through indexed function and and bound version per each object. This is inevitable in any case and it's almost exactly the same we do when we address once the bound function.&lt;br /&gt;Once the object has been Garbage Collected, related private arrays will have a reference count equal to zero so the memory should clean up automatically without problems and including all functions bound to that object.&lt;br /&gt;&lt;br /&gt;As explained in the example, it is possible in any case to release explicitly bound functions so we can feel like the memory usage is under control.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Why No Arguments&lt;/h3&gt;The combination of arguments could be such big number that this technique won't be interesting anymore, specially regarding performances.&lt;br /&gt;It does not really make sense to over complicate such basic, most needed, scenario but if you think this is the biggest impediment, then the name should simply be &lt;em&gt;asContextOf&lt;/em&gt; so that no ambiguity would be shared with &lt;em&gt;bind&lt;/em&gt; native signature.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Update - Preserving Private Methods&lt;/h3&gt;Another reason to chose my proposal is the ability to bind proper private methods without using the current instance to store the bound method anywhere ... follow &lt;a href="https://mail.mozilla.org/pipermail/es-discuss/2012-January/019277.html"&gt;the es-discuss ML&lt;/a&gt; to know more but here the stupid, basic, proof of concept:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// stupid useless example ... just as concept&lt;br /&gt;var Counter = (function () {&lt;br /&gt;  // private&lt;br /&gt;  function increase() {&lt;br /&gt;    this.clicks++;&lt;br /&gt;  }&lt;br /&gt;&lt;br /&gt;  function Counter() {&lt;br /&gt;    // none out there should be able to retrieve the bound function&lt;br /&gt;    document.addEventListener("click", this.boundTo(increase), false);&lt;br /&gt;  };&lt;br /&gt;  Counter.prototype.clicks = 0;&lt;br /&gt;  Counter.prototype.destroy = function () {&lt;br /&gt;    // so that only this class scope can control things and nobody else&lt;br /&gt;    document.removeEventListener("click", this.boundTo(increase), false);&lt;br /&gt;  };&lt;br /&gt;  return Counter;&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;I am pretty sure this simple lazy created proposal would be ideal for many frameworks and projects but if I am missing something or if you have any improvement to suggest, I will be more than happy to listen to you.&lt;br /&gt;Enjoy simplicity over semantic, this is yet another KISS and YAGNI proposal from this blog.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-6460446763109846399?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/6460446763109846399/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=6460446763109846399' title='6 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/6460446763109846399'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/6460446763109846399'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2012/01/improving-functionprototypebind.html' title='Improving Function.prototype.bind'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>6</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-8892808504319268322</id><published>2011-12-30T14:26:00.011+01:00</published><updated>2012-01-02T10:51:28.679+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='CSS3'/><category scheme='http://www.blogger.com/atom/ns#' term='2011'/><category scheme='http://www.blogger.com/atom/ns#' term='html5'/><title type='text'>Learning From 2011</title><content type='html'>It's time to summarize at least few mistakes or epic fails of the year, hoping the next one will try to follow a better direction.&lt;br /&gt;I won't mention anything related to war, politic, Berlusconi, or fashion related stuff, other more prepared than me will do via pictures or posts, all I gonna talk about is the field I am concerned about: web and mobile web oriented technologies and facts.&lt;br /&gt;The order is completely random, so grab a mug of coffee, take few minutes, and read 'till the end, forgetting for once &lt;em&gt;tl;dr&lt;/em&gt; philosophy ;)&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Partially (Multi)? Touch Device Case&lt;/h3&gt;This has been the most annoying fact of the year: vendors going out with freaking powerful mobile devices with touch or multi touch capable screen/hardware &lt;strong&gt;not exposed through the browser&lt;/strong&gt; and only available for native apps.&lt;br /&gt;We are not talking about potentially "dangerous" technologies as WebGL could be, we are talking about the most basic thing able to break 140% the user experience.&lt;br /&gt;If a user plays a native game or use a native map, as classic Map application could be, she will naturally use at least a finger, or more, to interact with the screen. Interaction does not mean &lt;em&gt;scroll the page&lt;/em&gt; and nothing else, interaction means full control of what the user is doing with the screen.&lt;br /&gt;As soon as the user surf the web, the browser pretends to know what the user would like to do on the screen without giving web developers any control over those actions.&lt;br /&gt;The inconsistent behavior comes when the &lt;strong&gt;viewport&lt;/strong&gt; meta tag is used to block, as example, the zooming in and out gesture because the whole layout has been developed for a &lt;strong&gt;static viewport&lt;/strong&gt; that should not change.&lt;br /&gt;In this case, only few vendors ( Apple ) or browsers ( Opera Mobile ) got it right, any other vendor with a WebKit based browser got it wrong. Here a few examples:&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;IE9 Mobile Epic Fail&lt;/h4&gt;IE9 is a great browser, compared with all other previous version, and it's freaking fast. This is true for both desktop and mobile phones but in latter case, IE9 is an epic fail when it comes to User Interaction.&lt;br /&gt;There is no bloody way to intercept a user moving a finger on the screen, and standard W3C Touch Events are not supported.&lt;br /&gt;You may think: oh well, I gonna use mouse events then ... and you are wrong, these are not fired until the user release her finger so ... forget about it, no "scroll" hacks will work as expected there ... also why on earth when everybody else is disabling JS actions during scrolling, IE9 Mobile fires it all the time?&lt;br /&gt;&lt;img src="http://s3.amazonaws.com/ragefaces/3fa9aa4e19889110c01bae7601d70e25.png" width="400" /&gt;&lt;br /&gt;&lt;br /&gt;Sad part is that Microsoft is investing a lot into HTML5, but if the most basic thing as Touch Events are, is not there, no reason to have the fastest mobile Canvas implementation because no game will be interactive, and no web app can be created as desired.&lt;br /&gt;Hopefully IE10 will simply follow W3C exposing both Touch and TouchList in a meaningful way ... please don't screw this or few developers will even consider to write software for this browser, thanks.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;webOS 2 Sad Fail&lt;/h4&gt;I have upgraded few minutes ago my Pre 2 to webOS 2.4.4 ... and I was expecting more from this update. My Palm Pre 2 exposes correctly multi touches through the system, but the web browser does not expose them and this is freaking annoying. Same IE9 behavior and at least at the end of 2011 I was expecting such simple browser update able to bring my Palm to the next level: User Interaction Through The Web ... &lt;strong&gt;FAIL&lt;/strong&gt;.&lt;br /&gt;The good old native Google Maps application for webOS 2.0.X is gone. This app was working like a charm and it was exposing multi touches through the multi touches capable screen ... now I have a slower and flicking version of Bing maps that is not even able to render pinch/spread without loosing the position on the screen since everything gets stuck truly easily.&lt;br /&gt;Now, I have no idea why this happened and why somebody wasted time to do this ... it's just worse than before and the browser still does not expose multi touches ... come on guys, this phone did not deserve to die like this.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Ultra Powerful ... "broken" Androids&lt;/h4&gt;It does not matter if we have 16 cores in our expensive smart phone when developers life is made harder for no reason ... with most recent Android phones we could create any sort of web application but here again, no-f*cking-body exposes TouchList via browser except few tablets out there.&lt;br /&gt;OK, still better than nothing, as it is for IE9 Mobile, FF Mobile ( I will come back later to this one ), or webOS browser, but how comes 3rd parties browsers such Opera Mobile are able to bring TouchList and expose multi touches through the multi touches capable screen and native browsers are all lacking of this basic feature?&lt;br /&gt;You don't even want to know how we managed to bring multiple touches in android devices, all you need to know is that is basically a hack and it requires a native application wrapper and this is, in my opinion, ridiculous!&lt;br /&gt;Nowadays, all users with a friend that uses an iPhone, will consider the multi touch web app broken in its android: come on, I use two fingers in other &lt;em&gt;things&lt;/em&gt; why I cannot do the same in this web site/application?&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;FireFox Mobile Fail&lt;/h4&gt;I don't know where to start with this browser ... I mean, guys, this is not Desktop, this is a touch screen. If you decide that the user cannot even scroll a paragraph horizontally because your freaking cool settings or bookmark view has to show up instead, you should create your own device and make the phone 3 times larger: 1/3 for the actual screen, 2/3 for your things nobody expect to appear during navigation.&lt;br /&gt;About touches, at least most recent version implements touch events but performances are still too bad compared with native browsers or Opera Mobile, and the fact settings or bookmarks show up when we touch close to the edge of the screen, plus the fact AFAIK there is no way to avoid this, make this browser not suitable for full screen web games/apps based on canvas: slow and unusable ... please fix/drop this!&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Update&lt;/strong&gt;It must be said that latest FF mobile brings better canvas performances and apparently it exposes a not so fast WebGL. I dd not know this the moment I wrote this post so FF Mobile is definitively already going to the right direction.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;iOS Gesture Events VS Others&lt;/h4&gt;These are not standard and nobody should care. The moment we can rely in TouchList and multi touches exposes through this interface, the problem is solved 'cause we can implement by our self any gesture we want.&lt;br /&gt;No need to wait 'till on spread/pinch are implemted and documented, just please give us TouchList and take your time after to do things properly. TouchList has been already defined ... that's all we need so far, thanks!&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Curious Case of Opera Mobile&lt;/h3&gt;Opera did weird things this year ... it switched from partial ES3 support to full ES 5.1 support ... what the hell guys, congratulations! Still there is no way to understand &lt;strong&gt;numbers&lt;/strong&gt; of this browser (again: Opera Mobile, NOT Mini) .&lt;br /&gt;Today, I can say Opera Mobile is one of the fastest and most capable browsers I have been dealing with but the lack of many CSS3 features have been &lt;em&gt;the arrow in the knee&lt;/em&gt; together with the fact Opera could have been the &lt;em&gt;Phone Gap Like&lt;/em&gt; software of the year while they focused on ... I guess something else.&lt;br /&gt;Don't give up guys, Opera Mobile is amazing and people may chose to download it as soon as most common HTML5/CSS3 things are working as expected and also you may expose freaking cool stuff without necessarily follow W3C, giving web developers the possibility to distribute applications directly through your browser as native wrapper ( and fallback to Webkit for iOS ) .&lt;br /&gt;Opera has always been pioneer, and it's time to be pioneer on mobile too because on desktop I am afraid to tell you it's hard to compete. Firefox, Chrome, and Webkit Nightly, are really advanced and I believe bigger teams, what we are missing is a &lt;strong&gt;not so fragmented browser&lt;/strong&gt; that works as expected in as many devices as possible because what I have seen with all webkit versions I have worked with this year was painful, hard, inconsistent, and WTF development oriented.&lt;br /&gt;Last, but not least, If there is not SQL Database, don't put a native useless Database function on the global scope or shims are screwed and if you don't expose SQL Database, at least expose Indexed DB or shims are screwed.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Android Whatever&lt;/h3&gt;While many developers think that Android is an Operating System, I am every day more convinced that Android is a &lt;em&gt;Super Kernel&lt;/em&gt; that has almost nothing to do with the Operating System itself.&lt;br /&gt;There are too many damn versions of Android, and even same major versions do not guarantee anything.&lt;br /&gt;Every device must be tested a part because every device, with every vendor specific &lt;em&gt;gotcha&lt;/em&gt;, software, or extra cool stuff, may behave differently. Funny enough, while I was thinking this is true for the webkit based browser only, there are many exceptions device specific that do not work as expected even natively ... oh, come on, don't call it OS!&lt;br /&gt;If we think about Windows, almost every piece of hardware is supported. Then we have the classic &lt;em&gt;crapware&lt;/em&gt; every single vendor puts by default in its own distributed piece of hardware ... fair enough, at least most basic things gonna work as expected in all of them ... right?&lt;br /&gt;With Android, the most basic free version has almost nothing. Cyanogenmod is the basic example, once you install it, you gonna scream for apps you expect to be there and it comes up you need the specific Gapp package ( Google Applications ).&lt;br /&gt;Same thing with Kindle Fire, based on the very basic version of Android so common apps available for other tablets may not work or may not be there.&lt;br /&gt;This means we can trust only a truly basic set of functionalities that are hopefully working in all distributions out there but you know, this is IT, expectations are rarely matching reality.&lt;br /&gt;The performances tuning per each device is another problem, as problematic are performances of the same app through the browser compared with those through the native layer.&lt;br /&gt;If you wrap your single touch full page canvas game into phone Gap, as example, you will realize how freaking fast it is compared with the same exact code through the browser ... why that? Security layer is off plus bound stuff is limited compared with the whole browser application ... fair enough? No it's not. The moment I realize it is possible to force HW accelerated rendering via native wrapper but it's not possible to do the same via browser I start screaming ... let us develop through the web or stop telling us you support standards because if these are limited intentionally then those not supported are developers themselves.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Mobile Web Apps Too Limited&lt;/h3&gt;I really hope I won't need to write a similar post at the end of 2012 but I am not sure there will be many progresses here ...&lt;br /&gt;W3C is slow, plus it may waste their/our time. Web SQL Database is an example, something I loved screwed by dependencies free purist.&lt;br /&gt;I have talked about Web SQL many times and right now I don't care about this specific topic, all I care is about moving forward.&lt;br /&gt;Time to agree and promote such interface to drop it after 2 years is not the way to go.&lt;br /&gt;Time to replace such interface with another one limited, slower, and not widely adopted as IndexedDB is, still not the way to go.&lt;br /&gt;We need a database, please put it there one ASAP and &lt;strong&gt;drop 50Mb per domain/tab limit&lt;/strong&gt;.&lt;br /&gt;No fools guys, if the logic behind the Web is that &lt;strong&gt;user must explicitly agree&lt;/strong&gt; give the user full control.&lt;br /&gt;If a web application requires more than 50Mb give the user the possibility to increase the database.&lt;br /&gt;All native apps do not care about how much space is used, these simply informs the user through system settings how much stored data there is. Google Earth, as example, even maps, these are heavy memory applications that do not ask every 5 megabytes if more space can be allowed ... this was another epic fail.&lt;br /&gt;Once the user accepts the fact this web application would like to use the storage, create a way to simplify the task able to verify how much data is being stored and stop asking!&lt;br /&gt;From UX perspective is like accepting an explicit file upload/manipulation and while the file is being loaded into ram asking every 200Kb if the user would like to increase the memory allocation for that file ...&lt;br /&gt;&lt;img src="http://s3.amazonaws.com/ragefaces/4019c0bb4279608433b671092446b939.png" /&gt;&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;What If Every Web Page Asks For Space&lt;/h4&gt;Nothing, same is for "&lt;em&gt;what if every native app takes 4 gigs of space&lt;/em&gt;" ... either space is available or it's not possible ... is that easy ... but again, with an easy to access indicator and a limit that goes far beyond 50Mb the problem should not exist. User can clean the cache, or enable more space but it must be easy, as easy should be for web apps developers to understand the available space because if the device is full already, the 50 Mb limits is pointless in any case plus there are ways to trigger memory consumption behind the scene and fill up gigs of disk space/SSD ... once again, this ask on demand every time is an epic fail, imho.&lt;br /&gt;FYI, the behavior I am talking about is in iOS, where Android asks only once if the disk access is allowed, then it silently fails after we reach the 50Mb limit.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Native VS Web App&lt;/h4&gt;Every browser is based on a native web view or similar concept, which means every browser could expose anything. I would like to be able to record user voice via web, to decode it via audio tag, to create real time video chat, to replace all native applications and to forget Android, iOS, webOS, blackberry, Symbian, MeeGo, Windows, whatever SDK ... I want to leave the SDK power to much more complicated things and I would like to be able to do most basic things via browser, all those things that the user could do with native apps, performances a part.&lt;br /&gt;The gap between native and web app should be performances and nothing else indeed ... right now is: all possible nasty access to everything on native side, things that few users are rarely aware of, and almost no access to any functionality through the browser.&lt;br /&gt;No idea if Chrome OS solved this but if it did, I am pretty sure it did with in-house solution, same Windows 8 will do, and this is annoying at least until a jDevice library will come out able to make all these private API consistent across all platforms ... as summary, why Mobile Web App development has to be so hard is a complete mystery to me: is it about your own markets? Fine, then stop selling us your browser is promoting Standard Mobile Web development because this sounds, so far, like a big lie.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Patent Oriented Development&lt;/h3&gt;When I heard that Apple patented a slide to unlock the screen I did not feel like "&lt;em&gt;they are so advanced&lt;/em&gt;" ... I rather felt like "&lt;em&gt;is anyone trying to patent my finger&lt;/em&gt;" ?&lt;br /&gt;I move horizontally my thumb since ever and nowadays I know there is a patent for that and this is bad.&lt;br /&gt;A natural movement should never be patented ... the graphic used to guide the movement could eventually be a patent but the way I do things not.&lt;br /&gt;I don't want a patent to hold a fork, I don't want a patent for the position I use to sleep in a mattress, whatever weird sofa, or a chair, I don't want to do unnatural movements to unlock a touch screen.&lt;br /&gt;What the hell is going on here ... if I use my nose to unlock my old android device I don't have to pay the patent indirectly, right?&lt;br /&gt;Is this what is patent about? Yes, it is.&lt;br /&gt;Patents are about intellectual property of whatever but the problem is that patents are expensive, are not necessarily predictable, and all these patents are doing is to block future development on top of it, unless is not the same company.&lt;br /&gt;Patents are a sort of creativity barrier because if a company invents a generic something, nobody will even try to improve that invention due basic patent behind the original.&lt;br /&gt;Example, I use my right hand to hold the phone and when I am talking with someone I put my right thumb on the right side of the phone.&lt;br /&gt;If there is a button there, it's annoying, while if I have to swipe from left to right ... well, it's still annoying.&lt;br /&gt;Will I ever implement a swiping gesture from right to left to unlock the screen because usually the way I hold the phone is with my right finger on the right side and it's more convenient to me to swipe the other way round as it is convenient for all left hand users? Nope, I don't even want to remember that thing exist, I have to create something completely new being careful that what I am doing does not touch the other patent ... cool, uh?&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Hardware Patents&lt;/h4&gt;Same concept could be applied for hardware ... was that thing perfect? Yes, I pay the patent. Was that thing not perfect? No, I have to create something new ... even if based on laser(disc), the reason we all waited so much for new standards after the CD.&lt;br /&gt;This happened with Compact Discs, and it brought us DVD first and Blu Ray after. In the meanwhile, another standard better than CDs but a bit less capable than Blu Ray died ... fair enough, we have new hardware for all these technologies but how comes in the hardware field the patent problem is not so strong as it is for the Software one?&lt;br /&gt;3D TV, all vendors are making one, as well as CD players, DVD players, and Blu Ray players ... nobody cares about patents here, at least not the way we all do when it comes to Software.&lt;br /&gt;I don't have any answer for this but I believe patents should be re-evaluated in their meaning because in the fastest field ever, as technology/software is, something that last for 10 years is too much and price to pay is too much as well as too much is the time between the patent pending and the patent applied status.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;ES6 Focus&lt;/h3&gt;I have talked about this as well ... it's about what's truly needed today, at least in the Mobile Web Development, and the JavaScript.Next focus, often completely abstract over not-so-needed topics as syntax sugar and boring classes.&lt;br /&gt;iOS5 brought massive performances boost to all Apple devices but even having the fastest and complete browser out there, Safari Mobile cannot do miracles when it comes to performances.&lt;br /&gt;The side effect of not having performances oriented techniques in JavaScript and DOM world is that average web developers are not able to create cool stuff without draining the battery or being slightly fast only with most recent mobile devices.&lt;br /&gt;The need for performances in this Mobile era should be priority number one for W3C and a possible ES 5.2 milestone, after that take even 5 years to improve syntax with all sugar you want, if necessary, at least we can push Mobile Web Development to its limit in the meanwhile while many new proposals won't bring anything interesting, as far as I can read, performances speaking.&lt;br /&gt;We can deal with the fact protected and private variables are absent or different in JS, what we cannot deal with anymore is that a proper and fast 3D API is not available, that Parallels are not available, that WebWorkers are useless when it comes to move data back and forward, that postMessage requires a window.open which require a click which is too slow but cannot be faked ontouchend or window.open won't work anymore because not explicit ... that IndexedDB does not provide native way to join data and speed up queries, that DOM manipulation is slow, that we don't control repaints and/or reflows, that binary Arrays are still slow, that Structs like classes/objects are missing, that CSS3 is bringing logic in the view with lack of control ... etc etc ... &lt;br /&gt;I don't care if Proxy are in the browser, if these are 2X slower than good old JS on mobile, you know what I mean? We need more performances now and more APIs finalized to have access to hardware layers only SDK can expose without granting any better usage than an experienced web developer.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;WebGL Partial Fail&lt;/h3&gt;First of all this is not yet a standard, regardless the effort of the kronos group, which means browsers like Internet Explorer will never adopt this ... fair enough if we can shim through Silverlight but here comes the second point: WebGL, as well as Silverlight, are not available for mobile.&lt;br /&gt;Apple exposed it for Adds only, where adds are most likely those responsible for bad Web performances, generally speaking, due massive usage of Flash or arguable usage of automations to bring canvas Adds able to slow down all netbooks and tables out there .... congratulations, I'll never get this choices ... WebGL not for developers but for designers of adds only ... can I say brilliant?&lt;br /&gt;Too few mobile devices are exposing WebGL if not none of them while basically every mobile device has a GPU compatible with Open GL 2.0 ES&lt;br /&gt;Still experimental, true, and already available mainly for Chrome browser where Webkit, as well as Firefox, could do the same or truly similar. The direction WebGL is taking is not good at all and I can't wait to see cool demonstrations able to run with all WebGL capable browsers ... so far, not many of them ... and this is bad.&lt;br /&gt;Sony enabled WebGL in its latest version of Android, still about fragmentation, so I am expecting at least every other vendor to bring WebGL in our current devices already capable ... it was a massive fail to drop it for the whole 2011, cool things may have been experimented already on devices plus typed Arrays could have been used more even for non WebGL related tasks.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;CSS3 Partial Fail&lt;/h3&gt;As mentioned before, CSS3 are becoming the most messed part of the whole Web stack, mobile and/or desktop. Examples with &lt;em&gt;counters&lt;/em&gt; to change dynamically text via &lt;em&gt;:after&lt;/em&gt; selector ... is it just me? I mean ... dafuq is that?&lt;br /&gt;Internet Explorer dropped the most misunderstood proprietary feature as &lt;em&gt;expression&lt;/em&gt; was and webkit is introducing any sort of unmanageable logic inside CSS3? ... counters? webkitTransitionEnd withou webkitTransitionStart? No way to trigger properly transitions if not without asynchronous rendering? Lots of hacks to make them work cross platform with control through JS for something written in CSS?&lt;br /&gt;CSS3 is bringing MVC in Web world without the C and if we would like to create robust behaviors/interactions/applications that make sense, programming speaking, we should forget the case where the user has no JavaScript because CSS3 is becoming indirectly strongly dependent on JavaScript for many reasons ... why not bring standard DOM method to control states via JS, rather than control partially what is supposed to happen via CSS3 only? I don't get it, I have seen cool stuff, but I have not seen cool stuff adopted cross browser and I am not seeing cool stuff easy to handle via JS and/or vice-versa.&lt;br /&gt;CSS3 needs notification into the JS world or we gonna have Photoshop like power without tools to control what we are doing.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;I have more things to say, and more I forgot but I thought a rant on 2011 was needed at least to check, in one year, what happened, what improved, and what did not change at all.&lt;br /&gt;I hope all people that are doing hard work on daily basis to promote a better web won't take anything I wrote personal and will simply consider the point of view of somebody that works with all these things on daily basis so ... it's my personal feedback, on what I think should change ASAP and specially for mobile web development.&lt;br /&gt;&lt;br /&gt;Happy New Year Everybody&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-8892808504319268322?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/8892808504319268322/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=8892808504319268322' title='5 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/8892808504319268322'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/8892808504319268322'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/12/learning-from-2011.html' title='Learning From 2011'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>5</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-7083090361354753298</id><published>2011-12-21T18:31:00.005+01:00</published><updated>2011-12-21T19:29:08.670+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='performances'/><category scheme='http://www.blogger.com/atom/ns#' term='coercion'/><title type='text'>Coercion Performances</title><content type='html'>There are cases where JS coercion may be wanted/needed/necessary, at least logically speaking.&lt;br /&gt;&lt;br /&gt;A classic case is a list of primitives, e.g. strings, or numbers, and a check we would like to perform &lt;strong&gt;without creating a new function each time&lt;/strong&gt;.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// recycled function&lt;br /&gt;function alreadyThere(value) {&lt;br /&gt;  // wanted coercion, no cast needed&lt;br /&gt;  return value == this;&lt;br /&gt;  // shitty code, logically speaking&lt;br /&gt;  // one cast per iteration&lt;br /&gt;  return value === "" + this;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;var listOfNames = ["Me", "You", "Others"];&lt;br /&gt;&lt;br /&gt;// the pointless check&lt;br /&gt;listOfNames.some(&lt;br /&gt;  // the recycled callback&lt;br /&gt;  alreadyThere,&lt;br /&gt;  // the *passed as object* this&lt;br /&gt;  "You"&lt;br /&gt;); // will be true&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Now, for above specific case anyone would use an indexOf but this is not the point.&lt;br /&gt;The point is that in some case we may want to do more complicated stuff and compare the result with &lt;em&gt;this&lt;/em&gt;&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// know if word was already in the dictionary&lt;br /&gt;function alreadyThere(value) {&lt;br /&gt;  return value.toLowerCase() == this;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;// convert the check once per iteration&lt;br /&gt;listOfNames.some(&lt;br /&gt;  alreadyThere,&lt;br /&gt;  "yoU".toLowerCase()&lt;br /&gt;); // still true&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;It's About Optimizations&lt;/h3&gt;The whole point is to try to perform as less runtime computations as possible.&lt;br /&gt;Following this logic, we may decide to lower-case all items in the list once, and never again, but unfortunately this will require duplicated amount of RAM used per each collection.&lt;br /&gt;The &lt;em&gt;String#toLowerCase()&lt;/em&gt; is fast enough for a not so frequent check so why bother the RAM?&lt;br /&gt;The optimization is also to avoid &lt;em&gt;this.toLowerCase()&lt;/em&gt; per each entry of the dictionary.&lt;br /&gt;The concept here is again simple, avoid duplicated entries in a generic list of chars, but things may be similar with numbers.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Performances&lt;/h3&gt;I have created a &lt;a href="http://jsperf.com/some-coercion"&gt;specific test&lt;/a&gt; able to understand performances gap between &lt;em&gt;coercion&lt;/em&gt; and &lt;em&gt;cast per iteration&lt;/em&gt;.&lt;br /&gt;Surprising Google Chrome seems to be able to optimize in core once per iteration the cast, resulting almost twice as fast as competitors.&lt;br /&gt;Specially on mobile, the &lt;strong&gt;in core coercion&lt;/strong&gt; seems to be faster, sometimes almost twice as fast as the cast per iteration is.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;JIT Oriented Development ?&lt;/h3&gt;I believe we should code logically, rather than trust JIT optimization. What I mean is that performances test are always welcome but we all know that better logic and algorithms are always winning in therms of performances and maintainability. In this specific case, specially where mobiles suffer the most, I would never suggest to do the cast per iteration: first of all because only one engine seems to be able to optimize such cast, but we don't know if a more complex object/scenario would perform that well, secondly because if I see a cast per each loop iteration I start smelling laziness all over the place ... the boxing/unboxing has always been a well known problem performances speaking, so how can a developer approve a logic similar to &lt;em&gt;(String)alwaysSameObject&lt;/em&gt; per each iteration?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;Tools such JSLint should just do their business in these cases ... coercion is wanted/needed/logical, and unless every browser will show such gap in common tasks against coercion, I will rarely promote a cast per iteration ... and you know what? I believe that gap in Chrome, is a missed optimization in Chrome itself.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-7083090361354753298?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/7083090361354753298/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=7083090361354753298' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7083090361354753298'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7083090361354753298'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/12/coercion-performances.html' title='Coercion Performances'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-3643006474638852079</id><published>2011-12-13T21:13:00.021+01:00</published><updated>2011-12-14T08:40:16.372+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='ES6'/><category scheme='http://www.blogger.com/atom/ns#' term='__noSuchMethod__'/><category scheme='http://www.blogger.com/atom/ns#' term='proxy'/><title type='text'>Please, Give Us Back __noSuchMethod__ !</title><content type='html'>For those who don't know what &lt;a href="https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Object/NoSuchMethod"&gt;__noSuchMethod__&lt;/a&gt; is here the quick summary: it was a bloody handy non-standard method able to provide a fallback whenever we invoked an object method that did not exist.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var o = {};&lt;br /&gt;o.__noSuchMethod__(function (name, args) {&lt;br /&gt;    alert(name); // "iDoNotExist"&lt;br /&gt;    alert([].slice.call(args)); // 1,2,3&lt;br /&gt;});&lt;br /&gt;o.iDoNotExist(1, 2, 3); // will produce above alerts&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;A Bit Of Background&lt;/h3&gt;Well, if you are patient enough, you may consider to read this &lt;a href="https://mail.mozilla.org/pipermail/es-discuss/2010-October/011912.html"&gt;never-ending post&lt;/a&gt; in Mozilla mailing list.&lt;br /&gt;The reason that post is called &lt;strong&gt;Proxies: get+fn vs. invoke&lt;/strong&gt; is because &lt;a href="https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Proxy"&gt;Proxy&lt;/a&gt; supposes to be the new way to go able to bring us much more power than we probably ever need ... but hey, this is welcome, while what is not welcome, is that Proxy may not be implemented first, which means browsers vendors should have waited to remove &lt;em&gt;__noSuchMethod__&lt;/em&gt; 'cause right now we may not have a pseudo equivalent, and second, but surely not less important, , &lt;strong&gt;Proxy does not provide the same functionality&lt;/strong&gt;.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Minified Theory Against The Practice&lt;/h3&gt;The main argument from &lt;a href="https://twitter.com/BrendanEich"&gt;@BrendanEich&lt;/a&gt; is that JavaScript has properties only so that &lt;strong&gt;o.fn() is the equivalent of o.fn.apply(o)&lt;/strong&gt;.&lt;br /&gt;While this is true with any normal object, this is &lt;strong&gt;totally different with __noSuchMethod__&lt;/strong&gt;.&lt;br /&gt;The equivalent of &lt;em&gt;__noSuchMethod__&lt;/em&gt; for that operation, and behind the scene, is:&lt;ul&gt;&lt;li&gt;is there a property in &lt;em&gt;o&lt;/em&gt; or its &lt;em&gt;__proto__&lt;/em&gt; called &lt;em&gt;fn&lt;/em&gt; ?&lt;/li&gt;&lt;ul&gt;&lt;li&gt;&lt;strong&gt;yes&lt;/strong&gt;, proceed as usual as if it was &lt;em&gt;o.fn.call(o)&lt;/em&gt; and throw error if that property was not callable&lt;/li&gt;&lt;li&gt;&lt;strong&gt;no&lt;/strong&gt;, is there a &lt;em&gt;__noSuchMethod__&lt;/em&gt; callback to burn instead of throwing an error due undefined property?&lt;/li&gt;&lt;ul&gt;&lt;li&gt;&lt;strong&gt;yes&lt;/strong&gt;, perform the current operation: &lt;em&gt;nsm_callback.apply(o, arguments)&lt;/em&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;no&lt;/strong&gt;, throw an error since property was undefined and obviously not callable&lt;/li&gt;&lt;/ul&gt;&lt;/ul&gt;&lt;/ul&gt;Got it? The equivalent of &lt;em&gt;o.fn()&lt;/em&gt; in an environment where &lt;em&gt;__noSuchMethod__&lt;/em&gt; was supported is potentially different from &lt;em&gt;o.fn.apply(o)&lt;/em&gt; ... I am 100% sure Brendan knows this before and better than me and this is the reason I don't really get his strongest point.&lt;br /&gt;Once again, &lt;em&gt;o.fn()&lt;/em&gt; may be the equivalent of &lt;em&gt;nsm_callback.apply(o, arguments)&lt;/em&gt; and not &lt;em&gt;o.fn.apply(o)&lt;/em&gt;.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Inexistent Theory Against The Practice&lt;/h3&gt;If above "reason" was not enough, I have read even worst in the same thread. I am sorry guys, but sometimes you must be realistic and understand that if a developer does, as example, this:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// de-context fn from o and invoke it&lt;br /&gt;(o.fn)();&lt;br /&gt;&lt;br /&gt;// exact equivalent of&lt;br /&gt;var fn = o.fn; // GETTER, no invokation&lt;br /&gt;// and after ...&lt;br /&gt;fn()&lt;br /&gt;// this is a problem? we have same with missing bind then ...&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;rather than this:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// invoke fn through o as default context&lt;br /&gt;o.fn();&lt;br /&gt;// can we see the difference?&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;it means that developer has much bigger problems than &lt;em&gt;__noSuchMethod__&lt;/em&gt; inexistent &lt;em&gt;ambiguity&lt;/em&gt;, that developer does not even know that &lt;em&gt;__noSuchMethod__&lt;/em&gt; exist ... &lt;strong&gt;come on&lt;/strong&gt;!&lt;br /&gt;Going on and on, another point is that &lt;em&gt;get&lt;/em&gt; should be all we need to simulate the &lt;em&gt;__noSuchMethod__&lt;/em&gt; behavior through proxies ... but &lt;strong&gt;this is completely misleading&lt;/strong&gt;!&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;A Getter IS A Getter&lt;/h3&gt;Is that trivial ... if we access a generic object property we are doing nothing different from invoking a getter with such object as property context.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;o.whatever;&lt;br /&gt;// look for "whatever" property name in o&lt;br /&gt;// if found returns the "whatever" associated value&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;o.whatever.call&lt;br /&gt;// nothing change, THIS IS NOT AN INVOKE&lt;br /&gt;// look for "whatever" property name in o&lt;br /&gt;// if found returns the "whatever" associated value&lt;br /&gt;// since the value was a function, the call method is usable&lt;br /&gt;// if whatever was not defined, the call method won't exist&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Nobody should ever even consider to use property accessor and expect a &lt;em&gt;__noSuchMethod__&lt;/em&gt; behavior ... that property did not exist, what kind of &lt;em&gt;method&lt;/em&gt; would you expect to look for?&lt;br /&gt;&lt;strong&gt;call is a property of the Function.prototype&lt;/strong&gt; so following the accessor/getter logic, nothing is ambiguous here.&lt;br /&gt;Accordingly, lattest example is simply an &lt;strong&gt;inexistent mistake&lt;/strong&gt; that hopefully no developer would ever do ... but you know, shit happens, then we learn, then hopefully we don't repeat same shit.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Other Programming Languages&lt;/h3&gt;When it comes to PHP, they perfectly managed to make the behavior &lt;strong&gt;not ambiguous&lt;/strong&gt; through the &lt;em&gt;&lt;a href="http://php.net/manual/en/language.oop5.overloading.php"&gt;__call&lt;/a&gt;&lt;/em&gt; magic keyword in classes definition but no, we decided that in JavaScript we cannot even think to put an &lt;em&gt;invoke&lt;/em&gt; to make the life easier and completely NOT ambiguous for all of us ... do we?&lt;br /&gt;I still cannot understand where and what is the ambiguous part if we have an explicit invoke declaration ... maybe something a bit harder to solve behind the scene for these poor JS engines? It could be ... should we all limit JS because of this? I don't think so.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Think About Libraries APIs Migrations&lt;/h3&gt;I give you the most basic example, the most used JS library with a fake &lt;em&gt;getter&lt;/em&gt; and &lt;em&gt;setter&lt;/em&gt; behavior: &lt;strong&gt;jQuery&lt;/strong&gt;.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// jQuery simulation of getters and setters behaviors&lt;br /&gt;&lt;br /&gt;// the getter&lt;br /&gt;$("body").html(); // return string with content&lt;br /&gt;&lt;br /&gt;// the setter&lt;br /&gt;$("body").html("&lt;div&gt;whatever&lt;/div&gt;");&lt;br /&gt;// set the string with content&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;If you want, specially for chainability reasons through the simulated setter, the fact &lt;em&gt;html&lt;/em&gt; is a method is convenient for the library but this library is stuck forever behind these two methods.&lt;br /&gt;jQuery, at current ECMAScript status, &lt;strong&gt;will never be able to switch gradually to real getters and setters&lt;/strong&gt; ... why that? A simple example:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;$("body").html; // returns the string in jQuery 3000&lt;br /&gt;&lt;br /&gt;$("body").html(); // shows a "deprecated warning"&lt;br /&gt;// ... and returns the "html" getter&lt;br /&gt;&lt;br /&gt;// implementation example&lt;br /&gt;function setInnerHTML(node) {&lt;br /&gt;  node.innerHTML = this;&lt;br /&gt;}&lt;br /&gt;Object.defineProperty($.fn, "html", {&lt;br /&gt;  get: function () {&lt;br /&gt;    return this[0].innerHTML;&lt;br /&gt;  },&lt;br /&gt;  set: function (html) {&lt;br /&gt;    this.each(setInnerHTML, html);&lt;br /&gt;  }&lt;br /&gt;});&lt;br /&gt;&lt;br /&gt;// the deprecation warning&lt;br /&gt;$.fn.__noSuchMethod__(function (property, args) {&lt;br /&gt;  if (property in this) {&lt;br /&gt;    console.log("Warning: " + property + " is not a method anymore");&lt;br /&gt;    if (args.length) {&lt;br /&gt;      // invoke the setter&lt;br /&gt;      this[property] = args[0];&lt;br /&gt;      // preserve behavior&lt;br /&gt;      return this;&lt;br /&gt;    } else {&lt;br /&gt;      // invoke the getter&lt;br /&gt;      return this[property];&lt;br /&gt;    }&lt;br /&gt;  } else {&lt;br /&gt;    throw "Y U NO READ DOCUMENTATION";&lt;br /&gt;  }&lt;br /&gt;});&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;That's it, we can migrate from two different APIs implementing getters and setters whenever we had a similar behavior and bringing gracefully users to the new usage ... no wa can't!&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;It Is Not About jQuery&lt;/h3&gt;I don't even use jQuery so don't get me wrong, this is not my battle here ... the point is that for another private project I am working on I would like to educate developers to use properties correctly but I understand developers may already got use to invoke methods as if it is normal, even when they are simply looking for a getter behavior.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var o = {&lt;br /&gt;  whatever:"cool bro",&lt;br /&gt;  __noSuchMethod__: function (property, args) {&lt;br /&gt;    console.log("we got a bro-blem here, " +&lt;br /&gt;      "don't invoke if you want a getter");&lt;br /&gt;    return this[property];&lt;br /&gt;  }&lt;br /&gt;};&lt;br /&gt;&lt;br /&gt;// so that &lt;br /&gt;o.whatever === o.whatever();&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Secially last line of code is apparently impossible to reproduce with Proxies, those that suppose to be the new and best way to go, those that give us control on things rarely needed until now, those that made JS.Next group decide that &lt;em&gt;__noSuchMethod__&lt;/em&gt; was evil and it had to be abandoned.&lt;br /&gt;I really hope that JS.Next will not be &lt;em&gt;non-developer expectations behaviors driven&lt;/em&gt; because guys, somebody tries to do cool things with this cool language, and if the reason you drop something is because &lt;em&gt;we are all morons&lt;/em&gt;, as example misunderstanding the difference of a referenced property through parenthesis  ... oh well ...  good luck kkfuture JavaScript ...&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;How To Solve This&lt;/h3&gt;Please put an &lt;strong&gt;invoke&lt;/strong&gt; or even better an &lt;strong&gt;invokeProperty&lt;/strong&gt;, preserving &lt;em&gt;invoke&lt;/em&gt; for when the object itself is used as if it was callable, in the current Proxy specifications so that who knows what is doing, can keep doing it and who never even bothered with this stuff, won't be affected at all.&lt;br /&gt;Thank you for listening.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-3643006474638852079?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/3643006474638852079/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=3643006474638852079' title='16 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/3643006474638852079'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/3643006474638852079'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/12/please-give-us-back-nosuchmethod.html' title='Please, Give Us Back __noSuchMethod__ !'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>16</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-1021140272600815513</id><published>2011-12-12T19:19:00.012+01:00</published><updated>2011-12-12T22:07:30.323+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='process'/><category scheme='http://www.blogger.com/atom/ns#' term='build'/><category scheme='http://www.blogger.com/atom/ns#' term='structure'/><category scheme='http://www.blogger.com/atom/ns#' term='minification'/><category scheme='http://www.blogger.com/atom/ns#' term='Builder'/><title type='text'>Create a JS builder with node.js</title><content type='html'>A very good and common practice with JS projects bigger than 100 lines of code is to split code in different files.&lt;br /&gt;Benefits are clear:&lt;ul&gt;&lt;li&gt;smaller pieces of code to maintain&lt;br /&gt;&lt;/li&gt;&lt;li&gt;swappable portions for experiments and/or improvements or new features, as example including for a build &lt;em&gt;magic2.js&lt;/em&gt; and get it, rather than change drastically &lt;em&gt;magic.js&lt;/em&gt; and follow the repository logs&lt;/li&gt;&lt;li&gt;better organization of the code, and I'll come back on this in this post&lt;/li&gt;&lt;li&gt;possibility to distribute bigger closures, as example the jQuery approach&lt;/li&gt;&lt;li&gt;create ad hoc builds including or excluding portion of the library, specially suitable for specific version of the code that must be compatible with IE only&lt;/li&gt;&lt;/ul&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Solutions All Over The Place&lt;/h3&gt;There are really tons of solutions able to make the described build process easy to use and easy to go. As example, I have created my own one and I am using it with basically every project I am working with: the &lt;a href="http://code.google.com/p/javascript-builder/"&gt;JavaScript Builder&lt;/a&gt;.&lt;br /&gt;However, this builder requires a couple of extra technologies such Python and Java ... but aren't we using simply JavaScript?&lt;br /&gt;So why not an easy to create guide on &lt;em&gt;how to build your code via JS only&lt;/em&gt;?&lt;br /&gt;This is what this post is about, and I hope you'll find useful.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;How To Structure Your Project&lt;/h3&gt;If all files are in the same directory is not easy to find the right file immediately since these could be many. A good solution I came up with is &lt;em&gt;folder related structure with both namespaces and private keywords paths&lt;/em&gt;.&lt;br /&gt;Here an example on how I would structure this library ( and please ignore the library itself )&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var myLib = (function (global, undefined) {"use strict";&lt;br /&gt;&lt;br /&gt;  // private scope function&lt;br /&gt;  function query(selector) {&lt;br /&gt;    return document.querySelectorAll(selector);&lt;br /&gt;  }&lt;br /&gt;&lt;br /&gt;  function Wrapper(nodeList) {&lt;br /&gt;    this.length = nodeList.length;&lt;br /&gt;    this._list = nodeList;&lt;br /&gt;  }&lt;br /&gt;&lt;br /&gt;  // a prototype method of the Wrapper "class"&lt;br /&gt;  Wrapper.prototype.item = function item(i) {&lt;br /&gt;    return this._list[i];&lt;br /&gt;  };&lt;br /&gt;&lt;br /&gt;  // public static query method&lt;br /&gt;  query.asWrapper = function (selector) {&lt;br /&gt;    return new Wrapper(query(selector));&lt;br /&gt;  };&lt;br /&gt;&lt;br /&gt;  var // private scope variables&lt;br /&gt;    document = global.document,&lt;br /&gt;    slice = [].slice&lt;br /&gt;  ;&lt;br /&gt;&lt;br /&gt;  // the actual object/namespace&lt;br /&gt;  return {&lt;br /&gt;    query: query,&lt;br /&gt;    internals: {&lt;br /&gt;      Wrapper: Wrapper&lt;br /&gt;    }&lt;br /&gt;  };&lt;br /&gt;&lt;br /&gt;}(this));&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The code should be easy enough to understand. The object used as namespace for &lt;em&gt;myLib&lt;/em&gt; has a couple of methods, few private variables and functions and something exposed through the &lt;em&gt;internals&lt;/em&gt; namespace.&lt;br /&gt;It does not matter what the library does or how good/badly is structured, what matters is that our folder structure should be smart enough to be able to scale with any sort of allowed JS pattern ... OK?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Folder&lt;/h3&gt;Well, to start with, let's say our source code should be inside an &lt;em&gt;src&lt;/em&gt; folder so we can add other folders for tests or builds beside in the same hierarchy.&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;dist&lt;br /&gt;src&lt;br /&gt;tests&lt;br /&gt;builder.js&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;We'll see the builder.js later, in the meanwhile, let's have a look into the src folder:&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;dist&lt;br /&gt;src&lt;br /&gt;    intro.js&lt;br /&gt;    outro.js&lt;br /&gt;    var.js&lt;br /&gt;    function&lt;br /&gt;        Wrapper.js&lt;br /&gt;        query.js&lt;br /&gt;        Wrapper&lt;br /&gt;            prototype&lt;br /&gt;                item.js&lt;br /&gt;        query&lt;br /&gt;            asWrapper.js&lt;br /&gt;tests&lt;br /&gt;builder.js&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The distinction will be much cleaner once you read above list through your editor or even your shell ... query and files are well distributed but bear in mind this is only the first example.&lt;br /&gt;Let's see what we are going to write into each file ?&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;src/intro.js&lt;/strong&gt;&lt;pre class="code"&gt;&lt;br /&gt;var myLib = (function (global, undefined) {"use strict";&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;src/function/query.js&lt;/strong&gt;&lt;pre class="code"&gt;&lt;br /&gt;  // private scope function&lt;br /&gt;  function query(selector) {&lt;br /&gt;    return document.querySelectorAll(selector);&lt;br /&gt;  }&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;src/function/Wrapper.js&lt;/strong&gt;&lt;pre class="code"&gt;&lt;br /&gt;  function Wrapper(nodeList) {&lt;br /&gt;    this.length = nodeList.length;&lt;br /&gt;    this._list = nodeList;&lt;br /&gt;  }&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;src/function/Wrapper/prototype/item.js&lt;/strong&gt;&lt;pre class="code"&gt;&lt;br /&gt;  // a prototype method of the Wrapper "class"&lt;br /&gt;  Wrapper.prototype.item = function item(i) {&lt;br /&gt;    return this._list[i];&lt;br /&gt;  };&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;src/function/query/asWrapper.js&lt;/strong&gt;&lt;pre class="code"&gt;&lt;br /&gt;  // public static query method&lt;br /&gt;  query.asWrapper = function (selector) {&lt;br /&gt;    return new Wrapper(query(selector));&lt;br /&gt;  };&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;src/var.js&lt;/strong&gt;&lt;pre class="code"&gt;&lt;br /&gt;  var // private scope variables&lt;br /&gt;    document = global.document,&lt;br /&gt;    slice = [].slice&lt;br /&gt;  ;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;src/outro.js&lt;/strong&gt;&lt;pre class="code"&gt;&lt;br /&gt;  // the actual object/namespace&lt;br /&gt;  return {&lt;br /&gt;    query: query,&lt;br /&gt;    internals: {&lt;br /&gt;      Wrapper: Wrapper&lt;br /&gt;    }&lt;br /&gt;  };&lt;br /&gt;&lt;br /&gt;}(this));&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Got it?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Structure Rules&lt;/h3&gt;&lt;ul&gt;&lt;li&gt;every part of the scope can be distributed&lt;/li&gt;&lt;li&gt;each file can or cannot be compatible as stand alone with a parser because to test the library &lt;strong&gt;we need to build it first&lt;/strong&gt; ( eventually with automations )&lt;/li&gt;&lt;li&gt;function declarations should be included in a dedicated folder called &lt;em&gt;function&lt;/em&gt; accordingly with the nested level&lt;/li&gt;&lt;li&gt;var declaration &lt;strong&gt;per scope&lt;/strong&gt; could be included in a folder &lt;em&gt;var&lt;/em&gt; accordingly with the nested level. Do not create a var folder per each function where you define variables 'cause if you need it it means the function is too complex. Split it in sub task and do not define 100 variables per a single function: closures are the only exception.&lt;br /&gt;&lt;/li&gt;&lt;li&gt;nested closure must be named in order to be able to define nested closure structure following previous rules. Every minifier will be able to remove function expression names, included named closures, while not every developer would like to deeply understand the whole code to recognize why the nested closure was useful. A classic example is the inclusion inside our own closure of an external library that uses its own closure. in this case name that closure so you know were to look for the library inside your folder structure.&lt;/li&gt;&lt;li&gt;function prototypes should be placed inside a prototype folder, inside the function folder.&lt;br /&gt;&lt;strong&gt;We don't need to reassign an object when we want to pollute the function prototype&lt;/strong&gt; so please stop this awkward common practice ASAP: &lt;code&gt;MyFunction.prototype = { /* THIS IS WRONG */ }&lt;/code&gt; and use the already available prototype object defined by default in every ECMAScript standard and per each function declaration or expression.&lt;br /&gt;If your argument is that the code will be bigger, use the outer scoped variables definition to address the prototype once and reuse this reference within the prototype folder. This approach will make your life easier once you get use to work with structured and distributed JavaScript files.&lt;/li&gt;&lt;/ul&gt;&lt;br /&gt;Specially about last example, we could have set a shortcut to the Wrapper.prototype object in the &lt;em&gt;var.js&lt;/em&gt; file and reuse the reference inside Wrapper.&lt;br /&gt;The structured folders will always help you to find references in the library thanks to the lookup that you, as well as the code, have to do.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;    // in the var.js file&lt;br /&gt;    WrapperPrototype = Wrapper.prototype,&lt;br /&gt;&lt;br /&gt;    // in the Wrapper/prototype/item.js file&lt;br /&gt;    WrapperPrototype.item = function item(i) { ... };&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Order Partially Matters&lt;/h3&gt;In ECMAScript 3rd or higher edition &lt;strong&gt;function declarations are always available at the very beginning of the scope&lt;/strong&gt;. I really don't know why these are so much underrated in daily basis code ... the fact these are always available means we can reference their prototype at any moment in our code:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var internalProto = (function () {&lt;br /&gt;&lt;br /&gt;    // address any declaration made in this scope&lt;br /&gt;    var WhateverPrototype = Whatever.prototype;&lt;br /&gt;    return WhateverPrototype;&lt;br /&gt;&lt;br /&gt;    // even if defined after a return!!!&lt;br /&gt;    function Whatever() {}&lt;br /&gt;}());&lt;br /&gt;&lt;br /&gt;alert(internalProto); // [object Object]&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Now, the above code is simply a demonstration about how function declarations work ... &lt;strong&gt;I am not suggesting a return in the middle, and declarations after&lt;/strong&gt;, all I am saying is that the order of things in JavaScript may not be relevant, and function declarations are a perfect example.&lt;br /&gt;Another example is the usage of variables ... if a function, as declaration or as expression, reference a variable defined in the outer scope &lt;strong&gt;nothing will break&lt;/strong&gt; unless we are invoking that function before the referenced variable has been defined.&lt;br /&gt;&lt;br /&gt;This are really &lt;strong&gt;ABC concepts&lt;/strong&gt; we all should know about JS before even claiming that we know JavaScript ... OK?&lt;br /&gt;Is really important to get these points because to simplify ASAP the builder file we need to rely in these assumptions.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The builder.js File&lt;/h3&gt;It's time to create the magic file that will do the job for us in possibly a smart way so that we can cover all edge cases we could think of.&lt;br /&gt;This is the content of &lt;strong&gt;builder.js&lt;/strong&gt; file, in the root of our project&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// @name        builder.js&lt;br /&gt;// @author      Andrea Giammarchi&lt;br /&gt;// @license     Mit Style License&lt;br /&gt;&lt;br /&gt;// list of files to include&lt;br /&gt;var&lt;br /&gt;  scriptName = "myLib", // the namespace/object.project name&lt;br /&gt;  fileList = [&lt;br /&gt;    "intro.js",    // beginning of the closure&lt;br /&gt;    "var.js",      // all declared variables&lt;br /&gt;    "function/*",  // all declared functions&lt;br /&gt;    "function/Wrapper/prototype/*", // all methods&lt;br /&gt;    "function/query/*", // all public statics&lt;br /&gt;    "outro.js"     // end of the library&lt;br /&gt;  ],&lt;br /&gt;  fs = require("fs"),  // file system module&lt;br /&gt;  out = [],            // output&lt;br /&gt;  alreadyParsed = []   // parsed files for visual feedback&lt;br /&gt;;&lt;br /&gt;&lt;br /&gt;// per each file in the list ...&lt;br /&gt;fileList.forEach(function addFile(file) {&lt;br /&gt;  // if the file contains a wild char ...&lt;br /&gt;  if (file.charAt(file.length - 1) == "*") {&lt;br /&gt;    // read the directory and per each file found there ..&lt;br /&gt;    fs.readdirSync(&lt;br /&gt;      __dirname + "/src/" + file.slice(0, -2)&lt;br /&gt;    ).forEach(function (file) {&lt;br /&gt;      // if the file type is js&lt;br /&gt;      // and the file has not been defined explicitly&lt;br /&gt;      // in the original list&lt;br /&gt;      if (&lt;br /&gt;        file.slice(-3) == ".js" &amp;&amp;&lt;br /&gt;        fileList.indexOf(file) &lt; 0&lt;br /&gt;      ) {&lt;br /&gt;        // call this same function providing the whole path&lt;br /&gt;        addFile(this + file);&lt;br /&gt;      }&lt;br /&gt;       // the path is passed as context to simplify the logic&lt;br /&gt;    }, file.slice(0, -1));&lt;br /&gt;  // if the file has not been included yet&lt;br /&gt;  } else if (alreadyParsed.indexOf(file) &lt; 0){&lt;br /&gt;    // put it into the list of already included files&lt;br /&gt;    alreadyParsed.push(file);&lt;br /&gt;    // add the file content to the output&lt;br /&gt;    out.push(fs.readFileSync(__dirname + "/src/" + file));&lt;br /&gt;  } else {&lt;br /&gt;    // if here, we are messing up with inclusion order&lt;br /&gt;    // or files ... it's a nice to know in console&lt;br /&gt;    try {&lt;br /&gt;      console.log("duplicated entry: " + file);&lt;br /&gt;    } catch(e) {&lt;br /&gt;      // shenanigans&lt;br /&gt;    }&lt;br /&gt;  }&lt;br /&gt;});&lt;br /&gt;&lt;br /&gt;// put all ordered content into the destination file inside the dist folder&lt;br /&gt;fs.writeFileSync(__dirname + "/dist/" + scriptName + ".js", out.join("\n"));&lt;br /&gt;&lt;br /&gt;// that's it&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The reason there are so many checks if a wild char is encountered is quite simple ... the order may not matter but in some case the order matters.&lt;br /&gt;If as example a prototype property is used runtime to define other prototype methods or properties, this cannot be pushed in the output randomly but at the very beginning, example&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// src/function/Wrapper/prototype/behavior.js&lt;br /&gt;WrapperPrototype.behavior = "forEach" in [];&lt;br /&gt;&lt;br /&gt;// src/function/Wrapper/prototype/forEach.js&lt;br /&gt;WrapperPrototype.forEach = WrapperPrototype.behavior ?&lt;br /&gt;  function (callback) {[].forEach.call(this._list, callback, this)} :&lt;br /&gt;  function (callback) { /* a shim for non ES5 compatible browsers */ }&lt;br /&gt;;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Being file 2 strongly dependent on file 1, the list of files could be written as this:&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;  fileList = [&lt;br /&gt;    "intro.js",    // beginning of the closure&lt;br /&gt;    "var.js",      // all declared variables&lt;br /&gt;    "function/*",  // all declared functions&lt;br /&gt;    "function/Wrapper/prototype/behavior.js", // precedence&lt;br /&gt;    "function/Wrapper/prototype/*", // all methods&lt;br /&gt;    "function/query/*", // all public statics&lt;br /&gt;    "outro.js"     // end of the library&lt;br /&gt;  ],&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;When the wild char will be encountered and the behavior passed to the forEach, this will be simply ignored since it has been pushed already in the previous call.&lt;br /&gt;Same concept could happen if a specific file must be parsed runtime at the end:&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;  fileList = [&lt;br /&gt;    "function/Wrapper/prototype/behavior.js", // precedence&lt;br /&gt;    "function/Wrapper/prototype/*", // all methods&lt;br /&gt;    "function/Wrapper/prototype/doStuff.js" // after all&lt;br /&gt;  ],&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;I believe these are already edge cases most of the time but at least now we can better understand what the builder will do.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;How To Use The Builder&lt;/h3&gt;In console, inside the project folder where the &lt;em&gt;builder.js&lt;/em&gt; is:&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;node builder.js&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;That's pretty much it ... if you try to open &lt;em&gt;dist/myLib.js&lt;/em&gt; after above call you will find your beautiful library all in one piece and ready to be minified, debugged, and tested.&lt;br /&gt;If the process does not take long time you may bind the builder to the &lt;em&gt;Constrol+S&lt;/em&gt; action with a potential sentinel able to inform you if any problem occurred, as example checking if the output has been polluted with some redundant file logged through the process.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;All these techniques may be handy for many reasons. First of all it's always good to maintain a structure, rather than a single file with thousands of lines of code, and secondly once we understand how the process work, nothing can stop us to improve, change, make it ad-hoc for anything we may need such regular expressions to strip out some code before the output push or whatever else could come up for some reason at some point.&lt;br /&gt;&lt;strong&gt;The minification&lt;/strong&gt; can be done the way you prefer, as example adding this single line of code at the end of the process assuming you have a &lt;em&gt;jar&lt;/em&gt; folder with, as example, google closure compiler.&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;require('child_process').exec(&lt;br /&gt;  ['java -jar "',&lt;br /&gt;    __dirname + "/jar/compiler.jar",&lt;br /&gt;  '" --compilation_level=SIMPLE_OPTIMIZATIONS --language_in ECMASCRIPT5_STRICT --js "',&lt;br /&gt;    __dirname + "/dist/" + scriptName + ".js",&lt;br /&gt;  '" --js_output_file "',&lt;br /&gt;    __dirname + "/dist/" + scriptName + ".min.js",&lt;br /&gt;  '"'].join(""),&lt;br /&gt;  function (error, stdout, stderr) {&lt;br /&gt;    if (error) console.log(stderr);&lt;br /&gt;  }&lt;br /&gt;);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Enjoy your new builder :)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-1021140272600815513?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/1021140272600815513/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=1021140272600815513' title='18 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/1021140272600815513'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/1021140272600815513'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/12/create-js-builder-with-nodejs.html' title='Create a JS builder with node.js'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>18</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-4048523001362663624</id><published>2011-12-06T01:30:00.006+01:00</published><updated>2011-12-06T02:27:08.324+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JSON'/><category scheme='http://www.blogger.com/atom/ns#' term='comments'/><title type='text'>On JSON Comments</title><content type='html'>Another active exchange with &lt;a href="https://twitter.com/getify"&gt;@getify&lt;/a&gt; about &lt;a href="http://bettween.com/webreflection/getify"&gt;JSON comments&lt;/a&gt; and here my take because tweets are cool but sometimes is hard to tell everything you think in 140 bytes ...&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Kyle Facts&lt;/h3&gt;JSON is used on daily basis for billion of things and configuration files are one, surely common, way to use JSON ( just think about npm packages for node.js ).&lt;br /&gt;His frustration about the fact JSON does not allow comments is comprehensible, and he even created an online petition about &lt;a href="http://52r.geti.fi/json-comments/petition"&gt;allowing comments in JSON specs&lt;/a&gt; ... but are comments really what we need?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Just A Side Effect&lt;/h3&gt;JSON is extremely attractive as standard, first of all because it's available and widely adopted by basically any programming language in this world, even those that never had to deal with a single JavaScript interlocutor, secondly because it's both simple to parse, and easy to read for humans.&lt;br /&gt;After all, what can be so wrong about comments inside such common serialization standard?&lt;br /&gt;Aren't comments just as easy to parse as white spaces?&lt;br /&gt;The problem is, in my opinion, that we are mixing up an easy process to serialize data, much easier compared to what PHP &lt;em&gt;serialize&lt;/em&gt; and &lt;em&gt;unserialize&lt;/em&gt; functions do, with the possibility to describe it.&lt;br /&gt;I have always seen JSON as a protocol, rather than a &lt;a href="http://yaml.org/"&gt;YAML&lt;/a&gt; substitute, and as a protocol I expect to be as compact as possible and as cross platform as possible.&lt;br /&gt;Specially about the latter point:&lt;br /&gt;&lt;blockquote cite="getify"&gt;&lt;a href="https://twitter.com/#!/getify/status/143847951993806848"&gt;that's annoying to port to every single language&lt;/a&gt;&lt;/blockquote&gt;Precisely, what we should understand is that if JSON became so popular without needing comments, maybe the fact today we would like to use it as a "&lt;i&gt;descriptive markup&lt;/i&gt;" does not reflect anymore the success, the adoption, and possibilities this standard brought to all these languages?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Improve The Standard&lt;/h3&gt;Thanks gosh software is not always stuck behind immutable standards or patents ... and neither is JSON.&lt;br /&gt;If the need for comments is such big topic, define another standard able to combine the good old one with a new one.&lt;br /&gt;If this new standard is truly what developers need, every JSON implementor will spend few hours to test and optimize the well defined standard in order to accept comments, isn't it?&lt;br /&gt;I mean ... &lt;a href="http://www.ietf.org/rfc/rfc4627.txt"&gt;RFC 4627&lt;/a&gt; was not meant to be the final solution, that was a Crockford proposal universally adopted.&lt;br /&gt;To create a new standard able to extend RFC 4627 should not be a big problem ... or maybe ...&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;JSON Is Not A JavaScript Thing&lt;/h3&gt;The JSON serialization looks just like JavaScript ... but not JavaScript only.&lt;br /&gt;Other programming languages use curly brackets and squared brackets to define lists and objects ( Python and others ) ... the fact JSON has been accepted so well is probably because the design of the format was indeed already widely adopted, it was not a JS thing, and never should be.&lt;br /&gt;What's the deal here, is define a standard for JSON comments.&lt;br /&gt;Let me better explain this point ... &lt;br /&gt;&lt;br /&gt;I am a JS developer and I edit my JSON files via my JS editor ... fair enough ... I want to communicate my data to a server side service, let's say Python.&lt;br /&gt;Python would like to be able to parse my data and produce a file compatible with ... Python, of course.&lt;br /&gt;Does it mean that Python at that point should keep comments in a JavaScript standard? And why that, since the format used to exchange data was already somehow evaluable via Python and right now not anymore due some double slash in the file?&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;# this is PYTHOOOOOOOOOON&lt;br /&gt;o = {"test": "data"}&lt;br /&gt;o.get("test") # data&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Will the renewed JSON work as well?&lt;br /&gt;&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;# still python&lt;br /&gt;o = {"test": "data"} // and some WTF&lt;br /&gt;o.get("test")&lt;br /&gt;&lt;br /&gt;&gt;&gt; SyntaxError: invalid syntax&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Well done ... making JSON with comments a JS thing python, as other languages, need extra effort to parse data.&lt;br /&gt;What will happen once Python uses the json library?&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;import json&lt;br /&gt;&lt;br /&gt;jsonh.loads(theReceivedData);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Should it print data with python compatible comments or with JS compatible comments so that data is not directly usable anymore for any python application, storing it as example in a file.py or a database ?&lt;br /&gt;And once the renewed JSON has been transformed into Python valid syntax, wouldn't this file not be usable anymore from all others programming languages due possible syntax errors ?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Not That Easy&lt;/h3&gt;I like JSON as it is, except few broken implementations quite common even on browsers, because it's about creating a bloody piece of text many other languages can understand basically on the fly.&lt;br /&gt;No need to remember which comment style has been saved with that version of JSON, no need to parse back and finally, no need to ask every single programming language that is using JSON as protocol to update their legacy ... that just worked, and it will aways work for what it was meant: transfer data, not transfer JS like code without functions and/or functions calls only ...&lt;br /&gt;What we are doing, we as JavaScript developer, is to abuse JSON as if it's a piece of our JS code, polluting today with comments, and who knows what else tomorrow.&lt;br /&gt;The right way to go, still in my opinion, would be, once again, to enrich, propose, create, a new standard that allows comments and why not, other features.&lt;br /&gt;As example, what I always found annoying is that in PHP we can unserialize preserving the class, so that we can serialize objects states ... where is this in JSON?&lt;br /&gt;Nowhere, indeed &lt;a href="http://webreflection.blogspot.com/2007/06/jsomon-json-evolution.html"&gt;I have spent in my past&lt;/a&gt; few hours &lt;a href="http://webreflection.blogspot.com/2010/04/json-sleep-wakeup-serialize-and.html"&gt;trying to enrich this protocol&lt;/a&gt; ... did it work? Was it interesting ? Probably not, except for my last attempt that is 100% based on current JSON and it's about optimizing bandwidth and performances ... that worked better, accordingly with &lt;a href="https://github.com/WebReflection/JSONH"&gt;JSONH github status&lt;/a&gt;, still I was not expecting every other that never had this problem to adopt that approach ... you know what I mean?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Still Valid JSON&lt;/h3&gt;If it's about writing comments, next snippet is perfectly valid JSON string. All we need to do is to use the replacer in a proper way:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;{&lt;br /&gt;  "@description": "something meaningful",&lt;br /&gt;   "property": "value",&lt;br /&gt;&lt;br /&gt;  "@description": "something else",&lt;br /&gt;  "other": "other value"&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;// parse above text via JSON&lt;br /&gt;console.log(JSON.parse(aboveText, function (key, value){&lt;br /&gt;  if (key.charAt(0) != "@")&lt;br /&gt;    return value;&lt;br /&gt;}));&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Here we are with our object, comments manually written on the original JSON, and every language able to parse them&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-4048523001362663624?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/4048523001362663624/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=4048523001362663624' title='5 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/4048523001362663624'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/4048523001362663624'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/12/on-json-comments.html' title='On JSON Comments'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>5</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-2603321261506692989</id><published>2011-11-30T20:28:00.015+01:00</published><updated>2011-11-30T22:05:22.702+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Array'/><category scheme='http://www.blogger.com/atom/ns#' term='Object'/><category scheme='http://www.blogger.com/atom/ns#' term='extras'/><category scheme='http://www.blogger.com/atom/ns#' term='prototype'/><title type='text'>Array extras and Objects</title><content type='html'>When &lt;a href="https://developer.mozilla.org/en/New_in_JavaScript_1.6"&gt;Array extras&lt;/a&gt; landed in JavaScript 1.6 I had, probably together with other developers, one of those &lt;em&gt;HOORRAYYY&lt;/em&gt; moment ...&lt;br /&gt;What many libraries and frameworks out there still implement, is this sort of universal &lt;em&gt;each&lt;/em&gt; method that supposes to be compatible with both Arrays and Objects.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;A Bit Messed Up&lt;/h3&gt;What I have never liked that much about these &lt;em&gt;each&lt;/em&gt; methods is that we have to know in advance in any case if the object we are passing is an Array, an ArrayLike one, or an Object.&lt;br /&gt;In latter case, the callback passed as second argument will receive as second argument &lt;em&gt;the key&lt;/em&gt;, and not &lt;em&gt;the index&lt;/em&gt;, which simply means we cannot trust a generic callback unless this does not check per each iterated item the second argument type, or unless we don't care at all about the second argument.&lt;br /&gt;In any case I always found this a bad design. If we think about events, as example, it's totally natural to expect a single argument as event object and then we can act accordingly.&lt;br /&gt;This let us reuse callbacks for similar purpose and maintain a &lt;abbr title="Don't Repeat Yourself"&gt;DRY&lt;/abbr&gt; code.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Need For An Object#forEach&lt;/h3&gt;All implementation of each, and as far as I know with the only exception of jQuery which makes things even more complicated since we generally have to completely ignore the first argument in this case, have some natural confusion inside the method.&lt;br /&gt;If you take the &lt;a href="http://documentcloud.github.com/underscore/"&gt;underscore.js&lt;/a&gt; library, as example, you will note that there are two aliases for the &lt;em&gt;each&lt;/em&gt; method, each itself and forEach, so it's more than clear for me that JS developers are clearly missing an &lt;em&gt;Array#forEach&lt;/em&gt; like method in order to iterate with objects, rather than lists.&lt;br /&gt;It must be also underlined that all these methods are somehow error prone: what if the object we are passing has a &lt;em&gt;length&lt;/em&gt; property that does not necessary mean it points to the length of items stored via index as if it was an Array?&lt;br /&gt;You may consider this an edge case, or an anti pattern, then you have to remember that &lt;em&gt;functions&lt;/em&gt; in JavaScript are first class objects.&lt;br /&gt;Probably all these methods will nicely fail indeed with functions, passed as objects, whenever you decide that your function can be used as object too.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var whyNot = function (obj) {&lt;br /&gt;  /* marvelous stuff here */&lt;br /&gt;  this.calls++;&lt;br /&gt;  return this.doStuff(obj);&lt;br /&gt;};&lt;br /&gt;whyNot.calls = 0;&lt;br /&gt;whyNot.doStuff = function (obj) {&lt;br /&gt;  /* kick-ass method */&lt;br /&gt;};&lt;br /&gt;&lt;br /&gt;// the unexpected but allowed&lt;br /&gt;whyNot = whyNot.bind(whyNot);&lt;br /&gt;&lt;br /&gt;whyNot.length; // 1&lt;br /&gt;whyNot[0];        // undefined&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;By design, the length of any function in JavaScript is &lt;em&gt;read-only&lt;/em&gt; and means nothing, in therms of Array iteration, it simply means the number of arguments the function defined during its declaration/definition as expression.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;WTF&lt;/h3&gt;Whenever above example makes sense or not, I am pros patterns exploration and when a common method is not compatible with all scenarios, I simply think something went wrong or is missing in the language.&lt;br /&gt;Thanks gosh JS is freaking flexible and with ES5 we can define some prototype without affecting &lt;em&gt;for( in )&lt;/em&gt; loops but hopefully simplifying our daily basis stuff.&lt;br /&gt;Remember? With underscore or others we still have to know in advance if the passed object is an Array, an ArrayLike, or a generic object ... so what would stop us to simply chose accordingly?&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// Array or ArrayLike&lt;br /&gt;[].forEach.call(genericArrayLike, callbackForArrays);&lt;br /&gt;&lt;br /&gt;// generic object to iterate&lt;br /&gt;{}.forEach.call(object, callbackForObjects);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;An explicit choice in above case is the fastest and most reliable way we have to do things properly. A DOM collection, as well as any array or arrayLike object will use the native forEach, but we can still recycle callbacks designed to deal with &lt;em&gt;value, key&lt;/em&gt; and objects, rather than &lt;em&gt;value, index&lt;/em&gt;, and this is the little experiment:&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Object extras&lt;/h3&gt;The concept of each callback is exactly the same of original, native, Array callbacks, except things are based on native functions available in all ES5 compatible desktop and basically all mobile browsers, and easy to shim with all others too old to deal with JS 1.6 or higher.&lt;br /&gt;&lt;br /&gt;&lt;script src="https://gist.github.com/1410420.js?file=Object.extra.js"&gt;&lt;/script&gt;&lt;br /&gt;&lt;br /&gt;Here a couple of examples:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var o = {a:"a", b:"b", c:""};&lt;br /&gt;&lt;br /&gt;// know if all values are strings&lt;br /&gt;o.every(function (value, key, object) {&lt;br /&gt;  return typeof value == "string";&lt;br /&gt;}); // true&lt;br /&gt;&lt;br /&gt;// filter by content, no empty strings&lt;br /&gt;var filtered = o.filter(function (value, key, object) {&lt;br /&gt;  return value.length;&lt;br /&gt;}); // {a:"a",b:"b"} // original object preserved&lt;br /&gt;&lt;br /&gt;// loop through all values (plus checks)&lt;br /&gt;o.forEach(function (value, key, object) {&lt;br /&gt;  object === o; // true&lt;br /&gt;  this === o;    // true&lt;br /&gt;  if (key.charAt(0) != "_") {&lt;br /&gt;    doSomethingWithThisValue(value);&lt;br /&gt;  }&lt;br /&gt;}, o); // NOTE: all these methods respect Array extras signatures&lt;br /&gt;&lt;br /&gt;// map a new object&lt;br /&gt;var mapped = o.map(function (value, key, object) {&lt;br /&gt;  return value + 1;&lt;br /&gt;}); // {a:"a1",b:"b1"} // original object preserved&lt;br /&gt;&lt;br /&gt;// know if a value contains "a"&lt;br /&gt;o.some(function (value, key, object) {&lt;br /&gt;  return value === "a";&lt;br /&gt;}); // true&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The reason &lt;em&gt;reduce&lt;/em&gt; and &lt;em&gt;reduceRight&lt;/em&gt; are not in the list is simple: which one would be the key to preserve, the first of the list? There is no such thing as "&lt;em&gt;predefined for/in order&lt;/em&gt;" in JavaScript plus these methods are more Array related so out of this experiment.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;Once minified and minzipped the gist weights about &lt;strong&gt;296 bytes&lt;/strong&gt; which is ridiculous size compared with any application we are dealing with on daily basis.&lt;br /&gt;Specially &lt;em&gt;forEach&lt;/em&gt;, but probably others too, may become extremely handy and ... of course, using the &lt;em&gt;Object.keys&lt;/em&gt; method internally, this is gonna be compatible with Arrays too but hey, the whole point was to make a clear distinction ;)&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;[edited]&lt;br /&gt;&lt;h3&gt;The Misleading Signature&lt;/h3&gt;I don't know how many times I have spoken with jQuery developers, just because they are common, convinced that native &lt;em&gt;Array#forEach&lt;/em&gt; was accepting the value as &lt;strong&gt;second&lt;/strong&gt; argument.&lt;br /&gt;I always considered inverted signatures, whatever API it is, bad for both performances, no possibility to fallback into some native method, and learning curve, where new comers learn than a generic &lt;em&gt;each&lt;/em&gt; method must have the index as first argument.&lt;br /&gt;Bear in mind whenever we loop we are most likely interested into the value of that index or key, so this value should be the first, and if you need the only one, argument passed through the procedure.&lt;br /&gt;A completely ignored first argument is, once again and in my opinion, a bad design for an API: stuck without native power, teaching arguments order is not relevant.&lt;br /&gt;Well, specially latter point is true if we have named arguments, but in JS nothing have been planned so far, and in ES6 the way we gonna name arguments is still under discussion.&lt;br /&gt;&lt;br /&gt;Have fun with JS&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-2603321261506692989?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/2603321261506692989/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=2603321261506692989' title='6 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/2603321261506692989'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/2603321261506692989'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/11/array-extras-and-objects.html' title='Array extras and Objects'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>6</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-7238362446865515823</id><published>2011-11-27T15:26:00.017+01:00</published><updated>2011-11-27T21:11:58.288+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='guide'/><category scheme='http://www.blogger.com/atom/ns#' term='style'/><title type='text'>About Felix's Style Guide</title><content type='html'>Style guides are good as long as these are meaningful and a bit "&lt;em&gt;open minded&lt;/em&gt;" because if one style is recognized as anti pattern then it must be possible to update/change it.&lt;br /&gt;&lt;br /&gt;The &lt;a href="http://nodeguide.com/style.html"&gt;Felix's Node.js Style Guide&lt;/a&gt; is surely a meaningful one, but I hope it's open minded too.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Why This Post&lt;/h3&gt;Because I write node.js code as well sometimes and I would like to write code accepted by the community. Since developers may go too religious about guides I don't want explain all these points per each present or future node.js module I gonna write ... I post it once, I will eventually update it, but it's here and I can simply point at this any time.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Style Guide Side Effect&lt;/h3&gt;As happened before with &lt;a href="http://javascript.crockford.com/code.html"&gt;the older one&lt;/a&gt; or &lt;a href="http://www.jslint.com/lint.html"&gt;the linter&lt;/a&gt;, a style guide may mislead developers and if they are too religious and unable to think about some point, the quality of the result code may be worse rather than better.&lt;br /&gt;I have talked about JSLint already too much in this blog so ... let's bring the topic in track and see what Felix may re-consider.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Quotes&lt;/h3&gt;Current status: &lt;em&gt;Use single quotes, unless you are writing JSON&lt;/em&gt;&lt;br /&gt;A common mistake for JavaScript developers, specially those with PHP, Ruby, or other scripting languages background, is to think that single quotes are different from double quotes ... sorry to destroy this myth guys but in JavaScript &lt;strong&gt;there is no difference between single and double quotes&lt;/strong&gt;.&lt;br /&gt;Once you get this, you must think that if by standard definition JSON uses double quotes there is no reason to prefer single quotes over double.&lt;br /&gt;What should this difference tell us, that one is JSON and one is JavaScript for node.js? Such assumption is a bit ridiculous to me since JSON &lt;strong&gt;is&lt;/strong&gt; JavaScript, nothing more, nothing less.&lt;br /&gt;More over, I am not a big fan of HTML strings inside JS files because of separation of concerns, and I'll come back on it, but in English, as well as in many other languages, the single quote inside a string is quite common, isn't it?&lt;br /&gt;Accordingly, are you really planning to prefer &lt;em&gt;'it\'s OK'&lt;/em&gt; over &lt;em&gt;"it's OK"&lt;/em&gt;?&lt;br /&gt;And if the suggested editor, in the guide itself, is one with supported syntax highlight, shouldn't we simply trust the highlighted string in order to recognize it, rather than distinguish between JSON and non JSON strings?&lt;br /&gt;Shouldn't we write comfortably without &lt;em&gt;silly rules&lt;/em&gt;, as Felix says in another point, so that we can chose whatever string delimiter we want accordingly with the content of the string?&lt;br /&gt;Last, but not least, for those convinced that in HTML there is any sort of difference between single and double quotes, I am sorry to, once again, destroy this myth since &lt;strong&gt;&lt;a href="http://www.w3.org/TR/html4/intro/sgmltut.html#h-3.2.2"&gt;there is no difference in HTML between quotes&lt;/a&gt;&lt;/strong&gt; ... so, once again, chose what you want and focus on something else than distinction between JSON and non JSON strings ...&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Variable declarations&lt;/h3&gt;Current status: &lt;em&gt;Declare one variable per var statement, it makes it easier to re-order the lines. Ignore Crockford on this, and put those declarations wherever they make sense.&lt;/em&gt;&lt;br /&gt;If there is one thing that I always agreed with Crockford is this one: &lt;strong&gt;variable declared at the beginning of the function&lt;/strong&gt;, with the exception for function declarations that should be before variable declarations, and not after.&lt;br /&gt;The reason is quite simple: wherever we declare a variable, this will be available at the very beginning of the scope so which place can be better than the beginning of the scope itself to instantly recognize all local scope variables rather than scrolling the whole closure 'till the end in order to find that name that completely screwed up the whole logic in the middle because is shadowing something else inside or outside the scope ?&lt;br /&gt;Is that easy, I don't want to read potentially thousands of lines of code to understand which variable has been defined where, I want a single bloody place to understand what is local and what is not.&lt;br /&gt;The only exception to this rule may be some temporary variable, as is the classic &lt;em&gt;i&lt;/em&gt; used in for loops, or some &lt;em&gt;tmp&lt;/em&gt; reference still common in for loops&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;// the exception ... in the middle of the code&lt;br /&gt;&lt;br /&gt;for (var i = 0, length = something.length, tmp; i &lt; length; ++i) {&lt;br /&gt;    tmp = something[i];&lt;br /&gt;    // do something meaningful &lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Chances that above loop will destroy our logic because of a shadowed &lt;em&gt;i&lt;/em&gt; or &lt;em&gt;tmp&lt;/em&gt; reference are really rare and we should use meaningful variables name.&lt;br /&gt;As summary, there are only advantages on declaring variables on top, and until we have no &lt;em&gt;let&lt;/em&gt; statements it is only risky, and dangerous for our business, to define variables in the wild.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// how you may write code&lt;br /&gt;(function () {&lt;br /&gt;  return true;&lt;br /&gt;  var inTheWild = 123;&lt;br /&gt;  function checkTheWild() {&lt;br /&gt;    return inTheWild === 123;&lt;br /&gt;  }&lt;br /&gt;}());&lt;br /&gt;&lt;br /&gt;// how JS works in any case&lt;br /&gt;(function () {&lt;br /&gt;&lt;br /&gt;  // function declarations instantly available in the scope&lt;br /&gt;  function checkTheWild() {&lt;br /&gt;    return inTheWild === 123;&lt;br /&gt;  }&lt;br /&gt;&lt;br /&gt;  // any var declaration instantly available as undefined&lt;br /&gt;  var inTheWild;&lt;br /&gt;&lt;br /&gt;  return true;&lt;br /&gt;&lt;br /&gt;  // no matters where/if we assign the value&lt;br /&gt;  // the inTheWild is already available everywhere&lt;br /&gt;  // with undefined as default value&lt;br /&gt;  // and before this assignment&lt;br /&gt;  inTheWild = 123;&lt;br /&gt;  &lt;br /&gt;  // shadows should be easy to track&lt;br /&gt;  // top of the function is the right place to track them&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Constants&lt;/h3&gt;Current status: &lt;em&gt;Constants should be declared as regular variables or static class properties, using all uppercase letters.&lt;br /&gt;&lt;br /&gt;Node.js / V8 actually supports mozilla's const extension, but unfortunately that cannot be applied to class members, nor is it part of any ECMA standard.&lt;/em&gt;&lt;br /&gt;I could not disagree more here ... the meaning of constant is something immutable and the reason we use constant is to believe these are immutable.&lt;br /&gt;Why on earth avoid a language feature when it provides exactly what we need? Don't we want more reliable code? And what about security?&lt;br /&gt;Neither in PHP we can &lt;a href="http://php.net/manual/en/function.define.php"&gt;define&lt;/a&gt; an object property and this does not mean we should avoid the usage of &lt;em&gt;define&lt;/em&gt; function, isn't it?&lt;br /&gt;Use &lt;em&gt;const&lt;/em&gt; as much as you want unless the code does not have to run cross platform ( browsers included ) and if you want to define constants with objects, use the JavaScript equivalent to do that.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;function define(object, property, value) {&lt;br /&gt;    Object.defineProperty(object, property, {&lt;br /&gt;        get: function () {&lt;br /&gt;            return value;&lt;br /&gt;        }&lt;br /&gt;        // if you really want to throw an error&lt;br /&gt;        // , set: function () {throw "unable to redefine " + property;}&lt;br /&gt;    });&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;var o = {};&lt;br /&gt;define(o, "TEST", 123);&lt;br /&gt;o.TEST = 456;&lt;br /&gt;o.TEST; // 123&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;I have personally proposed &lt;a href="http://webreflection.blogspot.com/2007/10/cow-javascript-define-php-like-function.html"&gt;cross platform ways to do the same&lt;/a&gt; without or &lt;a href="http://webreflection.blogspot.com/2011/10/objectprototypedefine-proposal.html"&gt;within objects themselves&lt;/a&gt;.&lt;br /&gt;As we can see there are many ways to define constants and if the argument is that const is not standard it's a weak one because nobody is planning to remove this keyword from V8 or SpiderMonkey, most likely every other browser will adopt this keyword in the future but if that won't happen, to find and replace it with &lt;em&gt;var&lt;/em&gt; only when necessary is a better way to go: security and features, we should encourage these things rather than ignore them, imho.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Equality operator&lt;/h3&gt;Current status: &lt;em&gt;Programming is not about remembering stupid rules. Use the triple equality operator as it will work just as expected.&lt;/em&gt;&lt;br /&gt;No it doesn't because coercion is not about equality only.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;alert("2" &lt; 3 &amp;&amp; 1 &lt; "2");&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Programming IS about remembering rules, that's the reason we need to know the syntax in order to code something ... right?&lt;br /&gt;&lt;strong&gt;Coercion must be understood rather than being ignored&lt;/strong&gt; and rules are pretty much simple and widely explained in the specs, &lt;a href="http://webreflection.blogspot.com/2010/10/javascript-coercion-demystified.html"&gt;even more simplified in this old post of mine&lt;/a&gt;.&lt;br /&gt;If any of you developers still do this idiotic check &lt;strong&gt;you are doing it wrong&lt;/strong&gt;.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// WRONG!!!!!!!!!!!!!&lt;br /&gt;arg === null || arg === undefined&lt;br /&gt;&lt;br /&gt;// THE SAFER EXACT EQUIVALENT&lt;br /&gt;arg == null&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;You should rather avoid &lt;em&gt;undefined&lt;/em&gt; equality in any piece of code you wrote, unless you did not create an undefined reference by yourself.&lt;br /&gt;As summary, a good developer does not ignore problems, a good developer understands them and only after decide which way is the best one.&lt;br /&gt;Felix is a good developer and he should promote deeper knowledge ... this specific point was really bad because it's like saying "&lt;em&gt;avoid regular expressions because you don't understand them and you don't want to learn them&lt;/em&gt;".&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Extending prototypes&lt;/h3&gt;Current status: &lt;em&gt;Do not extend the prototypes of any objects, especially native ones&lt;/em&gt;&lt;br /&gt;&lt;a href="http://perfectionkills.com/extending-built-in-native-objects-evil-or-not/"&gt;Read this article&lt;/a&gt; and stick an "&lt;em&gt;it depends&lt;/em&gt;" in your screen. Nobody wants to limit JS potentials and &lt;em&gt;Object.defineProperty/ies&lt;/em&gt; is a robust way to do things properly.&lt;br /&gt;Sure we must understand that even a method like &lt;em&gt;Array#empty&lt;/em&gt; could have different meanings ... e.g.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var arr = Array(3);&lt;br /&gt;// is arr empty ?&lt;br /&gt;// length is 3 but no index has been addressed&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;If we pollute native prototype we must agree on the meaning or we must prefix our extension so that nobody can complain if that empty was good enough or just a wrong concept.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// a meaningful Array#empty&lt;br /&gt;Object.defineProperty(Array.prototype, "empty", {&lt;br /&gt;  value: function empty() {&lt;br /&gt;    for (var i in this) return false;&lt;br /&gt;    return true;&lt;br /&gt;  }&lt;br /&gt;});&lt;br /&gt;&lt;br /&gt;alert([&lt;br /&gt;  [].empty(),       // true&lt;br /&gt;  Array(3).empty(), // true&lt;br /&gt;  [null].empty()    // false&lt;br /&gt;]);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Conditions&lt;/h3&gt;Current status: &lt;em&gt;Any non-trivial conditions should be assigned to a descriptive variable&lt;/em&gt;&lt;br /&gt;I often write empty condition on purpose and to both avoid superflous re-assignment and speed up the code.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// WRONG&lt;br /&gt;object.property = object.property || defaultValue;&lt;br /&gt;&lt;br /&gt;// better&lt;br /&gt;object.property || (object.property = defaultValue):&lt;br /&gt;&lt;br /&gt;// RIGHT&lt;br /&gt;"property" in object || (object.property = defaultValue);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Why on earth would I assign that ? Same I would not do it if the condition is not reused at least twice.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;if (done.something() &amp;&amp; done.succeed) {&lt;br /&gt;    // done.something() &amp;&amp; done.succeed useful&lt;br /&gt;    // here and nowhere else in the code&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Accordingly with the fact spread variable declarations are a bad practice, I cannot think about creating flags all over the place for these kind of &lt;em&gt;one shot&lt;/em&gt; checks.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Function length&lt;/h3&gt;Current status: &lt;em&gt;Keep your functions short. A good function fits on a slide that the people in the last row of a big room can comfortably read. So don't count on them having perfect vision and limit yourself to ~10 lines of code per function.&lt;/em&gt;&lt;br /&gt;I agree on this point but JavaScript is all about functions.&lt;br /&gt;I understand the &lt;em&gt;require&lt;/em&gt; approach does not need a closure to surround the whole module, being this already somehow sandboxed, but cross platform code and private functions or variables are really common in JS so that a module may be entirely written inside a closure.&lt;br /&gt;A closure is a function so as long as this point is flexible is fine to me, also as long as the code is still readable and elegant ... I can already imagine developers writing &lt;strong&gt;10 lines of functions using all 80 characters per line&lt;/strong&gt; in order to respect this point ...&lt;br /&gt;&lt;br /&gt;&lt;img style="border:0" src="http://s3.amazonaws.com/ragefaces/fed47e7ffa874d01b771474d2eef1a60.png" width="320" /&gt;&lt;br /&gt;&lt;br /&gt;... now, that would be lame.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Object.freeze, Object.preventExtensions, Object.seal, with, eval&lt;/h3&gt;Current status: &lt;em&gt;Crazy shit that you will probably never need. Stay away from it.&lt;/em&gt;&lt;br /&gt;Felix here put language features together with "&lt;em&gt;language mistakes&lt;/em&gt;".&lt;br /&gt;With &lt;em&gt;"use strict"&lt;/em&gt; directive, the one Felix should have put at the very beginning of his guideline, &lt;em&gt;with&lt;/em&gt; statement is not even allowed.&lt;br /&gt;&lt;em&gt;eval&lt;/em&gt; has nothing to do with Object.freeze and others and these methods are part of the ES5 specification.&lt;br /&gt;It is true you may not need them, to define them as &lt;em&gt;something to stay away from&lt;/em&gt;, specially from somebody that said there are no constants for objects, is kinda limitative and a sort of non sense.&lt;br /&gt;Learn these new methods, and use them if you think/want/need.&lt;br /&gt;&lt;br /&gt;And that's all folks&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-7238362446865515823?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/7238362446865515823/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=7238362446865515823' title='13 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7238362446865515823'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7238362446865515823'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/11/about-felixs-style-guide.html' title='About Felix&apos;s Style Guide'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>13</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-8883226946059331960</id><published>2011-11-26T12:52:00.003+01:00</published><updated>2011-11-26T13:39:00.625+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JSON'/><category scheme='http://www.blogger.com/atom/ns#' term='JSONH'/><category scheme='http://www.blogger.com/atom/ns#' term='homogeneous'/><category scheme='http://www.blogger.com/atom/ns#' term='Collection'/><title type='text'>JSONH New schema Argument</title><content type='html'>The freaking fast and bandwidth saver &lt;a href="https://github.com/WebReflection/JSONH"&gt;JSONH Project&lt;/a&gt; has finally a new &lt;em&gt;schema&lt;/em&gt; argument added at the end of every method in order to make nested Homogeneous Collections automatically "&lt;i&gt;packable&lt;/i&gt;", here an example:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;            var&lt;br /&gt;                // nested objects b property&lt;br /&gt;                // have same homogeneous collections&lt;br /&gt;                // in properties c and d&lt;br /&gt;                schema = ["b.c", "b.d"],&lt;br /&gt;                &lt;br /&gt;                // test case&lt;br /&gt;                test = [&lt;br /&gt;                    {   // homogeneous collections in c and d&lt;br /&gt;                        b: {&lt;br /&gt;                            c: [&lt;br /&gt;                                {a: 1},&lt;br /&gt;                                {a: 2}&lt;br /&gt;                            ],&lt;br /&gt;                            d: [&lt;br /&gt;                                {a: 3},&lt;br /&gt;                                {a: 4}&lt;br /&gt;                            ]&lt;br /&gt;                        }&lt;br /&gt;                    }, {&lt;br /&gt;                        a: 1,&lt;br /&gt;                        // same homogeneous collections in c and d&lt;br /&gt;                        b: {&lt;br /&gt;                            c: [&lt;br /&gt;                                {a: 5},&lt;br /&gt;                                {a: 6}&lt;br /&gt;                            ],&lt;br /&gt;                            d: [&lt;br /&gt;                                {a: 7},&lt;br /&gt;                                {a: 8}&lt;br /&gt;                            ]&lt;br /&gt;                        }&lt;br /&gt;                    }&lt;br /&gt;                ]&lt;br /&gt;            ;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The &lt;em&gt;JSONH.pack(test, schema)&lt;/em&gt; output will be the equivalent of this string:&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;[{"b":{"c":[1,"a",1,2],"d":[1,"a",3,4]}},{"a":1,"b":{"c":[1,"a",5,6],"d":[1,"a",7,8]}}]&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;How Schema Works&lt;/h3&gt;It does not matter if the output is an object or a list of objects, as well as it does not matter if the output has nested properties.&lt;br /&gt;As soon as there is an homogeneous collection somewhere deep in the nested chain and common for all other levels, the schema is able to reach that property and optimize it directly.&lt;br /&gt;Objects inside objects do not need to be the same or homogeneous, these can simply have a unique property which is common for all items and this is enough to take advantage of the &lt;em&gt;schema&lt;/em&gt; argument that could be one string, or an array of strings.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Experimental&lt;/h3&gt;Not because it does not work, I have &lt;a href="https://github.com/WebReflection/JSONH/blob/master/js/test/jsonh.js"&gt;added tests indeed&lt;/a&gt;, simply because I am not sure 100% this implementation covers all possible cases but I would rather keep it simple and let developers deal with more complex scenario via manual parsing through the &lt;em&gt;JSONH.pack/unpack&lt;/em&gt; and without schema ... this is still possible as it has always been.&lt;br /&gt;Let me know what you think about the schema, if accepted, I will implement it in Python and PHP too, thanks.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-8883226946059331960?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/8883226946059331960/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=8883226946059331960' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/8883226946059331960'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/8883226946059331960'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/11/jsonh-new-schema-argument.html' title='JSONH New schema Argument'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-2248627748932897780</id><published>2011-11-25T21:41:00.007+01:00</published><updated>2011-11-25T22:55:18.708+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='performances'/><category scheme='http://www.blogger.com/atom/ns#' term='recycle'/><category scheme='http://www.blogger.com/atom/ns#' term='defineProperties'/><title type='text'>On Complex Getters And Setters</title><content type='html'>A common use case for getters and setters is via scalar values rather than complex data.&lt;br /&gt;Well, this is just a programmer mind limit since data we could set, or get, can be of course much more complex: here an example&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;function Person() {}&lt;br /&gt;Person.prototype.toString = function () {&lt;br /&gt;    return this._name + " is " + this._age;&lt;br /&gt;};&lt;br /&gt;// the magic identity configuration object&lt;br /&gt;Object.defineProperty(Person.prototype, "identity", {&lt;br /&gt;    set: function (identity) {&lt;br /&gt;        // do something meaningful&lt;br /&gt;        this._name = identity.name;&lt;br /&gt;        this._age = identity.age;&lt;br /&gt;        // store identity for the getter&lt;br /&gt;        this._identity = identity;&lt;br /&gt;    },&lt;br /&gt;    get: function () {&lt;br /&gt;        return this._identity;&lt;br /&gt;    }&lt;br /&gt;});&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;With above pattern we can automagically update a Person instance name and age through a single identity assignment.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var me = new Person;&lt;br /&gt;me.identity = {&lt;br /&gt;    name: "WebReflection",&lt;br /&gt;    age: 33&lt;br /&gt;};&lt;br /&gt;&lt;br /&gt;alert(me); // WebReflection is 33&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;While the example may not make much sense, the concept behind could be extended to any sort of property of any sort of class/instance/object.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;What's Wrong&lt;/h3&gt;The problem is that the setter does something in order to keep the object updated in all its parts but the getter does nothing different than returning just the identity reference.&lt;br /&gt;As summary, the problem is with the getter and the reason is simple: from user/coder perspective this may not make sense!&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;me.identity.name = "Andrea";&lt;br /&gt;&lt;br /&gt;alert(me); // WebReflection is 33&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;In few words we are changing an object property, the one used as identity for the &lt;em&gt;me&lt;/em&gt; variable, leaving the instance of Person untouched ... and semantically speaking this looks wrong!&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;A Better Approach&lt;/h3&gt;If the setter aim is to update a state there will be only a well known amount of properties to re-assign before this status can be updated.&lt;br /&gt;In this example we would like to be sure that as soon as the identity has been set, the instance toString method will produce the expected result and without relying an external reference, the identity object itself.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// listOfNames and listOfAges are external Arrays&lt;br /&gt;// with same length&lt;br /&gt;for (var&lt;br /&gt;  identity = {},&lt;br /&gt;  population = [],&lt;br /&gt;  i = 0,&lt;br /&gt;  length = listOfNames.length;&lt;br /&gt;  i &lt; length; ++i&lt;br /&gt;) {&lt;br /&gt;  // reuse a single object to define identities&lt;br /&gt;  identity.name = listOfNames[i];&lt;br /&gt;  identity.age = listOfAges[i];&lt;br /&gt;  population[i] = new Person;&lt;br /&gt;  population[i].identity = identity;&lt;br /&gt;  // out of this loop we want that each &lt;br /&gt;  // instanceof Person prints out&lt;br /&gt;  // the right name and surname&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;// we cannot do it lazily in the toString method ...&lt;br /&gt;// this will fail indeed&lt;br /&gt;Person.prototype.toString = function () {&lt;br /&gt;  return this._identity.name + " is " + this.identity._age;&lt;br /&gt;};&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Got it? It's basically what happens when we use an object to define a property, more properties, or to create inheriting from another one: properties and values are parsed and assigned at that moment, not after!&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var commonDefinition = {&lt;br /&gt;  enumerable: true,&lt;br /&gt;  writable: true,&lt;br /&gt;  configurable: false&lt;br /&gt;};&lt;br /&gt;&lt;br /&gt;var&lt;br /&gt;  name = (commonDefinition.value = "a"),&lt;br /&gt;  a = Object.defineProperty({}, "name", commonDefinition),&lt;br /&gt;  name = (commonDefinition.value = "b"),&lt;br /&gt;  b = Object.defineProperty({}, "name", commonDefinition)&lt;br /&gt;;&lt;br /&gt;alert([&lt;br /&gt;  a.name,  // "a"&lt;br /&gt;  b.name   // "b"&lt;br /&gt;]);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;As we can see if the property assignment would have been lazy the result of the latest alert would have been "b", "b" since the object used to define these properties has been recycled ... I hope you are still following ...&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;A &lt;em&gt;Costy&lt;/em&gt; Solution&lt;/h3&gt;There is one approach we may consider in order to make this identity consistent ... the one that stores an identity with getters and setters.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// the magic identity configuration object&lt;br /&gt;Object.defineProperty(Person.prototype, "identity", {&lt;br /&gt;    set: function (identity) {&lt;br /&gt;        var self = this;&lt;br /&gt;&lt;br /&gt;        // do something meaningful&lt;br /&gt;        self._name = identity.name;&lt;br /&gt;        self._age = identity.age;&lt;br /&gt;&lt;br /&gt;        // store identity as fresh new object with bound behavior&lt;br /&gt;        this._identity = Object.defineProperties({}, {&lt;br /&gt;            name: {&lt;br /&gt;                get: function () {&lt;br /&gt;                    return self._name;&lt;br /&gt;                },&lt;br /&gt;                set: function (name) {&lt;br /&gt;                    self._name = name;&lt;br /&gt;                }&lt;br /&gt;            },&lt;br /&gt;            age: {&lt;br /&gt;                get: function () {&lt;br /&gt;                    return self._age;&lt;br /&gt;                },&lt;br /&gt;                set: function (age) {&lt;br /&gt;                    self._age = age;&lt;br /&gt;                }&lt;br /&gt;            }&lt;br /&gt;        });&lt;br /&gt;    },&lt;br /&gt;    get: function () {&lt;br /&gt;        return this._identity;&lt;br /&gt;    }&lt;br /&gt;});&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;What changed ? The fact that now we are able to pass through the instance and operate through the identity:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;&lt;br /&gt;me.identity.name = "Andrea";&lt;br /&gt;&lt;br /&gt;alert(me); // Andrea is 33&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Cool hu ? ... well, it could be better ... &lt;br /&gt;&lt;br /&gt;&lt;h3&gt;A Faster Solution&lt;/h3&gt;If for each Person and each identity we have to create a fresh new object plus at least 4 functions, 2 for getters and 2 for relative setters, our memory will fill up so quickly that we won't be able to define any other person identity soon and here comes the fun part: use the knowledge gained by this pattern internally!&lt;br /&gt;Yes, what we could do to make things slightly better is to recycle the internal identity setter object definition in order to borrow maximum 4 functions rather than 4 extra per each Person instance ... sounds cool. uh?&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;function Person() {}&lt;br /&gt;Person.prototype.toString = function () {&lt;br /&gt;  return this._name + " is " + this._age;&lt;br /&gt;};&lt;br /&gt;&lt;br /&gt;(function () {&lt;br /&gt;&lt;br /&gt;  var identityProperties = {&lt;br /&gt;    name: {&lt;br /&gt;      get: function () {&lt;br /&gt;        return this.reference._name;&lt;br /&gt;      },&lt;br /&gt;      set: function (name) {&lt;br /&gt;        this.reference._name = name;&lt;br /&gt;      },&lt;br /&gt;      configurable: true&lt;br /&gt;    },&lt;br /&gt;    age: {&lt;br /&gt;      get: function () {&lt;br /&gt;        return this.reference._age;&lt;br /&gt;      },&lt;br /&gt;      set: function (age) {&lt;br /&gt;        this.reference._age = age;&lt;br /&gt;      },&lt;br /&gt;      configurable: true&lt;br /&gt;    },&lt;br /&gt;    reference: {&lt;br /&gt;      value: null,&lt;br /&gt;      writable: true,&lt;br /&gt;      configurable: true&lt;br /&gt;    }&lt;br /&gt;  };&lt;br /&gt;&lt;br /&gt;  Object.defineProperty(Person.prototype, "identity", {&lt;br /&gt;    get: function () {&lt;br /&gt;      return this._identity;&lt;br /&gt;    },&lt;br /&gt;    set: function (identity) {&lt;br /&gt;      // something meaningful&lt;br /&gt;      this._name = identity.name;&lt;br /&gt;      this._age = identity.age;&lt;br /&gt;&lt;br /&gt;      // set the reference to the recycled object&lt;br /&gt;      identityProperties.reference.value = this;&lt;br /&gt;&lt;br /&gt;      // define the _identity property&lt;br /&gt;      if (!this._identity) {&lt;br /&gt;        Object.defineProperty(&lt;br /&gt;          this, "_identity", {value: {}}&lt;br /&gt;        );&lt;br /&gt;      }&lt;br /&gt;      Object.defineProperties(&lt;br /&gt;        this._identity,&lt;br /&gt;        identityProperties&lt;br /&gt;      );&lt;br /&gt;    }&lt;br /&gt;  });&lt;br /&gt;&lt;br /&gt;}());&lt;br /&gt;&lt;br /&gt;var&lt;br /&gt;  identity = {},&lt;br /&gt;  a = new Person,&lt;br /&gt;  b = new Person&lt;br /&gt;;&lt;br /&gt;&lt;br /&gt;identity.name = "a";&lt;br /&gt;identity.age = 30;&lt;br /&gt;a.identity = identity;&lt;br /&gt;&lt;br /&gt;identity.name = "b";&lt;br /&gt;identity.age = 31;&lt;br /&gt;b.identity = identity;&lt;br /&gt;&lt;br /&gt;alert([&lt;br /&gt;  a,  // "a is 30"&lt;br /&gt;  b   // "b is 31"&lt;br /&gt;]);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;So what we have there? A lazy &lt;em&gt;_identity&lt;/em&gt; definition, good for those scenario where some getter or setter may never been invoked, plus a smart recycled property definition through a single object descriptor, and performances boosted up N times per each instance since no multiple different functions are assigned per identity properties getters and setters and no extra objects are created runtime ... arf, arf .. are you still with me ?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;Some JS developer keep asking for standard ways to do these kind of crazy stuff without realizing that few other programming languages are that flexible as JavaScript is ... it's maybe not that simple to find better, optimized, in therms of both memory consumption and raw performances, patterns to cover &lt;em&gt;weird&lt;/em&gt; scenario but what we should appreciate is that with JS we almost have, always, a way to simulate something we did not even think about until the day before.&lt;br /&gt;Have fun with JS ;)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-2248627748932897780?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/2248627748932897780/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=2248627748932897780' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/2248627748932897780'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/2248627748932897780'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/11/on-complex-getters-and-setters.html' title='On Complex Getters And Setters'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-8942219230640236570</id><published>2011-11-21T03:19:00.003+01:00</published><updated>2011-11-21T03:55:59.817+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='scroll'/><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='CSS'/><category scheme='http://www.blogger.com/atom/ns#' term='background'/><category scheme='http://www.blogger.com/atom/ns#' term='size'/><title type='text'>Differential Background Scrolling</title><content type='html'>A quick one about this technique quite common in Flash sites but rarely seen on Web.&lt;br /&gt;Have &lt;a href="http://3site.it/diffbg/"&gt;a look at the example&lt;/a&gt; first so you can understand what I am talking about ... got it ?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;What Is This About&lt;/h3&gt;Let's say we have a background, a big massive graphic background surely not suitable for mobile phones, due data roaming, but maybe cool for desktop and fast ADSL.&lt;br /&gt;The &lt;em&gt;background-size&lt;/em&gt; CSS property is able to let us decide if the image used as background should fit the whole element or only a portion of it.&lt;br /&gt;In this case the image should fit, by default, the whole height of the document with an auto width in order to let the browser adjust the scale.&lt;br /&gt;A differential scrolling is visible the moment we scroll the page ... please resize the window into a smaller one if you are in an HD monitor and start scrolling the page.&lt;br /&gt;At the very beginning, the default height of the image is 100%, as body background, and with some padding in order to let space for few important image parts such the header, with clouds and enough space for a H1 tag, and the bottom, with the stylish logo of &lt;a href="http://www.elderscrolls.com/skyrim/"&gt;this game from elderscrolls.com&lt;/a&gt;, the one which page inspired this little experiment. Bear in mind no code has been even read from that website ... I have seen the effect, I have used it many times ages ago via ActionScript, I decided to do something similar for most advanced browsers, and here is ...&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Code&lt;/h3&gt;&lt;pre class="code"&gt;&lt;br /&gt;(function (document) {&lt;br /&gt; // (C) WebReflection - Mit Style Licence&lt;br /&gt; var&lt;br /&gt;  ratio = .85, // 0 to 1 where 1 is 100%&lt;br /&gt;  &lt;br /&gt;  // shortcuts&lt;br /&gt;  styleSheets = document.styleSheets,&lt;br /&gt;  documentElement = document.documentElement,&lt;br /&gt;  ceil = Math.ceil,&lt;br /&gt;  scroll = "scroll",&lt;br /&gt;  scrollHeight = scroll + "Height",&lt;br /&gt;  scrollTop = scroll + "Top",&lt;br /&gt;  body, sHeight, sTop, y, last&lt;br /&gt; ;&lt;br /&gt; styleSheets = styleSheets[styleSheets.length - 1];&lt;br /&gt; // redefine the rule for the height&lt;br /&gt; styleSheets.insertRule(&lt;br /&gt;  "body{background-size:auto " + ceil(&lt;br /&gt;   ratio * 100&lt;br /&gt;  ) + "%;}",&lt;br /&gt;  styleSheets.cssRules.length&lt;br /&gt; );&lt;br /&gt; // get the rest of the ratio&lt;br /&gt; ratio = 1 - ratio;&lt;br /&gt; // attach a scroll listener&lt;br /&gt; addEventListener(scroll, function (e) {&lt;br /&gt;  if (body || (body = document.body)) {&lt;br /&gt;   sHeight =  documentElement[scrollHeight] ||&lt;br /&gt;      body[scrollHeight];&lt;br /&gt;   sTop =   documentElement[scrollTop] ||&lt;br /&gt;      body[scrollTop];&lt;br /&gt;   y = ceil(&lt;br /&gt;    ratio * sHeight * sTop / (sHeight - innerHeight)&lt;br /&gt;   );&lt;br /&gt;   // this avoid some redundant assignment&lt;br /&gt;   // hopefully creating less flicking effect&lt;br /&gt;   if (last != y) {&lt;br /&gt;    body.style.backgroundPosition = "center " + (last = y) + "px";&lt;br /&gt;   }&lt;br /&gt;  }&lt;br /&gt; }, false);&lt;br /&gt; // you may want to try this for Chrome Browsers&lt;br /&gt; //documentElement.style.WebkitTransform = "translateZ(0)";&lt;br /&gt;}(document));&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Problem&lt;/h3&gt;Many of them ... to start with the fact this technique does not scale as showed in this example since for mobile phones, or generally speaking smaller screens, it does not make sense to use such big image: use media queries for this.&lt;br /&gt;Opera 12 is almost there but something goes terribly wrong during background reposition ... it's screwed up by N pixels even if the rest of the logic works and no error is shown on console.&lt;br /&gt;Firefox Nightly goes quite well but it is still flicking a bit while Safari, and even better WebKit Nightly, are the smoothest in this Mac.&lt;br /&gt;The disaster is Chrome Canary, which is not able to handle this background repositioning.&lt;br /&gt;You can see the effect if you scroll fast in both inspiration site and my experiment and, as commented out in the code, the only way to make it better is to force HW acceleration in the whole document 'cause in the body only the background looks broken ... it's really cool to see how DOM is able to mess up with GPUs, isn't it?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;Nothing much to add to this post, it was just a quick example over a cool effect but as it is, since ever, in this Web field, almost everything went terribly wrong :D&lt;br /&gt;Have fun with CSS and graceful JS enhancements!&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-8942219230640236570?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/8942219230640236570/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=8942219230640236570' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/8942219230640236570'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/8942219230640236570'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/11/differential-background-scrolling.html' title='Differential Background Scrolling'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-642033905920782506</id><published>2011-11-12T13:02:00.014+01:00</published><updated>2011-11-12T17:23:33.777+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='patterns'/><title type='text'>Few JavaScript Patterns</title><content type='html'>Just to be clear and once again, JavaScript can emulate:&lt;ul&gt;&lt;li&gt;classes&lt;/li&gt;&lt;li&gt;public and public static methods or properties&lt;/li&gt;&lt;li&gt;private and private static methods or properties&lt;/li&gt;&lt;li&gt;public and private constants&lt;/li&gt;&lt;li&gt;protected methods&lt;/li&gt;&lt;li&gt;... you name it ...&lt;/li&gt;&lt;/ul&gt;&lt;br /&gt;&lt;pre class="code"&gt;// duck typing ( maybe all you need )&lt;br /&gt;var me = {name: "WebReflection"};&lt;br /&gt;&lt;br /&gt;// basic class&lt;br /&gt;function Person() {}&lt;br /&gt;Person.prototype.getName = function () {&lt;br /&gt;    return this.name;&lt;br /&gt;};&lt;br /&gt;Person.prototype.setName = function (name) {&lt;br /&gt;    this.name = name;&lt;br /&gt;};&lt;br /&gt;&lt;br /&gt;// module pattern + private properties / methods&lt;br /&gt;function Person(_name) {&lt;br /&gt;    function _getName() {&lt;br /&gt;        return _name;&lt;br /&gt;    }&lt;br /&gt;    return {&lt;br /&gt;        getName: function () {&lt;br /&gt;            // redundant, example only&lt;br /&gt;            return _getName();&lt;br /&gt;        },&lt;br /&gt;        setName: function (name) {&lt;br /&gt;            _name = name;&lt;br /&gt;        }&lt;br /&gt;    };&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;// private shared methods via this&lt;br /&gt;var Person = (function () {&lt;br /&gt;    function Person() {}&lt;br /&gt;    function _getName () {&lt;br /&gt;        return this.name;&lt;br /&gt;    }&lt;br /&gt;    function _setName (name) {&lt;br /&gt;        this.name = name;&lt;br /&gt;    }&lt;br /&gt;    Person.prototype.getName = function () {&lt;br /&gt;        return _getName.call(this);&lt;br /&gt;    };&lt;br /&gt;    Person.prototype.setName = function (name) {&lt;br /&gt;        _setName.call(this, name);&lt;br /&gt;    };&lt;br /&gt;    return Person;&lt;br /&gt;}());&lt;br /&gt;&lt;br /&gt;// private shared method Python style&lt;br /&gt;var Person = (function () {&lt;br /&gt;    function Person() {}&lt;br /&gt;    function _getName (self) {&lt;br /&gt;        return self.name;&lt;br /&gt;    }&lt;br /&gt;    function _setName (self, name) {&lt;br /&gt;        self.name = name;&lt;br /&gt;    }&lt;br /&gt;    Person.prototype.getName = function () {&lt;br /&gt;        return _getName(this);&lt;br /&gt;    };&lt;br /&gt;    Person.prototype.setName = function (name) {&lt;br /&gt;        _setName(this, name);&lt;br /&gt;    };&lt;br /&gt;    return Person;&lt;br /&gt;}());&lt;br /&gt;&lt;br /&gt;// public static&lt;br /&gt;function Person() {&lt;br /&gt;    Person.TOTAL++;&lt;br /&gt;}&lt;br /&gt;Person.TOTAL = 0;&lt;br /&gt;&lt;br /&gt;// private static / constant&lt;br /&gt;var Person = (function () {&lt;br /&gt;    var TOTAL = 0;&lt;br /&gt;    return function Person() {&lt;br /&gt;        TOTAL++;&lt;br /&gt;    };&lt;br /&gt;}());&lt;br /&gt;&lt;br /&gt;// public constant&lt;br /&gt;function Person() {}&lt;br /&gt;Object.defineProperty(Person, "RACE", {&lt;br /&gt;    writable: false,    // default&lt;br /&gt;    configurable: false,// default&lt;br /&gt;    enumerable: true,&lt;br /&gt;    value: "HUMAN"&lt;br /&gt;});&lt;br /&gt;&lt;br /&gt;// public inherited constant&lt;br /&gt;function Person() {}&lt;br /&gt;Object.defineProperty(Person.prototype, "RACE", {&lt;br /&gt;    writable: false,    // default&lt;br /&gt;    configurable: false,// default&lt;br /&gt;    enumerable: true,&lt;br /&gt;    value: "HUMAN"&lt;br /&gt;});&lt;br /&gt;&lt;br /&gt;// protected method&lt;br /&gt;function Person() {}&lt;br /&gt;Person.prototype.getName = function () {&lt;br /&gt;    return this instanceof Person ?&lt;br /&gt;        this.name :&lt;br /&gt;        throw "protected method violation"&lt;br /&gt;    ; &lt;br /&gt;};&lt;br /&gt;Person.prototype.setName = function (name) {&lt;br /&gt;    this instanceof Person ?&lt;br /&gt;        this.name = name :&lt;br /&gt;        throw "protected method violation"&lt;br /&gt;    ; &lt;br /&gt;};&lt;br /&gt;&lt;br /&gt;// generic protected methods&lt;br /&gt;Function.prototype.protectedVia = function (Class) {&lt;br /&gt;    var method = this;&lt;br /&gt;    Class || (Class = Object);&lt;br /&gt;    return function () {&lt;br /&gt;        if (this instanceof Class) {&lt;br /&gt;            return method.apply(this, arguments);&lt;br /&gt;        }&lt;br /&gt;        throw "protected method violation on " + (&lt;br /&gt;            Class.name || Class&lt;br /&gt;        );&lt;br /&gt;    };&lt;br /&gt;};&lt;br /&gt;function Person() {}&lt;br /&gt;Person.prototype.getName = function () {&lt;br /&gt;    return this.name;&lt;br /&gt;}.protectedVia(Person);&lt;br /&gt;Person.prototype.setName = function (name) {&lt;br /&gt;    this.name = name&lt;br /&gt;}.protectedVia(Person);&lt;br /&gt;&lt;br /&gt;// private shared variables&lt;br /&gt;function Person() {}&lt;br /&gt;Person.prototype.getName = function () {&lt;br /&gt;    return this.name;&lt;br /&gt;};&lt;br /&gt;(function (PersonPrototype) {&lt;br /&gt;    var changes = 0;&lt;br /&gt;    PersonPrototype.setName = function (name) {&lt;br /&gt;        changes++;&lt;br /&gt;        this.name = name;&lt;br /&gt;    };&lt;br /&gt;    PersonPrototype.howManyChangedName = function () {&lt;br /&gt;        return changes;&lt;br /&gt;    };&lt;br /&gt;}(Person.prototype));&lt;br /&gt;&lt;br /&gt;// getters / setters on public property&lt;br /&gt;var person = Object.defineProperty({}, "name", {&lt;br /&gt;    get: function () {&lt;br /&gt;        return this._name;&lt;br /&gt;    },&lt;br /&gt;    set: function (_name) {&lt;br /&gt;        this._name = _name;&lt;br /&gt;    }&lt;br /&gt;});&lt;br /&gt;&lt;br /&gt;// getters setters on public property via prototype&lt;br /&gt;function Person() {}&lt;br /&gt;Object.defineProperty(Person.prototype, "name", {&lt;br /&gt;    get: function () {&lt;br /&gt;        return this._name;&lt;br /&gt;    },&lt;br /&gt;    set: function (_name) {&lt;br /&gt;        this._name = _name;&lt;br /&gt;    }&lt;br /&gt;});&lt;br /&gt;&lt;br /&gt;// getters / setters on private property&lt;br /&gt;var person = Object.defineProperty({}, "name", (function () {&lt;br /&gt;    var _name;&lt;br /&gt;    return {&lt;br /&gt;        get: function () {&lt;br /&gt;            return _name;&lt;br /&gt;        },&lt;br /&gt;        set: function (name) {&lt;br /&gt;            _name = name;&lt;br /&gt;        }&lt;br /&gt;    };&lt;br /&gt;}()));&lt;br /&gt;&lt;br /&gt;// singleton&lt;br /&gt;var me = {name: "WebReflection"};&lt;br /&gt;&lt;br /&gt;// singleton via anonymous __proto__&lt;br /&gt;// plus private properties&lt;br /&gt;var me = new function () {&lt;br /&gt;    var _name;&lt;br /&gt;    this.getName = function () {&lt;br /&gt;        return _name;&lt;br /&gt;    };&lt;br /&gt;    this.setName = function (name) {&lt;br /&gt;        _name = name;&lt;br /&gt;    };&lt;br /&gt;};&lt;br /&gt;&lt;br /&gt;// generic singleton cross browser&lt;br /&gt;Function.prototype.singleton = (function () {&lt;br /&gt;    function anonymous(){};&lt;br /&gt;    function create(Class, args) {&lt;br /&gt;        anonymous.prototype = Class.prototype;&lt;br /&gt;        Class.apply(&lt;br /&gt;            Class.__singleton__ = new anonymous,&lt;br /&gt;            args&lt;br /&gt;        );&lt;br /&gt;        return Class.__singleton__;&lt;br /&gt;    }&lt;br /&gt;    return function singleton() {&lt;br /&gt;        return this.__singleton__ || create(this, arguments);&lt;br /&gt;    };&lt;br /&gt;}());&lt;br /&gt;&lt;br /&gt;// generic singleton ES5&lt;br /&gt;Function.prototype.singleton = (function () {&lt;br /&gt;    function create(Class, args) {&lt;br /&gt;        Class.apply(&lt;br /&gt;            Class.__singleton__ = Object.create(&lt;br /&gt;                Class.prototype&lt;br /&gt;            ), args&lt;br /&gt;        );&lt;br /&gt;        return Class.__singleton__;&lt;br /&gt;    }&lt;br /&gt;    return function singleton() {&lt;br /&gt;        returh this.__singleton__ || create(this, arguments);&lt;br /&gt;    };&lt;br /&gt;}());&lt;br /&gt;&lt;br /&gt;// per function private singleton&lt;br /&gt;var Person = (function () {&lt;br /&gt;    var instance;&lt;br /&gt;    return function Person () {&lt;br /&gt;        return instance || (instance = this);&lt;br /&gt;        // or ... ot be more than sure ...&lt;br /&gt;        return instance || (&lt;br /&gt;            (instance = true) &amp;&amp; // avoid infinite recursion&lt;br /&gt;            (instance = new Person)&lt;br /&gt;        );&lt;br /&gt;    };&lt;br /&gt;}());&lt;br /&gt;&lt;br /&gt;// generic factory&lt;br /&gt;Function.prototype.factory = (function () {&lt;br /&gt;    function anonymous() {};&lt;br /&gt;    return function factory() {&lt;br /&gt;        anonymous.prototype = this.prototype;&lt;br /&gt;        var instance = new anonymous;&lt;br /&gt;        this.apply(instance, arguments);&lt;br /&gt;        return instance;&lt;br /&gt;    };&lt;br /&gt;}());&lt;br /&gt;&lt;br /&gt;// generic factory ES5 + ruby style&lt;br /&gt;Function.prototype.new = function factory() {&lt;br /&gt;    var instance = Object.create(this.prototype);&lt;br /&gt;    this.apply(instance, arguments);&lt;br /&gt;    return instance;&lt;br /&gt;};&lt;br /&gt;&lt;/pre&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-642033905920782506?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/642033905920782506/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=642033905920782506' title='10 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/642033905920782506'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/642033905920782506'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/11/few-javascript-patterns.html' title='Few JavaScript Patterns'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>10</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-6267040038417456704</id><published>2011-11-08T23:33:00.007+01:00</published><updated>2011-11-09T08:45:45.704+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='function'/><category scheme='http://www.blogger.com/atom/ns#' term='notification'/><category scheme='http://www.blogger.com/atom/ns#' term='monitor'/><category scheme='http://www.blogger.com/atom/ns#' term='Callback'/><category scheme='http://www.blogger.com/atom/ns#' term='test'/><title type='text'>Function.prototype.notifier</title><content type='html'>There are way too many ways to &lt;em&gt;stub&lt;/em&gt; functions or methods, but at the end of the day all we want to know is always the same:&lt;ul&gt;&lt;li&gt;has that function been invoked ?&lt;/li&gt;&lt;li&gt;has that function received the expected context ?&lt;/li&gt;&lt;li&gt;which argument has been passed to that function ?&lt;/li&gt;&lt;li&gt;what was the output of the function ?&lt;/li&gt;&lt;/ul&gt;&lt;br /&gt;&lt;strong&gt;Update&lt;/strong&gt; thanks to &lt;a href="http://twitter.com/bga_"&gt;@bga_&lt;/a&gt; hint about the output property in after notification, it made perfect sense&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Concept&lt;/h3&gt;For fun and no profit I have created a prototype which aim is to bring a &lt;strong&gt;DOM like interface to any sort of function or method&lt;/strong&gt; in order to monitor its lifecycle:&lt;ul&gt;&lt;li&gt;the &lt;em&gt;"before"&lt;/em&gt; event, able to &lt;em&gt;preventDefault()&lt;/em&gt; and avoid the original function call at all&lt;/li&gt;&lt;li&gt;the &lt;em&gt;"after"&lt;/em&gt; event, in order to understand if the function did those expected changes to the environment or to a generic input object, or simply to analyze the output of the previous call&lt;/li&gt;&lt;li&gt;the &lt;em&gt;"error"&lt;/em&gt; event, in case we want to be notified if something went wrong during function execution&lt;/li&gt;&lt;li&gt;the &lt;em&gt;"handlererror"&lt;/em&gt; event, just in case we are the cause of an error while we are monitoring the original function&lt;/li&gt;&lt;/ul&gt;The reason I have chosen an &lt;em&gt;addEventListener&lt;/em&gt; like interface, called in this case &lt;em&gt;addListener&lt;/em&gt;, is simple: JavaScript works pretty well with event driven applications so what else could be better than an event driven approach?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Basic Example&lt;/h3&gt;&lt;pre class="code"&gt;&lt;br /&gt;var nFromCharcode = String.fromCharCode.notifier({&lt;br /&gt;    before: function (e) {&lt;br /&gt;        if (e.arguments.length &amp;gt; 2048) {&lt;br /&gt;            throw "too many arguments";&lt;br /&gt;            e.preventDefault(); // won't even try to execute it&lt;br /&gt;        }&lt;br /&gt;        // in case you want to remove this listener ... &lt;br /&gt;        e.notifier.removeListener("before", e.handler);&lt;br /&gt;    },&lt;br /&gt;    after: function (e) {&lt;br /&gt;        if (e.output !== "PQR") {&lt;br /&gt;            throw "expected PQR got " + e.output + " instead";&lt;br /&gt;        }&lt;br /&gt;    },&lt;br /&gt;    handlererror: function (e) {&lt;br /&gt;        testFramework.failBecause("" + e.error);&lt;br /&gt;    }&lt;br /&gt;});&lt;br /&gt;&lt;br /&gt;// run the test ...&lt;br /&gt;nFromCharcode(80, 81, 82); // "PQR"&lt;br /&gt;nFromCharcode.apply(null, arrayOf2049Codes); // testFramework will fail&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The notifier itself is a function, precisely the original function wrapper with enriched API in order to monitor almost every aspect of a method or a function.&lt;br /&gt;The event object passed through each listener has these properties:&lt;ul&gt;&lt;li&gt;notifier: the object create to monitor the function and notify all listeners&lt;/li&gt;&lt;li&gt;handler: the current handler to make the notifier remove listener easier&lt;/li&gt;&lt;li&gt;callback: the original function that has been wrapped by the notifier&lt;/li&gt;&lt;li&gt;type: the event type such before, error, after, handlererror&lt;/li&gt;&lt;li&gt;arguments: passed arguments transformed already into array&lt;/li&gt;&lt;li&gt;context: the "this" reference used as callback context&lt;/li&gt;&lt;li&gt;error: the optional error object for events error and handlererror&lt;/li&gt;&lt;li&gt;preventDefault: the method able to avoid function execution if called in the before listener&lt;/li&gt;&lt;li&gt;output: assigned only during &lt;em&gt;"after"&lt;/em&gt; notification and if no error occurred, handy to compare expected results&lt;/li&gt;&lt;/ul&gt;&lt;br /&gt;I guess there is really nothing else we could possibly know about a notifier, and its callback, lifecycle, what do you think?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Code&lt;/h3&gt;&lt;br /&gt;&lt;script src="https://gist.github.com/1345695.js?file=Function.prototype.notifier.js"&gt;&lt;/script&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;&lt;br /&gt;I have also a &lt;a href="https://gist.github.com/1349511"&gt;full test coverage&lt;/a&gt; for this notifier and I hope someone will use it and will come back to provide some feedback, cheers!&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-6267040038417456704?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/6267040038417456704/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=6267040038417456704' title='9 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/6267040038417456704'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/6267040038417456704'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/11/functionprototypenotifier.html' title='Function.prototype.notifier'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>9</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-7923066140429273468</id><published>2011-10-31T20:52:00.009+01:00</published><updated>2011-10-31T22:53:40.983+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='Sniff'/><category scheme='http://www.blogger.com/atom/ns#' term='User'/><category scheme='http://www.blogger.com/atom/ns#' term='Agent'/><title type='text'>On User Agent Sniffing</title><content type='html'>Oh well, who was following me on twitter today is already bored about this topic (I guess) but probably other developers would like to read this too so ...&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;What Is UA Sniffing&lt;/h3&gt;UserAgent sniffing means that a generic software is relying into a generic string representation of the underlying system. The User Agent is basically considered a unique identifier of "&lt;em&gt;the current software or hardware that is running the app&lt;/em&gt;".&lt;br /&gt;In native applications world UA could be simply the platform name ... where if it's "&lt;i&gt;Darwin&lt;/i&gt;" it means we are in a Mac platform, while if it's Win32 or any other "&lt;i&gt;/^Win.*$/&lt;/i&gt;" environment, the app reacts, compile, execute, as if it is in a Windows machine ... and so on with Linux and relative distributions.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The "Native" Software Behavior&lt;/h3&gt;If you have an hybrid solution, example those solutions not allowed anymore but called Hachintosh not long time ago, your machine has most likely Windows Starter capable Hardware but it's running compiled Objective-C language. How reliable you think this machine is? Every software will consider it a Mac Hardware capable machine.&lt;br /&gt;Should these applications optimize for &lt;strong&gt;non Mac&lt;/strong&gt; hardware? I don't think so .... I mean, that machine was not classified in first place as Mac capable machine, it was the user/hacker that decided to do something "&lt;i&gt;nasty&lt;/i&gt;" so that if something does not work ... who does really care?&lt;br /&gt;Do you really want to provide support for that "&lt;i&gt;random machine in the system&lt;/i&gt;"?&lt;br /&gt;I still don't think so ... also, if you know performances and provided hardware has reached certain levels in that environment, do you even want to waste time optimizing things for a Netbook user?&lt;br /&gt;I think reality is that you just create software for the target, or those targets, you want to support and nothing else, isn't it? ... but of course new unexpected comers are, hopefully, welcome ...&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Old Web Behavior&lt;/h3&gt;UA sniffing has historically been a bad practice in the world wide web (internet). At the very beginning there was only a major and supported browser, Internet Explorer, and this had something like 80% or more of market share. All developers, browsers vendors, and users with a different browser where most likely redirected into a page that was saying something like: "&lt;i&gt;Your browser is not supported. Please come back with IE!&lt;/i&gt;"&lt;br /&gt;Even worst, this was happening on the server side level ... "&lt;i&gt;why that&lt;/i&gt;"? Because websites where created, and tested, entirely in Internet Explorer as unique target for any sort of online business.&lt;br /&gt;Was that a good choice? Today we can say it wasn't but back at that time it was making sense on business level.&lt;br /&gt;How many apps we know that work only on Windows or only on Mac? Many of them, and we are talking about only two platforms.&lt;br /&gt;At least at that point we had a server side degradation into a non service completely useless for not targeted browsers but ... hey, that was their business, and if they wanted to use &lt;em&gt;ActiveXObject&lt;/em&gt; because many things where not possible in other browsers, how can we blame these companies? "&lt;em&gt;Everywhere or nothing&lt;/em&gt;"? A nice utopia that won't bring you that far in real world .... nothing, I repeat, nothing works 100% as expected everywhere.&lt;br /&gt;The dream is to reach that point but stories like Java, .NET VS Mono, Python itself, and of course JavaScript, should ring a little bell in our developers mind ... we can still go close though, at least on the Web side!&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Modern Web Behavior&lt;/h3&gt;Recently things changed quite a lot on web side and only few companies are redirecting via server side User Agent sniffing. We have now something called &lt;strong&gt;runtime features detections&lt;/strong&gt;, something that supposes to test indeed runtime browser capabilities and understand, still runtime, if the browser should be redirected or not into a hopefully meaningful fallback or degraded service.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Features Detections Good Because&lt;/h3&gt;Well, specially because the browsers fragmentation is massive, FD can tell us what we need from the current one, without penalizing in advance anybody.&lt;br /&gt;The potential redirection or message only if necessary, informing the user his/her browser is not capable of features required to grant a decent experience in the current online application/service.&lt;br /&gt;FDs are also widely suggested for future compatibility with new browsers we may not be able to test, or recognize, with any sort of list present in our server side logic, the one that is not directly able to understand if the current browser may run the application/service or not.&lt;br /&gt;Of course to be automatically compatible with newer browsers is both business value, as "&lt;i&gt;there before we know&lt;/i&gt;", and simplified maintenance of the application/logic itself, since if it was working accordingly with certain features, of course it's going to work accordingly with newer or improved features we need.&lt;br /&gt;As summary, runtime features detections can be extremely valuable for our business ... but&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Features Detections Bad Because&lt;/h3&gt;Not sure I have to tell you that the first browser with disabled JavaScript support will fail all detections even if theoretically capable ... but lets ignore these cases for now, right?&lt;br /&gt;Well, it's kinda right, 'cause we may have detected browsers with JS disabled already in the server side thanks to user headers or specific agent ... should I mention Lynx browser ? Try to detect that one via JavaScript ... &lt;br /&gt;Back to "&lt;i&gt;real world cases&lt;/i&gt;", all techniques used today for runtime features detections are kinda weak ... or better, extremely weak!&lt;br /&gt;I give you an example:&lt;pre class="code"&gt;&lt;br /&gt;// the "shimmable"&lt;br /&gt;if (!("forEach" in []) || !Array.prototype.forEach) {&lt;br /&gt;    // you wish this gonna fix everything, uh? ... &lt;br /&gt;    Array.prototype.forEach = function () { ... };&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;// the unshimmable&lt;br /&gt;if (!document.createElement("canvas").getContext("2d")) {&lt;br /&gt;    // no canvas support ... you wish to know here ...&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;Not because I want to disappoint you but you gonna be potentially wrong in both cases ... why that?&lt;br /&gt;Even if &lt;em&gt;Array.prototype.forEach&lt;/em&gt; is exposed and this is the only Array extra you need, &lt;a href="http://code.google.com/p/chromium/issues/detail?id=100702&amp;thanks=100702&amp;ts=1318946276"&gt;things may go wrong&lt;/a&gt;. As example, the first shim will never be executed in a case where &lt;i&gt;"forEach" in []&lt;/i&gt; is true, even if that shim would have solved our problem.&lt;br /&gt;That bug I have filed few days ago demonstrated that we cannot really trust the fact a method is somewhere since we should write a whole test suite for a single method in order to be sure everything will work as expected &lt;strong&gt;OR&lt;/strong&gt; we gonna write unit, acceptance, integration, and functional tests to be sure that a bloody browser works as expected in our application.&lt;br /&gt;Same is valid for classic canvas capability ... once we have that, do we really test that every method works as expected? And if we need only a single method out of the canvas, how can we understand that method is there and is working as expected without involving, for the single test, part of the API that may not work but even though we don't care since we need only the very first one?&lt;br /&gt;I am talking about &lt;em&gt;drawImage&lt;/em&gt;, as example, in old Symbian browsers, where canvas is exposed but drawImage does not visually draw anything on the element ... nice, isn't it?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;You Cannot Detect Everything Runtime&lt;/h3&gt; ... or better, if you do, most likely any user has to wait few minutes before the &lt;a href="http://test262.ecmascript.org/#"&gt;whole&lt;/a&gt; &lt;a href="http://acid3.acidtests.org/"&gt;test&lt;/a&gt; suite becomes green, specially in mobile browsers where any of these tests take ages burning battery life, CPU clocks, RAM, and everything else before the page can be even visualized since we would like to redirect the user before he can see the experience is already broken, isn't it?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;IT Is Not Black Or White&lt;/h3&gt;... you think so? I think IT is more about "&lt;em&gt;what's the most convenient solution for this problem&lt;/em&gt;", assuming there is, generally speaking, no best solution to a specific problem, since every problem can be solved differently and in a better way, accordingly with the surrounding environment.&lt;br /&gt;So how do we brainstorm all these possible edge cases that cannot obviously be solved runtime in a meaningful, reliable way?&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;I want provide same experience to as many users as possible but thanks to my tests I have already found user X, Y, and Z, that cannot possibly be compatible with the application/service I am trying to offer.&lt;br /&gt;If I detect runtime everything I need for my app, assuming this is possible, every browser I already know has no problems there will be penalized for non updated, low market share, problematic alternatives.&lt;br /&gt;If I sniff the User Agent with a list of browsers I already know I cannot possibly support due lack of unshimmable features, how faster will be on startup time every other browser I am interested on?&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Best Solution Now&lt;/h3&gt;If you ask me, today and specially on mobile side, we have 3 categories of browsers:&lt;ol&gt;&lt;li&gt;those almost there&lt;/li&gt;&lt;li&gt;those not there yet&lt;/li&gt;&lt;li&gt;those will never be there&lt;/li&gt;&lt;/ol&gt;&lt;br /&gt;In a business logic you don't even want to waste time for the third category ... "&lt;em&gt;money for nothing&lt;/em&gt;", as &lt;a href="http://en.wikipedia.org/wiki/Mark_Knopfler"&gt;Mark Knopfler&lt;/a&gt; would say.&lt;br /&gt;You also do not want to penalize most interesting browsers categories due massive amount, size and computation logic speaking, of features detections ... I mean, we know those browsers are crap and a minority, the server side User Agent sniffing would be the most suitable solution ever providing any sort of possible fallback or info, if there is no budget for that fallback.&lt;br /&gt;But what about the second category?&lt;br /&gt;Well, it depends ... if the second category has a decent market share you may try to support it and let it pass all your tests but at which price?&lt;br /&gt;If the whole application has to be different for that single browser, and it shares less than 10% of the global market share, reflected into 1% of your users, do you really want to spend all possible effort to make it work?&lt;br /&gt;I would say it makes sense only if this browser has few, shimmable, problems ... otherwise the best place for this browser would be directly the server side, don't you think?&lt;br /&gt;About the first category ... well, it's still about guessing, hoping, praying, that things go as expected but at least for these browsers we can run all our tests against them and be sure that things are at least similar.&lt;br /&gt;I am not talking about pixel perfection, that is bad as well in most of the Web related cases, I am talking about providing a decent experience in your Web application/software/page that strongly relies into JavaScript and that without it cannot possibly work.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;Few things must be re-considered in the current Web era. Kangax already explained that &lt;a href="http://perfectionkills.com/extending-built-in-native-objects-evil-or-not/"&gt;things today are different&lt;/a&gt;, regarding native prototype pollutions and specially via &lt;em&gt;Object.defineProperty&lt;/em&gt; and the non enumerable flag but for years we have been all convinced that extending those proto was absolutely something to avoid.&lt;br /&gt;Well, as I agree with Juriy about latter topic, I am still a problem solver that does not exclude any possibility, including User Agent sniffing, when it comes to &lt;strong&gt;solve a real world problem&lt;/strong&gt;, rather than have fantasies about ideals that unfortunately do not reflect reality on our daily basis web development role.&lt;br /&gt;&lt;br /&gt;Just think about it ;)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-7923066140429273468?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/7923066140429273468/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=7923066140429273468' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7923066140429273468'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7923066140429273468'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/10/on-user-agent-sniffing.html' title='On User Agent Sniffing'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-8781151831894657341</id><published>2011-10-25T21:51:00.003+02:00</published><updated>2011-10-25T22:00:09.733+02:00</updated><title type='text'>JS getCSSPropertyName Function</title><content type='html'>I was re-checking &lt;a href="http://twitter.com/LeaVerou"&gt;@LeaVerou&lt;/a&gt; talk at jsconf.eu looking forward to see mine there too to understand how to improve and specially what the hell I have said for 45 minutes :D&lt;br /&gt;&lt;br /&gt;Lea made many valid points in &lt;a href="http://blip.tv/jsconfeu/lea-verou-polyfilling-the-gaps-5668145"&gt;her presentation&lt;/a&gt; but as is for &lt;em&gt;supports.property&lt;/em&gt; case, you never want to go too deep into a single point of your talk so ... here I come.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;getCSSPropertyName Function&lt;/h3&gt;This function aim is to understand if the current browser supports a generic CSS property. If property is supported, the whole name included prefix will be returned.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var getCSSPropertyName = (function () {&lt;br /&gt;    var&lt;br /&gt;        prefixes = ["", "-webkit-", "-moz-", "-ms-", "-o-", "-khtml-"],&lt;br /&gt;        dummy = document.createElement("_"),&lt;br /&gt;        style = dummy.style,&lt;br /&gt;        cache = {},&lt;br /&gt;        length = prefixes.length,&lt;br /&gt;        i = 0,&lt;br /&gt;        pre&lt;br /&gt;    ;&lt;br /&gt;    function testThat(name) {&lt;br /&gt;        for (i = 0; i &amp;lt; length; ++i) {&lt;br /&gt;            pre = prefixes[i] + name;&lt;br /&gt;            if (&lt;br /&gt;                pre in style || (&lt;br /&gt;                    (style.cssText = pre + ":inherit") &amp;&amp;&lt;br /&gt;                    style.getPropertyValue(pre)&lt;br /&gt;                )&lt;br /&gt;            ) return pre;&lt;br /&gt;        }&lt;br /&gt;        return null;&lt;br /&gt;    }&lt;br /&gt;    return function getCSSPropertyName(name) {&lt;br /&gt;        return cache.hasOwnProperty(name) ?&lt;br /&gt;            cache[name] :&lt;br /&gt;            cache[name] = testThat(name)&lt;br /&gt;        ;&lt;br /&gt;    };&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The function returns a string or null, if no property has been found.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// enable HW acceleration&lt;br /&gt;var cssPropertyName = getCSSPropertyName("transform");&lt;br /&gt;if (cssPropertyName != null) {&lt;br /&gt;    node.style.cssText += cssPropertyName + ":translate3d(0,0,0);";&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Please feel free to test this function and let me know if something went wrong, thanks ;-)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-8781151831894657341?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/8781151831894657341/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=8781151831894657341' title='5 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/8781151831894657341'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/8781151831894657341'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/10/js-getcsspropertyname-function.html' title='JS getCSSPropertyName Function'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>5</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-5623774948951873390</id><published>2011-10-20T21:25:00.006+02:00</published><updated>2011-10-20T21:32:05.381+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='wru'/><category scheme='http://www.blogger.com/atom/ns#' term='Unit Test'/><category scheme='http://www.blogger.com/atom/ns#' term='JavaScirpt'/><category scheme='http://www.blogger.com/atom/ns#' term='easy'/><title type='text'>My BerlinJS Slides</title><content type='html'>It was a great event today at &lt;a href="http://twitter.com/co_up"&gt;@co_up&lt;/a&gt; in &lt;a href="http://twitter.com/berlinjs"&gt;@berlinjs&lt;/a&gt; meet-up and &lt;a href="http://www.3site.eu/wru.pdf"&gt;here are my sides&lt;/a&gt; about &lt;strong&gt;wru&lt;/strong&gt; which accordingly with today meeting means &lt;em&gt;where are you&lt;/em&gt;, directly out of SMS syntax.&lt;br /&gt;&lt;br /&gt;Enjoy ;)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-5623774948951873390?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/5623774948951873390/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=5623774948951873390' title='5 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/5623774948951873390'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/5623774948951873390'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/10/jsberlin-slides.html' title='My BerlinJS Slides'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>5</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-8349619330375041121</id><published>2011-10-20T07:32:00.002+02:00</published><updated>2011-10-20T07:51:35.157+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='fun'/><category scheme='http://www.blogger.com/atom/ns#' term='DOM'/><title type='text'>Playing With DOM And ES5</title><content type='html'>A quick fun post about "&lt;i&gt;how would you solve this real world problem&lt;/i&gt;".&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Problem&lt;/h3&gt;Given a generic array of strings, create an unordered list of items where each item contains the text of the relative array index without creating a singe leak or reference during the whole procedure.&lt;br /&gt;As plus, make each item in the list clickable so that an &lt;i&gt;alert&lt;/i&gt; with current text content occur once clicked.&lt;br /&gt;&lt;br /&gt;The assumption is that we are in a standard W3C environment with ES5+ support.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Reason&lt;/h3&gt;I think is one of the most common tasks in Ajax world. We receive an array with some info, we want to display this info to the user and we want to react once the user interact with the list.&lt;br /&gt;If we manage to avoid references we are safer about leaks. If we manage to optimize the procedure, we are also safe about memory consumption over a simplified DOM logic ... &lt;br /&gt;How would you solve this ? Give it a try, then come back for my solution.&lt;br /&gt;&lt;br /&gt;&lt;img src="http://www.3site.eu/images/monkey-on-computer.jpg" /&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Solution&lt;/h3&gt;Here mine:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;document.body.appendChild(&lt;br /&gt;  /* input */["a","b","c"].map(&lt;br /&gt;    function (s, i) {&lt;br /&gt;      this.appendChild(&lt;br /&gt;        document.createElement("li")&lt;br /&gt;      ).textContent = s;&lt;br /&gt;      return this;&lt;br /&gt;    },&lt;br /&gt;    document.createElement("ul")&lt;br /&gt;  )[0]&lt;br /&gt;).addEventListener(&lt;br /&gt;  "click",&lt;br /&gt;  function (e) {&lt;br /&gt;    if (e.target.nodeName === "LI") {&lt;br /&gt;      alert(e.target.textContent);&lt;br /&gt;    }&lt;br /&gt;  },&lt;br /&gt;  false&lt;br /&gt;);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Did you solve it the same way ? :)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-8349619330375041121?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/8349619330375041121/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=8349619330375041121' title='9 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/8349619330375041121'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/8349619330375041121'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/10/playing-with-dom-and-es5.html' title='Playing With DOM And ES5'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>9</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-6475054649811876136</id><published>2011-10-19T01:05:00.007+02:00</published><updated>2011-10-19T01:58:19.570+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Object'/><category scheme='http://www.blogger.com/atom/ns#' term='configurable'/><category scheme='http://www.blogger.com/atom/ns#' term='enumerable'/><category scheme='http://www.blogger.com/atom/ns#' term='writable'/><category scheme='http://www.blogger.com/atom/ns#' term='defineProperty'/><title type='text'>Do You Really Know Object.defineProperty ?</title><content type='html'>I am talking about &lt;em&gt;enumerable&lt;/em&gt;, &lt;em&gt;configurable&lt;/em&gt;, and &lt;em&gt;writable&lt;/em&gt; properties of a generic property descriptor.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;enumerable&lt;/h3&gt;most likely the only one we all expect: if false, a classic &lt;em&gt;for/in&lt;/em&gt; loop will not expose the property, otherwise it will. &lt;em&gt;enumerable&lt;/em&gt; is false by default.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;writable&lt;/h3&gt;just a bit more tricky than we think. Nowadays, if a property is defined as non writable, no error will occur the moment we'll try to change this property:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var o = {};&lt;br /&gt;Object.defineProperty(o, "test", {&lt;br /&gt;  writable: false,&lt;br /&gt;  value: 123&lt;br /&gt;});&lt;br /&gt;o.test; // 123&lt;br /&gt;o.test = 456; // no error at all&lt;br /&gt;o.test; // 123&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;So the property is not writable but nothing happens unless we try to redefine that property.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;Object.defineProperty(o, "test", {&lt;br /&gt;  writable: false,&lt;br /&gt;  value: 456&lt;br /&gt;});&lt;br /&gt;// throws&lt;br /&gt;// Attempting to change value of a readonly property.&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Got it ? Every time we would like to set a property of an unknown object, or one shared in an environment we don't trust, either we use a &lt;em&gt;try/catch&lt;/em&gt; plus double check, or we must be sure that &lt;em&gt;Object.getOwnPropertyDescriptor(o, "test").writable&lt;/em&gt; is &lt;strong&gt;true&lt;/strong&gt;.&lt;br /&gt;&lt;em&gt;writable&lt;/em&gt; is false by default too.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;configurable&lt;/h3&gt;This is the wicked one ... what would you expect from configurable ?&lt;ul&gt;&lt;li&gt;I cannot set a different type of value&lt;/li&gt;&lt;li&gt;I cannot re-configure the descriptor&lt;/li&gt;&lt;/ul&gt;&lt;strong&gt;Fail in both cases&lt;/strong&gt; since things are a bit different on real world. Take this example:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var o = Object.defineProperty({}, "test", {&lt;br /&gt;  enumerable: false,&lt;br /&gt;  writable: true,&lt;br /&gt;  configurable: false, // note, it's false&lt;br /&gt;  value: 123&lt;br /&gt;});&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Do you think this would be possible ?&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;Object.defineProperty(o, "test", {&lt;br /&gt;  enumerable: false,&lt;br /&gt;  writable: false, // note, this is false only now&lt;br /&gt;  configurable: false,&lt;br /&gt;  value: "456" // note, type and value is different&lt;br /&gt;});&lt;br /&gt;&lt;br /&gt;// did I re-configure it ?&lt;br /&gt;o.test === "456"; // true !!!&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Good, so a variable that is writable can be reconfigured on writable attribute and on its type.&lt;br /&gt;The only attribute that cannot be changed, once flagged as configurable and bear in mind that &lt;em&gt;false&lt;/em&gt; is the default, is &lt;em&gt;configurable&lt;/em&gt; itself plus &lt;em&gt;enumerable&lt;/em&gt;.&lt;br /&gt;Also &lt;em&gt;writable&lt;/em&gt; is false by default.&lt;br /&gt;This inconsistency about &lt;em&gt;configurable&lt;/em&gt; seems to be pretty much cross platform and probably meant ... why ?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Brainstorming&lt;/h3&gt;If I can't change the value the descriptor must be &lt;em&gt;configurable&lt;/em&gt; at least on &lt;em&gt;writable&lt;/em&gt; property ... no wait, if I can set the value as not &lt;em&gt;writable&lt;/em&gt; then &lt;em&gt;configurable&lt;/em&gt; should be set as false otherwise it will loose its own meaning ... no, wait ... &lt;br /&gt;&lt;br /&gt;&lt;h3&gt;How It Is&lt;/h3&gt;&lt;em&gt;writable&lt;/em&gt; is the exception that confirms the rule. If &lt;em&gt;true&lt;/em&gt;, writable can always be configurable while if &lt;em&gt;false&lt;/em&gt;, &lt;em&gt;writable&lt;/em&gt; becomes automatically &lt;em&gt;not configurable&lt;/em&gt; and the same is true for both &lt;em&gt;get&lt;/em&gt; and &lt;em&gt;set&lt;/em&gt; properties ... these acts as &lt;em&gt;writable: false&lt;/em&gt; no matters how &lt;em&gt;configurble&lt;/em&gt; is set.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;How Is It If We Do Not Define&lt;/h3&gt;&lt;pre class="code"&gt;&lt;br /&gt;// simple object&lt;br /&gt;var o = {};&lt;br /&gt;&lt;br /&gt;// simple assignment&lt;br /&gt;o.test = 123;&lt;br /&gt;&lt;br /&gt;// equivalent in Object.defineProperty world&lt;br /&gt;Object.defineProperty(o, "test", {&lt;br /&gt;  configurable: true,&lt;br /&gt;  writable: true,&lt;br /&gt;  enumerable: true,&lt;br /&gt;  value: 123&lt;br /&gt;});&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Thanks to &lt;a href="http://twitter.com/jdalton"&gt;@jdalton&lt;/a&gt; to point few hints out.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;The &lt;em&gt;configurable&lt;/em&gt; property works as expected with &lt;em&gt;configurable&lt;/em&gt; itself and &lt;strong&gt;only&lt;/strong&gt; with &lt;em&gt;enumerable&lt;/em&gt; one.&lt;br /&gt;If we think that &lt;em&gt;writable&lt;/em&gt; has anything to do with both of them we are wrong ... at least now we know.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-6475054649811876136?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/6475054649811876136/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=6475054649811876136' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/6475054649811876136'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/6475054649811876136'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/10/do-you-really-know-objectdefineproperty.html' title='Do You Really Know Object.defineProperty ?'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-2889867172226370799</id><published>2011-10-16T13:49:00.003+02:00</published><updated>2011-10-16T14:24:51.563+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='programming'/><category scheme='http://www.blogger.com/atom/ns#' term='LLVM'/><category scheme='http://www.blogger.com/atom/ns#' term='languages'/><category scheme='http://www.blogger.com/atom/ns#' term='scripting'/><title type='text'>The Missing Tool In Scripting World</title><content type='html'>Few days ago I was having beers with &lt;a href="http://twitter.com/aadsm"&gt;@aadsm&lt;/a&gt; and &lt;a href="http://twitter.com/sleistner"&gt;@sleistner&lt;/a&gt; and we were talking about languages and, of course, JavaScript too.&lt;br /&gt;That night I have realized there is a missing process, or better tool, that could open new doors for JavaScript world.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Runtime Nightmare&lt;/h3&gt;The main difference between scripting languages and statically typed one is the inability to pre optimize or pre compile the code before it's actually executed.&lt;br /&gt;Engineers from different companies are trying on daily basis to perform this optimization at runtime, or better Just In Time, but believe me that's not easy task, specially with such highly dynamic language as JavaScript is.&lt;br /&gt;Even worst task is the tracing option: at runtime each reference is tracked and if its type does not change during its lifecycle, the code could be compiled as native one.&lt;br /&gt;The moment a type, an object structure, or a property changes, the tracer has to compile twice or split the optimizations up to N exponential changed performed in a single loop so that this tracer has to be smart enough to understand when it's actually worth it to perform such optimization, or when it's time to drop everything and optimize only sub tasks via JIT.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Static Pros And Cons&lt;/h3&gt;As I have said, statically typed languages can perform all these optimizations upfront and create, as example, &lt;a href="http://de.wikipedia.org/wiki/Low_Level_Virtual_Machine"&gt;LLVM&lt;/a&gt; byte code which is highly portable and extremely fast. As example, both C and C++ can be compiled into LLVM.&lt;br /&gt;There is also a disadvantage in this process ... if some unexpected input occurs runtime, the whole logic could crash, be compromised, or exit unexpectedly.&lt;br /&gt;Latter part is what will rarely happen in scripting world, but it can be also a weak point for application stability and reliability since things may keep going but who knows what kind of disaster an unexpected input could cause.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;What If ...&lt;/h3&gt;Try to imagine we have created unit tests for a whole application or, why not, just for a portion of it (module).&lt;br /&gt;Try to imagine these tests cover 100% of code, a really hard achievement on web due feature detections and different browsers behaviors, but absolutely easy task in node.js, Rhino, CouchDB, or any JS code that runs in a well known environment.&lt;br /&gt;The differential Mocking approach to solve the web situation requires time and effort but also what JS community is rarely doing, as example, is to share mocks of same native objects in both JS and DOM world. This should change, imo, because I have no idea how many different mocks of XMLHttpRequest or document we have out there and still there is no standard way to define a mock and listen to mocked methods or properties changes in a cross platform way.&lt;br /&gt;Let's keep trying imagine now ... imagine that our tests cover all possible input accepted in each part of the module.&lt;br /&gt;Try to imagine that our tests cover exactly how the application should behave, accordingly with all possible input we want to accept.&lt;br /&gt;It's insane to use typeof or instance of operator per each argument of each function .... this will kill performances, what is not impossible is to do it in a way that, once in production, &lt;a href="http://webreflection.blogspot.com/2010/08/objectdefineproperty-but-strict.html"&gt;these checks are dropped&lt;/a&gt;.&lt;br /&gt;Since with non tested input we can have unexpected behaviors, I would say that our application &lt;strong&gt;should fail&lt;/strong&gt; or exit the moment something untested occurs .... don't you agree?&lt;br /&gt;How many less buggy web apps we would have out there ? How much more stable and trustable could we be ?&lt;br /&gt;The process I am describing does not exist even in statically typed languages since in that case developers trust unconditionally the compiler, avoiding runtime misbehavior tests ... isn't it ?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Point Is ...&lt;/h3&gt;We wrote our code, we created 100% of code coverage and we created 100% of expected inputs coverage. At this point the only thing we are missing to &lt;strong&gt;compile JavaScript into LLVM&lt;/strong&gt; is a tool that will trace, and trace only, the test while it's executed and will be able to analyze all cases, all types, all meant behaviors, all loops, and all function calls, so that everything could be statically compiled and in separate modules ... how great would this be if possible today?&lt;br /&gt;&lt;br /&gt;Just try to imagine ...&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-2889867172226370799?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/2889867172226370799/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=2889867172226370799' title='8 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/2889867172226370799'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/2889867172226370799'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/10/missing-tool-in-scripting-world.html' title='The Missing Tool In Scripting World'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>8</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-532364624897524069</id><published>2011-10-15T14:27:00.004+02:00</published><updated>2011-10-15T14:55:56.335+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='define'/><category scheme='http://www.blogger.com/atom/ns#' term='defineProperties'/><title type='text'>Object.prototype.define Proposal</title><content type='html'>Somebody may think that &lt;a href="http://twitter.com/angusTweets/status/124950664852942848"&gt;defineProperties is boring&lt;/a&gt; and I kinda agree on that.&lt;br /&gt;&lt;br /&gt;The good news is that JavaScript is flexible enough to let you decide how to do that ... and here I am with a simple proposal that does not hurt, but can make life easier and more intuitive in modern JS environments.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Unobtrusive Object.prototype.define&lt;/h3&gt;&lt;br /&gt;&lt;script src="https://gist.github.com/1289401.js?file=Object.prototype.define.js"&gt;&lt;/script&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;How To&lt;/h3&gt;Well, the handy way you expect.&lt;br /&gt;The method returns the object itself, so it is possible to define one or more property runtime and chain different kind of definitions, as example splitting properties from method and protected properties from protected methods.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var o = {}.define("test", "OK");&lt;br /&gt;o.test; // OK&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Multiple properties can share same defaults:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var o = {}.define(["name", "_name"], "unknown");&lt;br /&gt;o.a; // unknown&lt;br /&gt;o._a; // unknown&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Methods are immutable by default and properties or methods prefixed with an underscore are by default not enumerable.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;function Person() {}&lt;br /&gt;Person.protoype.define(&lt;br /&gt;  ["getName", "setName", "_name"],&lt;br /&gt;  [&lt;br /&gt;    function getName() {&lt;br /&gt;      return this._name;&lt;br /&gt;    },&lt;br /&gt;    function setName(_name) {&lt;br /&gt;      this._name = _name;&lt;br /&gt;    },&lt;br /&gt;    "unknown"&lt;br /&gt;  ]&lt;br /&gt;);&lt;br /&gt;&lt;br /&gt;// by convention, _name property is not enumerable&lt;br /&gt;&lt;br /&gt;var me = new Person;&lt;br /&gt;me.getName(); // unknown&lt;br /&gt;&lt;br /&gt;me.setName("WebReflection");&lt;br /&gt;me.getName(); // WebReflection&lt;br /&gt;&lt;br /&gt;for (var key in me) {&lt;br /&gt;  if (key === "_name") {&lt;br /&gt;    throw "this should never happen";&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Last, but not least, if the descriptor is an object you decide how to configure the property.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var iDecide = {}.define("whatIsIt", {&lt;br /&gt;  value:"it does not matter",&lt;br /&gt;  enumerable: false&lt;br /&gt;});&lt;br /&gt;for (var key in iDecide) {&lt;br /&gt;  if (key === whatIsIt) {&lt;br /&gt;    throw "this should never happen";&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;100% Unit Test Code Coverage&lt;/h3&gt;Not such difficult task for such tiny proposal.&lt;br /&gt;&lt;a href="https://gist.github.com/1289486"&gt;This test simply demonstrates the proposal works in all possible meant ways&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;We can always find a better way to do boring things, this is why frameworks, in all sizes and purposes, are great to both use or create. Have fun&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-532364624897524069?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/532364624897524069/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=532364624897524069' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/532364624897524069'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/532364624897524069'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/10/objectprototypedefine-proposal.html' title='Object.prototype.define Proposal'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-7280524229193829201</id><published>2011-10-13T07:23:00.010+02:00</published><updated>2011-10-13T07:53:36.460+02:00</updated><title type='text'>about JS VS VBScript VS Dart</title><content type='html'>You can take it as a joke since this is not a proper comparison of these web programming languages.&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;                                JS      Dart    VBScript&lt;br /&gt;types                           √       √       sort of&lt;br /&gt;getters and setters             √       √       √&lt;br /&gt;immutable objects               √       √       √&lt;br /&gt;prototypal inheritance          √&lt;br /&gt;simulated classes               √&lt;br /&gt;"real" classes                          √       √&lt;br /&gt;closures                        √       √       &lt;br /&gt;weakly bound to JS                      √       √&lt;br /&gt;obtrusive for JS (global)       may be  √       √&lt;br /&gt;obtrusive for JS (prototypes)   may be  √&lt;br /&gt;operator overload                       √&lt;br /&gt;cross browser                   √&lt;br /&gt;real benefits for the Web       √       ?       ?&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;If you are wondering about JS types, we have both weak type and strong type, e.g. Float32Array.&lt;br /&gt;When StructType and ArrayType will be in place then JS will support any sort of type.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-7280524229193829201?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/7280524229193829201/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=7280524229193829201' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7280524229193829201'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7280524229193829201'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/10/about-vbscript-vs-dart.html' title='about JS VS VBScript VS Dart'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-32544485706285370</id><published>2011-10-13T06:18:00.007+02:00</published><updated>2011-10-13T07:04:58.396+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='Dart'/><category scheme='http://www.blogger.com/atom/ns#' term='questions'/><title type='text'>about that post</title><content type='html'>I have been blamed and insulted enough so I removed the possibility to comment and I also invite you again to do not stop reading the title of a generic post here or anywhere around the net.&lt;br /&gt;&lt;br /&gt;I would like to summarize few parts of that post:&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;on real world we should use the proper flag in order to generate files where only necessary parts of the library is included&lt;br /&gt;...&lt;br /&gt;I agree that at this stage can be premature to judge the quality of Dart code, once translated for JavaSript world&lt;br /&gt;...&lt;br /&gt;Google is a great company loads of ultra skilled Engineers&lt;br /&gt;...&lt;br /&gt;&lt;i&gt;n.d. I have proposed &lt;a href="https://code.google.com/p/dart/issues/detail?id=79"&gt;a fix&lt;/a&gt; for Dart code&lt;/i&gt;&lt;br /&gt;...&lt;br /&gt;you may realize how much overhead exists in Dart once this is used in non Dart capable browsers&lt;br /&gt;...&lt;br /&gt;Was operator overload the reason the web sucks as it is?&lt;br /&gt;...&lt;br /&gt;everything 2 up to 10 times slower for devices, specially older one, that will never see a native Dart engine in core&lt;br /&gt;...&lt;br /&gt;Not Really What We Need Today&lt;br /&gt;...&lt;br /&gt;What are the performances boost that V8 or WebCL will never achieve ? &lt;br /&gt;...&lt;br /&gt;What is the WebCL status in Chromium ?&lt;br /&gt;...&lt;br /&gt;Where is a native CoffeeScript VM if syntax was the problem ?&lt;br /&gt;...&lt;br /&gt;Doesn't this Dart language look like the VBScript of 2011 ?&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;You can understand the whole post is not about the number of lines, it's indeed about what this extra layer means today for the current web.&lt;br /&gt;&lt;br /&gt;I beg you to please answer my questions, any of them, so that I can understand reasons behind Dart decision.&lt;br /&gt;&lt;br /&gt;I have also always admired Google and its Engineers, and I am asking, after GWT and Dart, why many of them seem to be so hostile against JavaScript, the programming language that made Google "fortune" on the web ( gmail, adsense, and all successful stories about Google using massively JavaScript )&lt;br /&gt;&lt;br /&gt;Thanks for your patience and please accept my apologies since I followed the blaming mood rather than ignore it or better explain what I meant.&lt;br /&gt;&lt;br /&gt;All of this is for a better web or a better future of the web, none of this should fall down into insults.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-32544485706285370?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://webreflection.blogspot.com/2011/10/what-is-wrong-about-17259-lines-of-code.html' title='about that post'/><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/32544485706285370/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=32544485706285370' title='9 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/32544485706285370'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/32544485706285370'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/10/about-that-post.html' title='about that post'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>9</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-4244447587942464311</id><published>2011-10-12T07:34:00.022+02:00</published><updated>2011-10-13T06:17:47.431+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='first'/><category scheme='http://www.blogger.com/atom/ns#' term='look'/><category scheme='http://www.blogger.com/atom/ns#' term='Dart'/><title type='text'>What Is Wrong About 17259 Lines Of Code</title><content type='html'>Is the most popular, somehow pointless, and often funny &lt;a href="https://gist.github.com/1277224"&gt;gist&lt;/a&gt; of these days.&lt;br /&gt;&lt;br /&gt;It's about &lt;a href="http://www.dartlang.org/"&gt;Dart&lt;/a&gt;, the JavaScript alternative proposed by Google.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Why So Many Lines Of Code&lt;/h3&gt;The reason a simple &lt;em&gt;"Hello World"&lt;/em&gt; contains such amount of code is because:&lt;ol&gt;&lt;li&gt;the whole library core is included and not minified/optimized but on real world we should use the proper flag in order to generate files where only necessary parts of the library is included&lt;/li&gt;&lt;li&gt;whoever created such core library did not think about optimizing his code&lt;/li&gt;&lt;/ol&gt;What am I saying, is that common techniques as code reusability do not seem to be in place at all:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// first 15 lines of Dart core&lt;br /&gt;function native_ArrayFactory__new(typeToken, length) {&lt;br /&gt;  return RTT.setTypeInfo(&lt;br /&gt;      new Array(length), &lt;br /&gt;      Array.$lookupRTT(RTT.getTypeInfo(typeToken).typeArgs));&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;function native_ListFactory__new(typeToken, length) {&lt;br /&gt;  return RTT.setTypeInfo(&lt;br /&gt;      new Array(length), &lt;br /&gt;      Array.$lookupRTT(RTT.getTypeInfo(typeToken).typeArgs));&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;ListFactory is nothing, I repeat, nothing different from an Array and since the whole core is based on &lt;i&gt;weird&lt;/i&gt; naming convention, nothing could have been wrong so far doing something like:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// dropped 4 lines of library core&lt;br /&gt;var native_ListFactory__new = native_ArrayFactory__new;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Please note methods such &lt;em&gt;Array.$lookupRTT&lt;/em&gt; and bear in mind that Dart does not work well together with JavaScript libraries since native constructors and their prototypes seem to be polluted in all possible ways.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Not Only Redundant Or Obtrusive Code&lt;/h3&gt;While I agree that at this stage can be premature to judge the quality of Dart code, once translated for JavaSript world, is really not the firt time &lt;a href="http://webreflection.blogspot.com/2009/11/google-closure-im-not-impressed.html"&gt;I am not impressed&lt;/a&gt; about JavaScript code proposed by Google.&lt;br /&gt;Google is a great company loads of ultra skilled Engineers. Unfortunately it looks like few of them have excellent JavaScript skills and most likely they were not involved into this Dart project ( I have been too hard here but I have never really seen gems in google JS libraries )&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// line 56 of Dart core&lt;br /&gt;function native_BoolImplementation_EQ(other) {&lt;br /&gt;  if (typeof other == 'boolean') {&lt;br /&gt;    return this == other;&lt;br /&gt;  } else if (other instanceof Boolean) {&lt;br /&gt;    // Must convert other to a primitive for value equality to work&lt;br /&gt;    return this == Boolean(other);&lt;br /&gt;  } else {&lt;br /&gt;    return false;&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;// how I would have written that&lt;br /&gt;function native_BoolImplementation_EQ(other) {&lt;br /&gt;  return this == Boolean(other);&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Please note that &lt;a href="https://code.google.com/p/dart/issues/detail?id=79"&gt;both fails&lt;/a&gt; somehow ..&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;native_BoolImplementation_EQ.call(true, new Boolean(false)) // true&lt;br /&gt;// so that new Boolean(false) is EQ new Boolean(true)&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;... while if performances were the problem bear with me and look what Dart came up with ...&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;124 Lines Of Bindings&lt;/h3&gt;&lt;a href="https://gist.github.com/1277224#L80"&gt;Line 80&lt;/a&gt; starts with:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// Optimized versions of closure bindings.&lt;br /&gt;// Name convention: $bind&lt;number-of-scopes&gt;_&lt;number-of-arguments&gt;(fn, this, scopes, args)&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;... and it cannot go further any different from what you would never expect ...&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;function $bind0_0(fn, thisObj) {&lt;br /&gt;  return function() {&lt;br /&gt;    return fn.call(thisObj);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind0_1(fn, thisObj) {&lt;br /&gt;  return function(arg) {&lt;br /&gt;    return fn.call(thisObj, arg);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind0_2(fn, thisObj) {&lt;br /&gt;  return function(arg1, arg2) {&lt;br /&gt;    return fn.call(thisObj, arg1, arg2);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind0_3(fn, thisObj) {&lt;br /&gt;  return function(arg1, arg2, arg3) {&lt;br /&gt;    return fn.call(thisObj, arg1, arg2, arg3);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind0_4(fn, thisObj) {&lt;br /&gt;  return function(arg1, arg2, arg3, arg4) {&lt;br /&gt;    return fn.call(thisObj, arg1, arg2, arg3, arg4);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind0_5(fn, thisObj) {&lt;br /&gt;  return function(arg1, arg2, arg3, arg4, arg5) {&lt;br /&gt;    return fn.call(thisObj, arg1, arg2, arg3, arg4, arg5);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;function $bind1_0(fn, thisObj, scope) {&lt;br /&gt;  return function() {&lt;br /&gt;    return fn.call(thisObj, scope);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind1_1(fn, thisObj, scope) {&lt;br /&gt;  return function(arg) {&lt;br /&gt;    return fn.call(thisObj, scope, arg);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind1_2(fn, thisObj, scope) {&lt;br /&gt;  return function(arg1, arg2) {&lt;br /&gt;    return fn.call(thisObj, scope, arg1, arg2);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind1_3(fn, thisObj, scope) {&lt;br /&gt;  return function(arg1, arg2, arg3) {&lt;br /&gt;    return fn.call(thisObj, scope, arg1, arg2, arg3);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind1_4(fn, thisObj, scope) {&lt;br /&gt;  return function(arg1, arg2, arg3, arg4) {&lt;br /&gt;    return fn.call(thisObj, scope, arg1, arg2, arg3, arg4);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind1_5(fn, thisObj, scope) {&lt;br /&gt;  return function(arg1, arg2, arg3, arg4, arg5) {&lt;br /&gt;    return fn.call(thisObj, scope, arg1, arg2, arg3, arg4, arg5);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;function $bind2_0(fn, thisObj, scope1, scope2) {&lt;br /&gt;  return function() {&lt;br /&gt;    return fn.call(thisObj, scope1, scope2);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind2_1(fn, thisObj, scope1, scope2) {&lt;br /&gt;  return function(arg) {&lt;br /&gt;    return fn.call(thisObj, scope1, scope2, arg);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind2_2(fn, thisObj, scope1, scope2) {&lt;br /&gt;  return function(arg1, arg2) {&lt;br /&gt;    return fn.call(thisObj, scope1, scope2, arg1, arg2);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind2_3(fn, thisObj, scope1, scope2) {&lt;br /&gt;  return function(arg1, arg2, arg3) {&lt;br /&gt;    return fn.call(thisObj, scope1, scope2, arg1, arg2, arg3);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind2_4(fn, thisObj, scope1, scope2) {&lt;br /&gt;  return function(arg1, arg2, arg3, arg4) {&lt;br /&gt;    return fn.call(thisObj, scope1, scope2, arg1, arg2, arg3, arg4);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind2_5(fn, thisObj, scope1, scope2) {&lt;br /&gt;  return function(arg1, arg2, arg3, arg4, arg5) {&lt;br /&gt;    return fn.call(thisObj, scope1, scope2, arg1, arg2, arg3, arg4, arg5);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;function $bind3_0(fn, thisObj, scope1, scope2, scope3) {&lt;br /&gt;  return function() {&lt;br /&gt;    return fn.call(thisObj, scope1, scope2, scope3);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind3_1(fn, thisObj, scope1, scope2, scope3) {&lt;br /&gt;  return function(arg) {&lt;br /&gt;    return fn.call(thisObj, scope1, scope2, scope3, arg);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind3_2(fn, thisObj, scope1, scope2, scope3) {&lt;br /&gt;  return function(arg1, arg2) {&lt;br /&gt;    return fn.call(thisObj, scope1, scope2, arg1, arg2);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind3_3(fn, thisObj, scope1, scope2, scope3) {&lt;br /&gt;  return function(arg1, arg2, arg3) {&lt;br /&gt;    return fn.call(thisObj, scope1, scope2, scope3, arg1, arg2, arg3);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind3_4(fn, thisObj, scope1, scope2, scope3) {&lt;br /&gt;  return function(arg1, arg2, arg3, arg4) {&lt;br /&gt;    return fn.call(thisObj, scope1, scope2, scope3, arg1, arg2, arg3, arg4);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;function $bind3_5(fn, thisObj, scope1, scope2, scope3) {&lt;br /&gt;  return function(arg1, arg2, arg3, arg4, arg5) {&lt;br /&gt;    return fn.call(thisObj, scope1, scope2, scope3, arg1, arg2, arg3, arg4, arg5);&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;I really don't want to comment above code but here the thing:&lt;blockquote&gt;&lt;br /&gt;&lt;strong&gt;Dear Google Engineers&lt;/strong&gt;,&lt;br /&gt;  while I am pretty sure you all know the meaning of &lt;em&gt;apply&lt;/em&gt;, I wonder if you truly needed to bring such amount of code with "&lt;em&gt;optimization&lt;/em&gt;" in mind for a language translated into something that requires functions calls all over the place even to assign a single index to an array object&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;No fools guys, if you see functions like this:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;function native_ObjectArray__indexAssignOperator(index, value) {&lt;br /&gt;  this[index] = value;&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;you may realize how much overhead exists in Dart once this is used in non Dart capable browsers.&lt;br /&gt;These browsers will do, most likely, something like this:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;try {&lt;br /&gt;  if (-1 &lt; $inlineArrayIndexCheck(object, i)) {&lt;br /&gt;    native_ObjectArray__indexAssignOperator.call(object, i, value);&lt;br /&gt;    // or object.native_ObjectArray__indexAssignOperator(i, value)&lt;br /&gt;  }&lt;br /&gt;} catch(e) {&lt;br /&gt;  if (native_ObjectArray_get$length.call(object) &lt;= i) {&lt;br /&gt;    native_ObjectArray__setLength.call(object, i + 1);&lt;br /&gt;  }&lt;br /&gt;  try {&lt;br /&gt;    native_ObjectArray__indexAssignOperator.call(object, i, value);&lt;br /&gt;  } catch(e) {&lt;br /&gt;    // oh well ...&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;rather than:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;object[i] = value;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Early Stage For Optimizations&lt;/h3&gt;This is a partial lie because premature or unnecessary optimizations are all over the place. 120 lines of binding for a core library that will be &lt;a href="http://jsperf.com/dart-hello-world"&gt;slower not only on startup&lt;/a&gt; but during the whole lifecycle of the program cannot solve really a thing, isn't it?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Cost Of The Operator Overload&lt;/h3&gt;This is a cool feature representing other 150 lines of code so that something like this:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;1 + 2; // 3&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;will execute most likely this:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// well not this one ...&lt;br /&gt;function ADD$operator(val1, val2) {&lt;br /&gt;  return (typeof(val1) == 'number' &amp;&amp; typeof(val2) == 'number')&lt;br /&gt;      ? val1 + val2&lt;br /&gt;      : val1.ADD$operator(val2);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;// but this&lt;br /&gt;ADD$operator(1, 2); // 3&lt;br /&gt;&lt;br /&gt;// with recursive calls to the function itself if ...&lt;br /&gt;ADD$operator(new Number(1), new Number(2));&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;I am sure we all can sleep properly now that operators overload landed on the web, a feature that works nice with matrixes and vertexes as shortcut for multiplication is finally able to slow down every single addiction.&lt;br /&gt;Did we really need this? Was operator overload the reason the web sucks as it is?&lt;br /&gt;If so, I can't wait to see PHP moving into the same direction directly in core!&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Which Problem Would Dart Solve&lt;/h3&gt;I am at line 397 out of 17259 and I cannot go further than this right now but I think I have seen enough.&lt;br /&gt;I have heard/read about Dart aim which apparently is "&lt;em&gt;to solve mobile browsers fragmentation&lt;/em&gt;".&lt;br /&gt;Of course, mobile browsers, those already penalized by all possible non performances oriented practices, those browsers with the lower computation power ever, will basically &lt;strong&gt;die&lt;/strong&gt; if there is no native Dart engine ... everything 2 up to 10 times slower for devices, specially older one, that will never see a native Dart engine in core and that for this reason will have to:&lt;ul&gt;&lt;li&gt;download the normal page ignoring the script application/dart&lt;/li&gt;&lt;li&gt;download via JavaScript the whole Dart transpiler&lt;/li&gt;&lt;li&gt;once loaded, grab all script nodes with type application/dart&lt;/li&gt;&lt;li&gt;translate each node into JavaScript through the transpiler&lt;/li&gt;&lt;li&gt;inject the Dart library core and inject every script&lt;/li&gt;&lt;/ul&gt;From the company that did not close the body tag in its primary page in order to have fastest startup/visualization ever, don't ya think above procedure is a bit too much for a poor Android 2.2 browser?&lt;br /&gt;Bear in mind mobile browsers are already up to 100 times slower on daily web tasks than browsers present on Desktop.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Not Really What We Need Today&lt;/h3&gt;I keep &lt;i&gt;fighting&lt;/i&gt; about what's truly needed on the web and I have said already &lt;strong&gt;surely not a new programming language&lt;/strong&gt; ( and also ... guys you had already GWT, isn't it ? ).&lt;br /&gt;I would enormously appreciate if anyone from Google will explain me why Dart was so needed and what kind of benefits can it bring today.&lt;br /&gt;I can see a very long therm idea behind but still, why we all have to start from the scratch breaking everything we published and everything we know about web so far ?&lt;br /&gt;Why this team of 10 or 30 developers did not help V8 one to bring StructType and ArrayType and boost up inferences in JavaScript ?&lt;br /&gt;Why Dart ? What are the performances boost that V8 or WebCL will never achieve ? What is the WebCL status in Chromium ?&lt;br /&gt;Where is a native CoffeeScript VM if syntax was the problem ?&lt;br /&gt;... and many more questions ... thanks for your patience.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;update&lt;/strong&gt; ... I have to ask this too: &lt;br /&gt;Doesn't this Dart language look like the VBScript of 2011 ?&lt;br /&gt;Wasn't VBScript an &lt;strong&gt;Epic Fail&lt;/strong&gt; ?&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-4244447587942464311?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/4244447587942464311'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/4244447587942464311'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/10/what-is-wrong-about-17259-lines-of-code.html' title='What Is Wrong About 17259 Lines Of Code'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-2905615500859667542</id><published>2011-10-09T12:45:00.005+02:00</published><updated>2011-10-09T12:51:34.319+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='function'/><category scheme='http://www.blogger.com/atom/ns#' term='batman'/><title type='text'>Taking The Bat-Formula To The Next Level</title><content type='html'>When you wake up on Sunday morning with upside-down stomach and &lt;a href="http://twitter.com/#!/WebReflection/status/122964409390874624"&gt;batcode&lt;/a&gt; in mind, you may realize it's time to rest a bit.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;with (/*Bat*/Math) Array(16).join(&lt;br /&gt;  pow(/*JOK*/E/*R*/, cos, E/*vil*/)&lt;br /&gt;) + "batman";&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The output is the same produced by the &lt;a href="http://twitter.com/#!/frontendstuff/status/121996485578588160"&gt;original bat-formula&lt;/a&gt;:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;'NaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNNaNbatman'&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Have a nice Sunday.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-2905615500859667542?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/2905615500859667542/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=2905615500859667542' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/2905615500859667542'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/2905615500859667542'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/10/taking-bat-formula-to-next-level.html' title='Taking The Bat-Formula To The Next Level'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-5049177414703923488</id><published>2011-10-09T11:48:00.007+02:00</published><updated>2011-10-09T15:09:13.364+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='PHP'/><category scheme='http://www.blogger.com/atom/ns#' term='is_a'/><title type='text'>A Better is_a Function for JS</title><content type='html'>In 2007 I have posted &lt;a href="http://webreflection.blogspot.com/2007/01/javascript-getclass-and-isa-functions.html"&gt;about get_class and is_a&lt;/a&gt; functions in JavaScript in order to simulate original PHP functions.&lt;br /&gt;&lt;br /&gt;Well ... that was crap, since a much simpler and meaningful version of the &lt;em&gt;is_a&lt;/em&gt; function can be easily summarized like this:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var is_a = function () {&lt;br /&gt;  function verify(what) {&lt;br /&gt;    // implicit objet representation&lt;br /&gt;    // the way to test primitives too&lt;br /&gt;    return this instanceof what;&lt;br /&gt;  }&lt;br /&gt;  return function is_a(who, what) {&lt;br /&gt;    // only undefined and null&lt;br /&gt;    // return always false&lt;br /&gt;    return who == null ?&lt;br /&gt;      false :&lt;br /&gt;      verify.call(who, what)&lt;br /&gt;    ;&lt;br /&gt;  };&lt;br /&gt;}();&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;... or even smaller with explicit cast ... &lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;function is_a(who, what) {&lt;br /&gt;  // only undefined and null&lt;br /&gt;  // return always false&lt;br /&gt;  return who == null ?&lt;br /&gt;    false :&lt;br /&gt;    Object(who) instanceof what&lt;br /&gt;  ;&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;An "&lt;i&gt;even smaller&lt;/i&gt;" alternative via &lt;a href="http://twitter.com/kentaromiura"&gt;@kentaromiura&lt;/a&gt;&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;function is_a(who, what) {&lt;br /&gt;  return who != null &amp;&amp; Object(who) instanceof what;&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Here a usage example:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;alert([&lt;br /&gt;  is_a(false, Boolean),   // true&lt;br /&gt;  is_a("", String),       // true&lt;br /&gt;  is_a(123, Number),      // true&lt;br /&gt;  is_a(/r/, RegExp),      // true&lt;br /&gt;  is_a([], Array),        // true&lt;br /&gt;  is_a(null, Object),     // false&lt;br /&gt;  is_a(undefined, Object) // false&lt;br /&gt;]);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;As twitted few minutes ago, an alternative would be to pollute the Object.prototype:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;Object.defineProperty(Object.prototype, "is_a", {&lt;br /&gt;  value: function (constructor) {&lt;br /&gt;    return this instanceof constructor;&lt;br /&gt;  }&lt;br /&gt;});&lt;br /&gt;&lt;br /&gt;// (123).is_a(Number); // true&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;However, this way would not scale with null and undefined so that per each test we need to check them and this is boring.&lt;br /&gt;Finally, I would not worry about cross frame variables since via postMessage everything has to be serialized and unserialized.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-5049177414703923488?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/5049177414703923488/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=5049177414703923488' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/5049177414703923488'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/5049177414703923488'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/10/better-isa-function-for-js.html' title='A Better is_a Function for JS'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-1352700433341455575</id><published>2011-10-06T11:36:00.004+02:00</published><updated>2011-10-08T13:25:28.931+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='node.js'/><category scheme='http://www.blogger.com/atom/ns#' term='require'/><category scheme='http://www.blogger.com/atom/ns#' term='implicit'/><title type='text'>implicit require in node.js</title><content type='html'>playing with Harmony Proxy I came out with a simple snippet:&lt;br /&gt;&lt;br /&gt;&lt;script src="https://gist.github.com/1263932.js?file=module.js"&gt;&lt;/script&gt;&lt;br /&gt;The aim of above snippet is to forget the usage of require ... here some example:&lt;pre class="code"&gt;&lt;br /&gt;module.sys.puts("Hello implicit require");&lt;br /&gt;&lt;br /&gt;var fs = module.fs;&lt;br /&gt;fs.stat( ... );&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;It's compatible with nested namespaces too and if there are non JS chars in the middle ... well:&lt;pre class="code"&gt;var Proxy = module["node-proxy"];&lt;/pre&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-1352700433341455575?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/1352700433341455575/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=1352700433341455575' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/1352700433341455575'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/1352700433341455575'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/10/implicit-require-in-nodejs.html' title='implicit require in node.js'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-1438011157384517427</id><published>2011-10-05T12:27:00.003+02:00</published><updated>2011-10-05T12:35:15.346+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='function'/><category scheme='http://www.blogger.com/atom/ns#' term='call'/><category scheme='http://www.blogger.com/atom/ns#' term='apply'/><category scheme='http://www.blogger.com/atom/ns#' term='bind'/><category scheme='http://www.blogger.com/atom/ns#' term='prototype'/><title type='text'>bind, apply, and call trap</title><content type='html'>quick one out of ECMAScript ml&lt;pre class="code"&gt;&lt;br /&gt;var&lt;br /&gt;    // used to trap function calls via bind&lt;br /&gt;    invoke = Function.call,&lt;br /&gt;    // normal use cases&lt;br /&gt;    bind = invoke.bind(invoke.bind),&lt;br /&gt;    apply = bind(invoke, invoke.apply),&lt;br /&gt;    call = bind(invoke, invoke)&lt;br /&gt;;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;What Is It&lt;/h3&gt;This is a way to trap native functions method in a handy way. Used in a private scope, it can address these methods once so that we can rely nobody can possibly change them out there for some script injection and only if we are sure the script has been loaded at the very beginning.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;How To Use Them&lt;/h3&gt;Here few examples:&lt;pre class="code"&gt;&lt;br /&gt;// secure hasOwnProperty&lt;br /&gt;var hasOwnProperty = bind(invoke, {}.hasOwnProperty);&lt;br /&gt;// later on&lt;br /&gt;hasOwnProperty({key:1}, "key"); // true&lt;br /&gt;hasOwnProperty({}, "key");  // false&lt;br /&gt;&lt;br /&gt;// direct slice&lt;br /&gt;var slice = bind(invoke, [].slice);&lt;br /&gt;slice([1,2,3], 1); // 2,3&lt;br /&gt;slice(arguments); // array&lt;br /&gt;&lt;br /&gt;// direct call&lt;br /&gt;call([].slice, [1,2,3], 1); // 2,3&lt;br /&gt;// direct apply&lt;br /&gt;apply([].slice, [1,2,3], [1]); // 2,3&lt;br /&gt;&lt;br /&gt;// bound method&lt;br /&gt;var o = {name:"WebReflection"};&lt;br /&gt;o.getName = bind(&lt;br /&gt;    // the generic method&lt;br /&gt;    function () {&lt;br /&gt;        return this.name;&lt;br /&gt;    },&lt;br /&gt;    // the object&lt;br /&gt;    o&lt;br /&gt;);&lt;br /&gt;o.getName(); // WebReflection&lt;br /&gt;&lt;/pre&gt;That's pretty much it, except if we don't trust native Function.prototype, we should not trust anything else as well so maybe it's good to use these shortcuts just because they are handy ;)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-1438011157384517427?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/1438011157384517427/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=1438011157384517427' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/1438011157384517427'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/1438011157384517427'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/10/bind-apply-and-call-trap.html' title='bind, apply, and call trap'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-7384815584949807729</id><published>2011-10-03T09:17:00.010+02:00</published><updated>2011-10-03T10:53:40.522+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='ES6'/><category scheme='http://www.blogger.com/atom/ns#' term='CoffeeScript'/><title type='text'>Dear Brendan, Here Was My Question</title><content type='html'>I had the honor to personally shake the hand of the man that created my favorite programming language: &lt;a href="http://brendaneich.com/"&gt;Brendan Eich&lt;/a&gt;!&lt;br /&gt;&lt;br /&gt;I also dared to ask him a question about ES6 and I would like to better explain the reason of that question.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;I have 99 problems in JS, syntax ain't one&lt;/h3&gt;I don't know who said that but I completely agree with him.&lt;br /&gt;Here the thing: one of the main ES6 aim is to bring new, non breaking, shimmable, native constructors such &lt;em&gt;StructType&lt;/em&gt;, &lt;em&gt;ArrayType&lt;/em&gt;, and &lt;em&gt;ParallelsArray&lt;/em&gt;.&lt;br /&gt;We have all seen a demo during Brendan presentation and this demo was &lt;strong&gt;stunning&lt;/strong&gt;: an improvement from 3~7 to 40~60 Frames Per Second over a medium complex particles animation based, I believe, on WebGL.&lt;br /&gt;&lt;br /&gt;These new native constructors are indeed able to simplify the JS engine job being well defined, known, and "compilable" runtime in order to reach similar C/C++ performances.&lt;br /&gt;&lt;br /&gt;These new constructors can also deal directly behind the scene, without repeated and redundant "boxing/unboxing" or conversion, with canvas, I hope both 2d and 3D, and images.&lt;br /&gt;&lt;br /&gt;All of this without needing WebCL in the middle and this is both great and &lt;strong&gt;needed&lt;/strong&gt; in JS: give us more raw speed so we can do even more with the current JS we all know!&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Not Only Performances&lt;/h3&gt;The harmony/ES6 aim is also to enrich the current JavaScript with many new things such bock scopes, let, yeld, destructured and any sort of new syntax sugar we can imagine.&lt;br /&gt;It is also planning to bring a whole new syntax for JavaScript so that the one we known won't be recognizable anymore.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;I Have Been There Already&lt;/h3&gt;I am Certified ActionScript 2.0 Developer and back at that time, Adobe bought Macromedia and before Macromedia changed the ActionScript language 3 times in 3 years and a half: insane!!!&lt;br /&gt;The best part of it is that everything that was new and not compatible anymore with ActionScript 1, syntax speaking, was possible already before and with exactly same performances: &lt;strong&gt;the SWF generator was creating AS1.0 compatible bytecode out of AS2.0 syntax&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;AS 2.0 was just sugar on top indeed but it was not enough: in order to piss off even more the already frustrated community, ActionScript changed again into something Java&lt;em&gt;ish&lt;/em&gt; ... at least this time performances were slightly better thanks to better engine capable to use types in a convenient way.&lt;br /&gt;&lt;br /&gt;It must be said that at that time JIT compilers and all ultra powerful/engineered tricks included in every modern JavaScript engine were not considered, possible, implemented ... "&lt;em&gt;change the language is the solution&lt;/em&gt;" ... yeah, sure ...&lt;br /&gt;&lt;br /&gt;Rather than bring the unbelievable performances boost that V8 Engine, as example, brought to JavaScript in 2007, performances boost that keep improving since that time and almost in every engine, they simply changed the whole nature of the language breaking experience, libraries, legacy, and everything that has been done until that time: this was the Macromedia option, the one that failed by itself and has been acquired, indeed, by the bigger Adobe.&lt;br /&gt;&lt;br /&gt;Back in these days, the ActionScript 3.0 community is simply renewed and happy ... now, try to imagine if tomorrow Adobe will announce that ActionScript 4 will be like F#, a completely different new syntax, that most likely won't bring much more performances, neither concrete/real benefits for the community or their end users.&lt;br /&gt;&lt;br /&gt;Is this really the way to go? Break potentially everything for the sake of making happy some developer convinced that &lt;em&gt;-&amp;gt;&lt;/em&gt; is more explicit or semantic than &lt;em&gt;function&lt;/em&gt; ?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;CoffeeScript If You Want&lt;/h3&gt;As somebody wrote about W3C, why even waste time rather than focus on what is truly needed ?&lt;br /&gt;Didn't CoffeeScript or GWT teach us that if you want a language that is not JavaScript you can create your own syntax and if the community is happy it will adopt the "transformer" in their projects ?&lt;br /&gt;Didn't JavaScript demonstrate already that its flexibility is so great that almost everything can be recompiled into it ?&lt;br /&gt;Emscripten is another example: legacy C/C++ code recompiled out of its LLVM into JavaScript ... how freaking great must be this "&lt;em&gt;JavaScript toy&lt;/em&gt;" to be capable of all of this ?&lt;br /&gt;We all know now how to create our own syntax manager, and many developers are using CoffeeScript already and they are happy ... do they need ES6 sugar? No, they can use CoffeeScript, isn't it? Moreover ...&lt;br /&gt;The day ES6 will be CoffeeScript&lt;em&gt;ish&lt;/em&gt; the CofeeScript project itself will probably die since it won't make sense anymore.&lt;br /&gt;The day ES6 will be CoffeeScript&lt;em&gt;ish&lt;/em&gt; all our experience, everything written about JS so far, all freaking cool projects created, consolidated, and used for such long time demonstrating these are simply "that good" won't be recyclable anymore.&lt;br /&gt;Also, how should we suppose to integrate for cross browser compatibility, the new JS for cooler browsers, and the old one for "&lt;em&gt;not that cool yet&lt;/em&gt;" browser?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Continuous Integration&lt;/h3&gt;SCRUM teaches us that sprints should be well planned and tasks should be split down in smaller tasks if one of them is too big.&lt;br /&gt;What I see too big here is an ECMAScript milestone 6 which aim is to include:&lt;ul&gt;&lt;li&gt;the performances oriented constructors, the only thing truly needed by this community now&lt;/li&gt;&lt;li&gt;the block scoped let, generators, destructured stuff + for/of and pseudo JS friendly sugar that can be implemented without problems in CoffeeScript&lt;/li&gt;&lt;li&gt;the class statement, over a prototypal language we all love, plus all possible sugar and shortcuts for the function word, once again stuff already possible today but if truly needed, replicable via CoffeeScript&lt;/li&gt;&lt;/ul&gt;&lt;br /&gt;Is it really not posible to go ES 5.3 and bring what's needed with as much focus as possible on what's needed so that the community can be happy as soon as possible and think about what's not really needed after?&lt;br /&gt;&lt;br /&gt;Wouldn't this accelerate the process ?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;Mr Eich, it's your baby, and I am pretty sure you don't need me to feel proud of it. It's a great programming language a bit out of common schemas/patterns but able to survive for years revolutionizing the World Wide Web.&lt;br /&gt;It's also something "&lt;em&gt;everything can fallback into&lt;/em&gt;" and I would rather create a Firefox extension able to bring CoffeeScript runtime in every surfed page as long as we can have intermediate releases of these engines, bringing one step a time all these cool features but prioritizing them accordingly with what is missing.&lt;br /&gt;&lt;br /&gt;I thank you again for your answer, which summary is: "&lt;em&gt;we are already experimenting and bringing these features in SpiderMonkey ...&lt;/em&gt;" and &lt;strong&gt;this is great&lt;/strong&gt; but we are talking about meetings, decisions, and time in the meanwhile to agree about everything else too, specially new syntax.&lt;br /&gt;&lt;br /&gt;I am pretty sure that following one step a time we can already have a Christmas present here since I don't see how StructType and ArrayType can be problematic to implement, and eventually optimize later, in every single engine.&lt;br /&gt;&lt;br /&gt;These constructors should be finalized in some intermediate specification of the ECMAScript language, so that everybody can commit to it, and every single body would be gradually happier about JavaScript each half year.&lt;br /&gt;&lt;br /&gt;In 2013 most likely new powerful CPU/GPU will be able to handle heavy stuff we are trying to handle now ... so it's &lt;strong&gt;now&lt;/strong&gt; that we would like to be faster and it's now that we need these constructors.&lt;br /&gt;&lt;br /&gt;I have also shimmed down these constructors already so that incremental browsers upgrades will make these shims useless but performances will be increased whenever these are applied ... a simple example:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var Float32Array = Array, // better shimmed&lt;br /&gt;    Int32Array = Float32Array&lt;br /&gt;    ....&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;I use similar code already and on daily basis: it does not hurt much, it works today everywhere, and it goes full speed where those constructors are available.&lt;br /&gt;&lt;br /&gt;A whole new syntax incompatible with current specifications could be good and evil at the same time plus it will take ages before every engine can be compatible with it ... we all know the story here.&lt;br /&gt;&lt;br /&gt;I am pretty sure I am saying nothing new here and I do hope that Harmony will bring proper harmony between what we have now, what we need now, and what we would like to have tomorrow, using projects like CoffeeScript if we really can't cope, today, with this beautiful unicorn.&lt;br /&gt;&lt;br /&gt;Thank you for your patience&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-7384815584949807729?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/7384815584949807729/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=7384815584949807729' title='7 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7384815584949807729'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7384815584949807729'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/10/dear-brendan-here-was-my-question.html' title='Dear Brendan, Here Was My Question'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>7</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-4407369713065620722</id><published>2011-10-02T11:53:00.006+02:00</published><updated>2011-10-04T03:11:08.121+02:00</updated><title type='text'>Me At JSConf.EU 2011</title><content type='html'>About my &lt;a href="http://jsconf.eu/2011/buzz_it_for_real_the_tortuous.html"&gt;JSConf.EU Talk&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;Here my &lt;a href="http://www.3site.eu/JSConfEU.pdf"&gt;JSConf EU 2011 Slides&lt;/a&gt;, and here again the &lt;a href="http://speakerrate.com/talks/8460-buzz-it-for-real-the-tortuous-road-to-mobile-html5-apps"&gt;speaker rate&lt;/a&gt; (only if you have seen the talk, pls).&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;update&lt;/strong&gt; I forgot to mention &lt;a href="https://github.com/WebReflection/features"&gt;lazy features detection oject&lt;/a&gt; proposal!&lt;br /&gt;&lt;br /&gt;Thanks everybody, it has been a great week end :)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-4407369713065620722?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/4407369713065620722/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=4407369713065620722' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/4407369713065620722'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/4407369713065620722'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/10/me-at-jsconfeu-2011.html' title='Me At JSConf.EU 2011'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-6335014461799208736</id><published>2011-09-28T20:14:00.008+02:00</published><updated>2011-09-28T21:11:00.767+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='quality'/><category scheme='http://www.blogger.com/atom/ns#' term='thoughts'/><category scheme='http://www.blogger.com/atom/ns#' term='random'/><category scheme='http://www.blogger.com/atom/ns#' term='software'/><title type='text'>RIA VS OS</title><content type='html'>... have you ever thought about it ? I did few times in my 11+ years of &lt;abbr title="Reach Internet Application"&gt;RIA&lt;/abbr&gt; centric career!&lt;br /&gt;Even if it's like comparing potatoes with tomatoes I'd like to share my thoughts about it, would you mind ?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;What we always laughed about OS&lt;/h3&gt;&lt;ul&gt;&lt;br /&gt;&lt;li&gt;the blue/gray screen with an &lt;i&gt;incomprehensible&lt;/i&gt; error message&lt;/li&gt;&lt;br /&gt;&lt;li&gt;the Message Box with some rant about some memory address failure&lt;/li&gt;&lt;br /&gt;&lt;li&gt;the unresponsive OS due some broken application able to make everything else stuck regardless the number of CPU and thread the OS can handle&lt;/li&gt;&lt;br /&gt;&lt;li&gt;the "&lt;i&gt;quit program&lt;/i&gt;" explicit action that does not quit the program&lt;/li&gt;&lt;br /&gt;&lt;li&gt;any sort of security issue&lt;/li&gt;&lt;br /&gt;&lt;li&gt;the change/update that requires a system reboot&lt;/li&gt;&lt;br /&gt;&lt;/ul&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;What we are always "scared about" online&lt;/h3&gt;&lt;ul&gt;&lt;br /&gt;&lt;li&gt;the white screen due some JS/CSS failure for the current browser&lt;/li&gt;&lt;br /&gt;&lt;li&gt;the forgotten &lt;em&gt;alert&lt;/em&gt; or &lt;em&gt;console.log&lt;/em&gt; inside some try catch with some rant about generic error message (or even worst, the unmanaged error)&lt;/li&gt;&lt;br /&gt;&lt;li&gt;the unresponsive DOM/web page due some broken piece of JavaScript able to make everything else stuck regardless the number of CPU and WebWorkers the Browser can handle&lt;/li&gt;&lt;br /&gt;&lt;li&gt;the "&lt;i&gt;close window/tab&lt;/i&gt;" explicit action that takes ages due some greedy &lt;em&gt;onunload&lt;/em&gt; operation&lt;/li&gt;&lt;br /&gt;&lt;li&gt;any sort of security issue&lt;/li&gt;&lt;br /&gt;&lt;li&gt;the change/update that requires a page reload&lt;/li&gt;&lt;br /&gt;&lt;/ul&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;We are all in the same field&lt;/h3&gt;Architecture matters, experience matters, performances matter, investigations matter, code quality matter, unit tests matter, UX is essential, and UI only attractive.&lt;br /&gt;This is the software development world, no matters which language, no matters which customer, no matters which company ... isn't it? So why things keep being the same in every software field ?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Delivery, delivery, delivery !&lt;/h3&gt;The main reason many applications out there, web or not, will rarely be that good.&lt;br /&gt;The scrum purpose is to make theoretically well organized &lt;em&gt;baby steps&lt;/em&gt; and the agile often utopia due constant, drastic, changes you may &lt;strong&gt;want to face&lt;/strong&gt; during an already planned task while you are implementing the task itself.&lt;br /&gt;The time ? The worst enemy when it comes to quality. As I wrote &lt;a href="http://webreflection.blogspot.com/2009/09/software-quality-we-are-loosing-it.html"&gt;in September 2009&lt;/a&gt; we are loosing software quality due temporary solutions that last forever, decisions made without real world use cases to consider and everything else web developers are complaining, as example, about W3C decisions.&lt;br /&gt;Is W3C that bad ? I think it's great, and I think we should all appreciate the Open Source effort we can read, support, or comment, on daily basis as is for JavaScript future if you are tough enough to face people proud by default about their decisions ... they can understand, they can change their mind.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The direction ?&lt;/h3&gt;Too much new stuff in too short time that could imply future problems when it comes to maintainability and backward compatibility, the day somebody will realize: "&lt;em&gt;something went terribly wrong here!&lt;/em&gt;"&lt;br /&gt;The legacy code that blocks improvements, the country or corporates stuck behind old, deprecated, un-secure, old pseudo standard that are causing them more damage than saving.&lt;br /&gt;Is everything going to produce cheap with screwed up quality? Well, this is apparently the tendency about clothes, cars, and something I always wondered about: if your Master/Phd is from the most expensive and qualified institute in this world, how would you feel to work underpaid in some emerging country able to provide everything you have been instructed for in 1/10 of your salary and with much higher units per months ?&lt;br /&gt;Either that institute won't be worth it anymore, or you gonna feel like everything you learned did not really make sense.&lt;br /&gt;This is a potential side effect of out sourcing too, the cheap alternative to a problem that many times is not truly solved, simply delegated and delivered with lower quality but respecting, most of the time, the deadline that once published will make max 70% of customers happy, loosing 30% until they'll face same problems with next "brand" they decide to follow.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Dedicated to&lt;/h3&gt;All those persons out there that do their best in daily basis believing in their job, whatever it is.&lt;br /&gt;All those persons underpaid still able to put best effort and provide results regardless the country/economy situation.&lt;br /&gt;All those workers that would like to have more time to do things better, and all those Open Sources/Standards Maker that should be more distant from this frenetic delivery concept, and a bit more focused on doing things properly and able to last much longer ... we would not need so many changes, software speaking, if things were already great and this is what I have always tried to do with all my old projects, often forgotten, still working after 5 or more years of untouched code, and under newer versions of the same programming language.&lt;br /&gt;I had more time back at that time, and things are still working.&lt;br /&gt;I am missing products like the &lt;a href="http://en.wikipedia.org/wiki/Vespa"&gt;original Vespa&lt;/a&gt;, out of Italian company that can still run in your city street and with 30 years on its shoulder: can your cheap scooter, software, architectural decision, do the same?&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-6335014461799208736?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/6335014461799208736/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=6335014461799208736' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/6335014461799208736'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/6335014461799208736'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/09/ria-vs-os.html' title='RIA VS OS'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-3405057461799795566</id><published>2011-09-26T19:22:00.007+02:00</published><updated>2011-09-28T07:49:10.422+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='mobile'/><category scheme='http://www.blogger.com/atom/ns#' term='html5'/><category scheme='http://www.blogger.com/atom/ns#' term='EU'/><category scheme='http://www.blogger.com/atom/ns#' term='JSConf'/><title type='text'>About Me At JSConf EU</title><content type='html'>&lt;strike&gt;I know I am not in the list of speakers page yet, but I am actually in the official schedule already.&lt;/strike&gt;&lt;br /&gt;&lt;br /&gt;It's about &lt;a href="http://jsconf.eu/2011/"&gt;jsconf.eu&lt;/a&gt; and &lt;a href="http://jsconf.eu/2011/buzz_it_for_real_the_tortuous.html"&gt;my talk on Sunday morning at 10:45&lt;/a&gt; entitled ...&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Buzz It For Real !&lt;/h3&gt;&lt;h4&gt; ... the tortuous road to Mobile HTML5 Apps&lt;/h4&gt;For the very first time in my life I will not represent just myself during a conference. This time I will talk about few ideas, problems, and solutions, we have faced during the "&lt;i&gt;still in beta&lt;/i&gt;" development of our Mobile HTML5 Applications.&lt;br /&gt;&lt;br /&gt;I will talk about some problem completely ignored by majority of HTML5 developers providing concrete real-world examples, and solutions, over tested code.&lt;br /&gt;&lt;br /&gt;I know Sunday comes after the first conference party and I hope you, as well as me, won't be too drunk to follow my talk :D&lt;br /&gt;&lt;br /&gt;Of course a &lt;a href="http://speakerrate.com/talks/8460-buzz-it-for-real-the-tortuous-road-to-mobile-html5-apps"&gt;SpeakerRate&lt;/a&gt; page was a must have so see you there and enjoy the conference!&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-3405057461799795566?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/3405057461799795566/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=3405057461799795566' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/3405057461799795566'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/3405057461799795566'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/09/about-me-at-jsconf-eu.html' title='About Me At JSConf EU'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-3469553136633324002</id><published>2011-09-17T08:04:00.008+02:00</published><updated>2011-09-18T05:35:37.593+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='C'/><category scheme='http://www.blogger.com/atom/ns#' term='ctypes'/><category scheme='http://www.blogger.com/atom/ns#' term='JS.next'/><category scheme='http://www.blogger.com/atom/ns#' term='js-ctypes'/><title type='text'>An Introduction to JS-Ctypes</title><content type='html'>&lt;h3&gt;Update&lt;/h3&gt;If you have time follow the whole story in &lt;a href="https://mail.mozilla.org/pipermail/es-discuss/2011-September/016661.html"&gt;es-discuss mailing list&lt;/a&gt; while if you don't have time here the quick summary:&lt;br /&gt;&lt;strong&gt;js-ctypes purpose is different from JS.next typed structs/arrays&lt;/strong&gt; so it looks like it was my mistake to compare tomatoes and potatoes.&lt;br /&gt;I bet everybody else in this world could have compared these two different beasts due identical name, look, and similar usage.&lt;br /&gt;If ctypes are not used outside JS &lt;a href="https://twitter.com/#!/evilpies/status/115135892624125953"&gt;these are not JIT optimized&lt;/a&gt; in any case so now we know why performances are so slow compared with JS code.&lt;br /&gt;&lt;br /&gt;On &lt;em&gt;new Struct({literal:pairs})&lt;/em&gt; VS &lt;em&gt;new Struct(literal = pairs)&lt;/em&gt; there is still no answer and even if it's obviously possible to avoid an object creation per each created instance, recycling a single object and refreshing its properties same as we could do with properties descriptors and &lt;em&gt;Object.defineProperty&lt;/em&gt; I have pointed this out in that way on purpose since I can already see a massive usage of that unoptimized pattern and I would like to know that engines are able to optimize that pattern Just In Time or tracing it.&lt;br /&gt;&lt;br /&gt;More questions, "flames", and answers about this topic in the link I have already posted at the very beginning.&lt;br /&gt;&lt;hr /&gt;&lt;br /&gt;A few days ago I had a quick chat with &lt;a href="https://twitter.com/#!/veganben"&gt;Ben Green&lt;/a&gt; about statically defined JavaScript &lt;a href="http://en.wikipedia.org/wiki/Struct_(C_programming_language)"&gt;structs&lt;/a&gt;.&lt;br /&gt;He reminded me "&lt;em&gt;somebody wrote something about faster JS objects&lt;/em&gt;" and I remember I saw it as well but I could not find the bloody source until I crashed again into &lt;a href="https://twitter.com/#!/BrendanEich"&gt;Brendan Eich&lt;/a&gt; blog, more specifically the &lt;a href="http://brendaneich.com/2011/08/my-txjs-talk-twitter-remix/"&gt;My TXJS talk&lt;/a&gt; post.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;JavaScript Binary Data&lt;/h3&gt;The slide I am talking about is at page 14:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;const // the statically defined and typed structs&lt;br /&gt;         Point2D = new StructType({x:uint32, y:uint32}),&lt;br /&gt;         Color = new StructType({g:uint8, g:uint8, b:uint8}),&lt;br /&gt;         Pixel = new StructType({point: Point2D, color: Color}),&lt;br /&gt;         // the static collection&lt;br /&gt;         Triangle = new ArrayType(Pixel, 3);&lt;br /&gt;&lt;br /&gt;new Triangle([&lt;br /&gt;    {point: {x:0, y:0}, color: {r:0, g:0, b:0}},&lt;br /&gt;    {point: {x:5, y:5}, color: {r:10, g:10, b:10}},&lt;br /&gt;    {point: {x:10, y:0}, color: {r:20, g:20, b:20}}&lt;br /&gt;]);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;"&lt;em&gt;Mind Blown!&lt;/em&gt;" as first reaction, then I decided to investigate a bit more during the evening in order to bring some better feedback and have a better understanding of this concept ... but how did I do that?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;js-ctypes and Mozilla&lt;/h3&gt;Even if landed and approved only recently in JS.next, &lt;a href="https://developer.mozilla.org/en/js-ctypes"&gt;ctypes have been available in Firefox since version 4&lt;/a&gt;.&lt;br /&gt;I like the fact Mozilla keeps surprising me as one of the most advanced environment when it comes to JavaScript world but before getting too excited, we'd better keep reading this post.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The (ideal) Purpose&lt;/h3&gt;&lt;a href="http://www.slideshare.net/newmovie/know-yourengines-velocity2011"&gt;Dave Mandelin in Know Your Engines&lt;/a&gt; slides enlightened us describing how things get faster behind the interpreted JavaScript scene. As scripting language developers we would like to do not care at all about details such "&lt;i&gt;do not change variables type&lt;/i&gt;" but as I have asked during &lt;a href="http://falsyvalues.com/"&gt;falsy values&lt;/a&gt; conference: "&lt;em&gt;what about objects and their properties?&lt;/em&gt;"&lt;br /&gt;JS-Ctypes seem to be the "&lt;i&gt;ideal kick asses performances&lt;/i&gt;" trick we all were waiting for: an explicit, yet scriptish, way to describe well known structures in order to make the engine able to optimize and compile these structures runtime and boost up performances.&lt;br /&gt;This concept is not new at all in programming world.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Cython&lt;/h4&gt;From &lt;a href="http://en.wikipedia.org/wiki/Cython"&gt;Wikipedia&lt;/a&gt;:&lt;blockquote&gt;Cython is a programming language to simplify writing C and C++ extension modules for the CPython Python runtime. Strictly speaking, Cython syntax is a superset of Python syntax additionally supporting:&lt;br /&gt; - Direct calling of C functions, or C++ functions/methods, from Cython code.&lt;br /&gt; - &lt;strong&gt;Strong typing of Cython variables, classes, and class attributes as C types.&lt;/strong&gt;&lt;br /&gt;Cython compiles to C or C++ code rather than Python, and the result is used as a Python Extension Module or as a stand-alone application embedding the CPython runtime&lt;/blockquote&gt;I do believe it comes natural to compare js-ctypes to Cython and I am pretty sure initially this was the exact purpose of the Mozilla extension or, at least, Mozilla folks idea.&lt;br /&gt;Ironically this is the same reason js-ctypes are not available by default in Firefox and others except via extensions.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// if not in an extension, deprecated but&lt;br /&gt;// the only way to bring js-ctypes inline in a web page&lt;br /&gt;netscape.security.PrivilegeManager.enablePrivilege('UniversalXPConnect');&lt;br /&gt;&lt;br /&gt;// import ctypes&lt;br /&gt;Components.utils.import("resource://gre/modules/ctypes.jsm");&lt;br /&gt;&lt;/pre&gt;Bear in mind &lt;strong&gt;above code will not work online&lt;/strong&gt;. In order to test ctypes in Firefox we need to accept privileges risks &lt;strong&gt;offline&lt;/strong&gt; ( file://ctypes.test.html ).&lt;br /&gt;The reason is simple: rather than decouple the power of ctypes from &lt;a href="https://developer.mozilla.org/en/js-ctypes/Using_js-ctypes"&gt;the ability to use compiled libraries or dll&lt;/a&gt;, Mozilla put everything into a single module making its usage basically pointless/impossible for Web applications: &lt;strong&gt;big mistake&lt;/strong&gt;!&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;A Reasonable Shim&lt;/h3&gt;It's about 3 years or more I am writing examples and proposals in this blog about "&lt;em&gt;strict typed JavaScript&lt;/em&gt;" but this is not the case.&lt;br /&gt;If we want to shim in a good way js-ctypes we should actually forget the &lt;em&gt;type&lt;/em&gt; part or performances will be extremely compromised per each bloody created object.&lt;br /&gt;Unit test speaking, once we are sure that Firefox runs all our cases, we'd better trust nothing bad will happen in all shimmed browsers.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;try {&lt;br /&gt;    netscape.security.PrivilegeManager.enablePrivilege('UniversalXPConnect');&lt;br /&gt;    Components.utils.import("resource://gre/modules/ctypes.jsm");&lt;br /&gt;} catch(ctypes) {&lt;br /&gt;    // a minimal ctypes shim by WebReflection&lt;br /&gt;    this.ctypes = {&lt;br /&gt;        ArrayType: function ArrayType(constructor, length) {&lt;br /&gt;            var name = (constructor.name || "anonymous") + "Array";&lt;br /&gt;            return Function("c", "".concat(&lt;br /&gt;                "return function ", name, "(o){",&lt;br /&gt;                    "var i=(o||[]).length;",&lt;br /&gt;                    length ? "if(i!=" + length + ")throw 'wrong length';" : "",&lt;br /&gt;                    "if(!(this instanceof ", name, "))",&lt;br /&gt;                        "return new ", name, "(o);",&lt;br /&gt;                    "this.length=i;",&lt;br /&gt;                    "while(i--)",&lt;br /&gt;                        "this[i]=new c(o[i]);",&lt;br /&gt;                "};"&lt;br /&gt;            ))(constructor);&lt;br /&gt;        },&lt;br /&gt;        StructType: function StructType(name, fields) {&lt;br /&gt;            for (var key, current, proto = {}, init = [], i = 0; i &lt; fields.length; ++i) {&lt;br /&gt;                current = fields[i];&lt;br /&gt;                for (key in current) {&lt;br /&gt;                    if (current.hasOwnProperty(key)) {&lt;br /&gt;                        init.push("this['" + key + "']=o['" + key + "']");&lt;br /&gt;                        proto[key] = null;&lt;br /&gt;                    }&lt;br /&gt;                }&lt;br /&gt;            }&lt;br /&gt;            return Function("p", "".concat(&lt;br /&gt;                "function ", name, "(o){",&lt;br /&gt;                    "if(!(this instanceof ", name, "))",&lt;br /&gt;                        "return new ", name, "(o);",&lt;br /&gt;                    init.join(";"),&lt;br /&gt;                "}",&lt;br /&gt;                name, ".prototype=p;",&lt;br /&gt;                "return ", name&lt;br /&gt;            ))(proto);&lt;br /&gt;        }&lt;br /&gt;    };&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;To make things even faster, I have adopted an "&lt;em&gt;inline compiled JS&lt;/em&gt;" technique so that each defined struct will do most basic tasks per each instance creation.&lt;br /&gt;Following an example about js-ctypes usage:&lt;br /&gt;&lt;pre class="code"&gt;// as is for native cnstructor, no need to "new"&lt;br /&gt;const Point2D = ctypes.StructType(&lt;br /&gt;    "Point2D",  // the struct name&lt;br /&gt;    [           // the struct description&lt;br /&gt;        {x: ctypes.int},&lt;br /&gt;        {y: ctypes.int}&lt;br /&gt;    ]&lt;br /&gt;);&lt;br /&gt;        &lt;br /&gt;// a struct can be used to define a collection of same type&lt;br /&gt;const Segment2D = ctypes.ArrayType(&lt;br /&gt;    Point2D,    // the value type&lt;br /&gt;    2           // the length&lt;br /&gt;);&lt;br /&gt;&lt;br /&gt;// if length is specified, this must match during construction&lt;br /&gt;        &lt;br /&gt;// if no length is specified any amount of elements can be created&lt;br /&gt;const Line2D = ctypes.ArrayType(Segment2D);&lt;br /&gt;        &lt;br /&gt;// no need to invoke all constructors&lt;br /&gt;// as long as the Array/Object structure&lt;br /&gt;// matches the defined one&lt;br /&gt;var line = Line2D([&lt;br /&gt;    [&lt;br /&gt;        {x: 0, y: 0},&lt;br /&gt;        {x: 10, y: 10}&lt;br /&gt;    ], [&lt;br /&gt;        {x: 10, y: 10},&lt;br /&gt;        {x: 20, y: 20}&lt;br /&gt;    ], [&lt;br /&gt;        {x: 20, y: 20},&lt;br /&gt;        {x: 30, y: 30}&lt;br /&gt;    ]&lt;br /&gt;]);&lt;br /&gt;&lt;/pre&gt;Even if geometrically speaking above example does not make much sense, being a line by definition represented by infinite number of points, I am pretty sure you got the logic.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Still NOT JS.next&lt;/h4&gt;The struct definition is slightly different from the one shown by Brendan Eich but at least the ArrayType signature seems to be similar.&lt;br /&gt;If what Brendan showed is actually true, we will not have a way to define statically typed getters and setters.&lt;br /&gt;Not that a function per each get/set can improve performances, but I consider this a sort of limit over other statically typed programming languages.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;10X Slower&lt;/h3&gt;Surpriiiiiiiiiiiseeeeeee!!! Even Firefox Nightly performs like a turtle on steroids over statically typed collections and here the &lt;a href="http://www.3site.eu/examples/ctypes.perf.html"&gt;test you should save in your desktop&lt;/a&gt; and launch via file protocol.&lt;br /&gt;If you see the &lt;em&gt;alert&lt;/em&gt;, ctypes have not been loaded ... but if you test in on Firefox via file protocol and you allow the module, you will not see any alert but an actual benchmark of three different types of collections:&lt;ul&gt;&lt;li&gt;a generic Array of Objects&lt;/li&gt;&lt;li&gt;a typed collection of typed objects&lt;/li&gt;&lt;li&gt;an Int32Array implementation over int values with an object creation per each loop iteraction&lt;/li&gt;&lt;/ul&gt;I don't know what's your score ( and I could not manage to test it via jsperf ) but at least in my MacBookPro numbers are 110ms for ctypes VS 19 or 16 for other two tests.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;What The Fuck Is Going On&lt;/h3&gt;Pardon my french but I could not describe in a better way my reaction ... however, I have an idea of what's happening there ...&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Slow Binding&lt;/h4&gt;If ctypes are checking and transforming runtime all values in order to provide nicely written Errors somebody screwed up the speed boost idea here. I would rather prefer to see my browser implode, my system crash, my MacBook explode than thinking every single bloody object creation is actually &lt;strong&gt;slower&lt;/strong&gt; than non statically defined one!&lt;br /&gt;"&lt;em&gt;check all properties, check all types, convert them into C compatible structs, bring them back to JS world per each index access&lt;/em&gt;" ... I mean, this cannot be the way to make things faster.&lt;br /&gt;The operation could surely be more expensive in therms of Struct and List definitions but for fuck sake these cannot be trapped behind the scene: these must be instantly available as hidden pre compiled/pre optimized objects and if some assignment goes wrong just exit the whole thing!&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Static Is Not For Everybody&lt;/h4&gt;Let "&lt;em&gt;week end hobbyists&lt;/em&gt;" use JS as they know but give JS the native power of C. Don't try to save poor JS kids/developers here, you either bring this power in or you don't.&lt;br /&gt;Any application that will screw an assignment over a statically typed collection or struct does not deserve a place in the web, as well as any sort of broken C code cannot be compiled or it will kill the execution if something goes wrong runtime.&lt;br /&gt;&lt;br /&gt;I am not joking here, think about those developers that actually know what they are doing and forget for once the "&lt;em&gt;too easy to use&lt;/em&gt;" concept: &lt;strong&gt;we all desire to handle statically typed code via JS and we expect a massive performances boost&lt;/strong&gt;.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Double Memory Consumption&lt;/h3&gt;The typed part of JavaScript seems to ignore a little detail: every object will require both non statically typed structure, &lt;em&gt;{x: Number, y: Number}&lt;/em&gt; plus its statically typed equivalent: &lt;em&gt;Point2D&lt;/em&gt;.&lt;br /&gt;I am not sure engines can optimize that much here and thinking about mobile platforms I wonder if TC39 team is actually thinking "&lt;i&gt;Desktop only&lt;/i&gt;" ... &lt;a href="http://www.khronos.org/webcl/"&gt;WebCL&lt;/a&gt; seems, once again, a much better alternative than ctypes here 'cause if all these operations will mean higher memory footprint and slower interaction we are in a &lt;strong&gt;no-go&lt;/strong&gt; specification that should never land in JS world.&lt;br /&gt;We really can implement by ourself strict type checks so either ctypes bring something powerful and fast or I can see already a lot of effort, implementation speaking, for zero income, real use cases speaking.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;const Point2D = ctypes.StructType(&lt;br /&gt;    "Point2D",  // the struct name&lt;br /&gt;    [           // the struct description&lt;br /&gt;        {x: ctypes.int},&lt;br /&gt;        {y: ctypes.int}&lt;br /&gt;    ]&lt;br /&gt;);&lt;br /&gt;&lt;br /&gt;// how it is now in ES.next too&lt;br /&gt;var p = new Point2D(&lt;br /&gt;    {x: 123, y: 123} // why on earth!&lt;br /&gt;);&lt;br /&gt;&lt;br /&gt;// how it should be in ES.next&lt;br /&gt;var p = new Point2D(&lt;br /&gt;    // no object dependeny/creation&lt;br /&gt;    x=123,&lt;br /&gt;    y=123&lt;br /&gt;);&lt;br /&gt;&lt;/pre&gt;Above example is just one out of millions way to better initialize a statically typed structures. Since &lt;em&gt;JS.next&lt;/em&gt; will bring new sugar in any case, unless these objects used to initialize a structure will be completely ignored/discarded runtime, creating holes in therms of object reusability, the creation of a complementary object per each static instance is a non-sense.&lt;br /&gt;In few words, no need to overcomplicate engines when these will be already compatible with named defaults function arguments, isn't it?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;C could land into JavaScript but it must be done properly. A too hybrid solution could bring double problems and all I have tried to do in this post is collaborate with the initiative bringing thoughts and tests.&lt;br /&gt;I hope this part will be specified and implemented properly, removing the "&lt;em&gt;native dll binding&lt;/em&gt;" we don't need on te web, neither we do for &lt;em&gt;node.js&lt;/em&gt; modules.&lt;br /&gt;Sure it's a nice have, but once we can write proper modules based on statically typed structs and collections, there won't be such big need of pre-compiled C stuff and all cross platform problems at that point will be solved on browser engine level, rather than on JS specific C module side.&lt;br /&gt;Any sort of thoughts and/or clarification will be more than appreciated but right now all I can say is: avoid this extension, don't try to screw with native system libraries, don't use this extension thinking it will bring more efficient, fast, powerful, code into your app.&lt;br /&gt;Thanks for your patience&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-3469553136633324002?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/3469553136633324002/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=3469553136633324002' title='7 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/3469553136633324002'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/3469553136633324002'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/09/introduction-to-js-ctypes.html' title='An Introduction to JS-Ctypes'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>7</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-7765265188734647826</id><published>2011-09-10T10:03:00.023+02:00</published><updated>2011-09-13T09:11:39.961+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='Dash'/><category scheme='http://www.blogger.com/atom/ns#' term='Rant'/><category scheme='http://www.blogger.com/atom/ns#' term='Fart'/><category scheme='http://www.blogger.com/atom/ns#' term='Dart'/><title type='text'>My New Programming Language</title><content type='html'>yeah, you read it correctly ... we all need another better programming language because everything we've done until now sucks.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;What Sucks&lt;/h3&gt;&lt;ul&gt;&lt;li&gt;the fact we don't learn by mistakes, which means all of us should instantly try to create a new "&lt;em&gt;secretly open source programming language&lt;/em&gt;" so that the rest of the world can only endure it once it's out, rather than contribute to make it better/needed as it's happening since at least 5 years with JavaScript in all possible, and truly open, channels&lt;/li&gt;&lt;br /&gt;&lt;li&gt;the fact Java, .NET, and all others failed ... 'cause we are still looking for a new programming language in these days where C++ X11 has been approved while C never died&lt;/li&gt;&lt;br /&gt;&lt;li&gt;the fact we keep thinking that performances are possible only with compiled languages forgetting that better algorithms, better practices, better tools to develop and track leaks, memory consumptions, CPU/GPU cycles, can make any software fast enough or ...&lt;/li&gt;&lt;br /&gt;&lt;li&gt;... the fact new standards are coming to help us with performances, as is for &lt;a href="http://www.khronos.org/opencl/"&gt;OpenCL&lt;/a&gt;, and new techniques are already available to speed up common tasks, as is for Statically Typed Collections&lt;/li&gt;&lt;br /&gt;&lt;li&gt;the fact we are blaming JavaScript because is the most used programming language and as is for "&lt;em&gt;the most used whatever thing&lt;/em&gt;" out there more people will complain about it and even more people will enjoy it ( e.g. the unbelievable growing speed of node.js community and all latest server side JS related projects ) &lt;/li&gt;&lt;br /&gt;&lt;li&gt;the fact if a programming language is part of the &lt;em&gt;scripting&lt;/em&gt; group it's considered a toy regardless the fact any sort of application out of billions is working right now out there without major security, performances, or design problems&lt;/li&gt;&lt;br /&gt;&lt;li&gt;the fact that compiled programming language developers are not necessarily superior or more skilled than scripters ... the world of Software would be perfect otherwise and the Web as we know it, the good one, would not exist&lt;/li&gt;&lt;br /&gt;&lt;li&gt;the fact that if a programming language is appreciated and used by senior professionals as well as week end hobbyist &lt;em&gt;must mean&lt;/em&gt; that language is weak and it needs to be substituted&lt;/li&gt;&lt;br /&gt;&lt;li&gt;the fact that experience is a key, and with a new language it will be completely lost and all sort of inevitable problems or solutions will not be instantly available to the community&lt;/li&gt;&lt;br /&gt;&lt;li&gt;the fact that if it's possible to translate this new fantastic language into JavaScript for backward compatibility, everything new this language will bring tomorrow was already possible today&lt;/li&gt;&lt;/ul&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;Looking forward for the revolution and looking forward to forget that OpenCL even existed.&lt;br /&gt;Let's hope at least all Operating Systems companies will agree, let's hope it will be the universal language we have been dreaming about since ever ... let's hope ... and sorry for this surely not needed rant.&lt;hr /&gt;&lt;strong&gt;Update&lt;/strong&gt; A &lt;a href="http://news.ycombinator.com/item?id=2983157"&gt;must read post from BrendanEich&lt;/a&gt; who is apparently sharing my point of view with more technical reasons.&lt;br /&gt;Alex Russel also on &lt;a href="http://infrequently.org/2011/09/google-the-future-of-javascript/"&gt;Google &amp; the Future of JavaScript&lt;/a&gt; gives us something more about what's going on there, nice one.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-7765265188734647826?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/7765265188734647826/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=7765265188734647826' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7765265188734647826'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7765265188734647826'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/09/my-new-programming-language.html' title='My New Programming Language'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-6273354164548970996</id><published>2011-08-27T11:38:00.005+02:00</published><updated>2011-08-27T12:07:35.054+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='maps'/><category scheme='http://www.blogger.com/atom/ns#' term='OSX'/><category scheme='http://www.blogger.com/atom/ns#' term='mobile'/><category scheme='http://www.blogger.com/atom/ns#' term='Nokia'/><category scheme='http://www.blogger.com/atom/ns#' term='Lion'/><category scheme='http://www.blogger.com/atom/ns#' term='automator'/><title type='text'>OS X Lion Automator And Mobile NOKIA Maps</title><content type='html'>When I have read this article about &lt;a href="http://ihnatko.com/2011/07/22/making-desktop-webapps-in-lion/"&gt;Making Desktop Webapps in Lion&lt;/a&gt; my first thought was "&lt;em&gt;cool!&lt;/em&gt;" instantly followed by "&lt;em&gt;what about an experiment with Mobile NOKIA Maps WebApp?&lt;/em&gt;" ... and here I come :)&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;&lt;a href="http://m.maps.nokia.com/"&gt;m.maps.nokia.com&lt;/a&gt;&lt;/h3&gt;is the &lt;strong&gt;beta&lt;/strong&gt; project I am working on right now together with a bounce of HTML5 geeks :P in order to bring the mature &lt;a href="http://maps.nokia.com/"&gt;NOKIA Maps&lt;/a&gt; experience on Android 2.2+, iOS4+, and others already supported or "&lt;em&gt;coming soon&lt;/em&gt;" devices.&lt;br /&gt;Optimized for mobile but still usable with Desktop Chrome or Safari browser, the web app is quite "&lt;em&gt;cute&lt;/em&gt;" seen in iPhone or other medium and small screens and this experiment was about bringing same "&lt;em&gt;cuteness&lt;/em&gt;" on my Mac Mini as well: partially successful!&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Lion Automator And WebPopup Limits&lt;/h3&gt;Unfortunately it is not possible to customize that much the popup browser user agent and I am not even sure what kind of engine is used there ...&lt;br /&gt;With &lt;strong&gt;iPhone&lt;/strong&gt; UserAgent the version exposed is &lt;strong&gt;3&lt;/strong&gt; and &lt;strong&gt;Webkit 430+&lt;/strong&gt;.&lt;br /&gt;When it comes to iPad UserAgent the version is &lt;strong&gt;4&lt;/strong&gt; while with Safari UA the version is the current one.&lt;br /&gt;&lt;strong&gt;GeoLocation API&lt;/strong&gt; does not seem to work, and the cache seems to be cleaned every time the app is closed.&lt;br /&gt;Unfortunately these limits make the current beta less cool than usual, specially because every time the app is closed the storage seems to be reset which means last position is not shown next time, history and suggestions do not show off and even more annoying the routing "&lt;em&gt;home to place&lt;/em&gt;" is not available due missing location.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Grab The Desktop App For OSX Lion&lt;/h3&gt;I have prepared everything you need to launch &lt;a href="http://m.maps.nokia.com/"&gt;m.maps.nokia.com&lt;/a&gt; in your OSX Lion so you can give it a try.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;&lt;a href="http://www.3site.eu/examples/NOKIA%20Maps.app.zip"&gt;Mobile NOKIA Maps For Automator&lt;/a&gt;&lt;/strong&gt; and if necessary extract its content and click on the &lt;strong&gt;.app&lt;/strong&gt; file.&lt;br /&gt;&lt;br /&gt;I swear I did nothing different from what &lt;em&gt;Andy Ihnatko&lt;/em&gt; described in its article, except changing the icon with the one downloaded automatically on iPad if you pin the website to your home screen.&lt;br /&gt;&lt;br /&gt;If you are in OSX Lion give it a try and play around but bear in mind this beta offers much more on your smartphone ;)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-6273354164548970996?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/6273354164548970996/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=6273354164548970996' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/6273354164548970996'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/6273354164548970996'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/08/os-x-lion-automator-and-mobile-nokia.html' title='OS X Lion Automator And Mobile NOKIA Maps'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-1837751273855615477</id><published>2011-08-24T20:35:00.004+02:00</published><updated>2011-08-24T21:05:17.248+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='server'/><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='data'/><category scheme='http://www.blogger.com/atom/ns#' term='mock'/><category scheme='http://www.blogger.com/atom/ns#' term='uri'/><category scheme='http://www.blogger.com/atom/ns#' term='injection'/><category scheme='http://www.blogger.com/atom/ns#' term='script'/><title type='text'>Simulate Script Injection Via Data URI</title><content type='html'>Well, &lt;a href="http://webreflection.blogspot.com/2011/08/html5-how-to-create-downloads-on-fly.html"&gt;not only downloads on the fly&lt;/a&gt;, the data uri works for almost everything ( only iOS 5 beta does not want to work with inline data uri AUDIO sources .... but this is another story ... ) ... so ... &lt;br /&gt;&lt;br /&gt;&lt;h3&gt;How To Simulate Script injection&lt;/h3&gt;Let's say you want a test but you don't want to bother a server. However, you want to be sure the test is asynchronous and it simulates the server.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var&lt;br /&gt;    head = document.getElementsByTagName("head")[0],&lt;br /&gt;    script = document.createElement("script")&lt;br /&gt;;&lt;br /&gt;head.insertBefore(script, head.lastChild);&lt;br /&gt;script.src = "data:text/javascript;base64," + btoa(&lt;br /&gt;    "alert('Hello World')"&lt;br /&gt;);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;How To Simulate JSONP&lt;/h3&gt;Same trick, isn't it? ... except:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;script.src = "data:text/javascript;base64," + btoa(&lt;br /&gt;    "callback(" + JSON.stringify(dummyData) + ")"&lt;br /&gt;);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;How To Drop Server Requests&lt;/h3&gt;well, this is the tricky one ...&lt;br /&gt;&lt;script src="https://gist.github.com/1168884.js?file=fake-script.js"&gt;&lt;/script&gt;&lt;br /&gt;Surely there is some job to do in the &lt;em&gt;createResponse()&lt;/em&gt; function but ... hey, we can stop bothering servers now ;)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-1837751273855615477?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/1837751273855615477/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=1837751273855615477' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/1837751273855615477'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/1837751273855615477'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/08/simulate-script-injection-via-data-uri.html' title='Simulate Script Injection Via Data URI'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-3734174957053102279</id><published>2011-08-21T19:34:00.003+02:00</published><updated>2011-08-21T19:40:14.088+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Web'/><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='Rhino'/><category scheme='http://www.blogger.com/atom/ns#' term='essential'/><category scheme='http://www.blogger.com/atom/ns#' term='wru'/><category scheme='http://www.blogger.com/atom/ns#' term='node.js'/><category scheme='http://www.blogger.com/atom/ns#' term='Unit Test'/><category scheme='http://www.blogger.com/atom/ns#' term='Framework'/><title type='text'>wru, unit tests have ever been that easy</title><content type='html'>Do you remember my &lt;a href="http://webreflection.blogspot.com/2010/09/wru-my-new-tiny-unit-test-library.html"&gt;good old wru project&lt;/a&gt;? It has been &lt;strong&gt;refactored&lt;/strong&gt;, &lt;strong&gt;readapted&lt;/strong&gt; for both client and server side environment such &lt;strong&gt;node.js&lt;/strong&gt; and &lt;strong&gt;Rhino&lt;/strong&gt; and, most important, &lt;strong&gt;&lt;a href="https://github.com/WebReflection/wru"&gt;it landed in github&lt;/a&gt;&lt;/strong&gt; ;)&lt;br /&gt;&lt;br /&gt;Please spend few minutes to read &lt;a href="https://github.com/WebReflection/wru#readme"&gt;the documentation&lt;/a&gt; and you'll realize why I chose this title for this post.&lt;br /&gt;&lt;br /&gt;Have fun with JavaScript Unit Tests!&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-3734174957053102279?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/3734174957053102279/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=3734174957053102279' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/3734174957053102279'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/3734174957053102279'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/08/wru-unit-tests-have-ever-been-that-easy.html' title='wru, unit tests have ever been that easy'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-8876301888613443340</id><published>2011-08-20T10:39:00.007+02:00</published><updated>2011-08-20T20:52:59.991+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='operator'/><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='class'/><category scheme='http://www.blogger.com/atom/ns#' term='Ruby'/><category scheme='http://www.blogger.com/atom/ns#' term='new'/><category scheme='http://www.blogger.com/atom/ns#' term='ES5'/><category scheme='http://www.blogger.com/atom/ns#' term='Python'/><category scheme='http://www.blogger.com/atom/ns#' term='in'/><title type='text'>Overloading the in operator</title><content type='html'>In all its "&lt;em&gt;sillyness&lt;/em&gt;", the &lt;a href="http://webreflection.blogspot.com/2011/08/coffeeshit-coffeescript-parody.html"&gt;CoffeeShit project&lt;/a&gt; gave me a hint about the possibilities of an overloaded &lt;a href="https://developer.mozilla.org/en/JavaScript/Reference/Operators/Special/in"&gt;in operator&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Cross Language Ambiguity&lt;/h3&gt;In JavaScript, the &lt;em&gt;in&lt;/em&gt; operator checks if a property is present where the property is &lt;strong&gt;the name rather than its value&lt;/strong&gt;.&lt;pre class="code"&gt;&lt;br /&gt;"name" in {name:"WebReflection"}; // true&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;However, I bet at least once in our JS programming life we have done something like this, expecting a &lt;em&gt;true&lt;/em&gt; rather than &lt;em&gt;false&lt;/em&gt;.&lt;pre class="code"&gt;&lt;br /&gt;4 in [3, 4, 5]; // false&lt;br /&gt;// Array [3, 4, 5] has no *index* 4&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;The Python Way&lt;/h4&gt;In Python, as example, last operation is perfectly valid!&lt;pre class="code"&gt;&lt;br /&gt;"b" in ("a", "b", "c") #True&lt;br /&gt;4 in [3, 4, 5]         # True&lt;br /&gt;&lt;/pre&gt;The behavior of &lt;a href="http://pyref.infogami.com/in"&gt;Python in operator&lt;/a&gt; is indeed more friendly in certain situations.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;value in VS value.in()&lt;/h3&gt;What if we pollute the &lt;em&gt;Object.prototype&lt;/em&gt; with an &lt;em&gt;in&lt;/em&gt; method that is not enumerable and sealed? No &lt;em&gt;for/in&lt;/em&gt; loops problems, neither cross browsers issues since if it's possible in our target environment, we do it, otherwise we don't do it ... a fair compromise?&lt;br /&gt;&lt;script src="https://gist.github.com/1158853.js?file=Object.prototype.in.js"&gt;&lt;/script&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Rules&lt;/h3&gt;&lt;ul&gt;&lt;li&gt;if the target object is an &lt;em&gt;Array&lt;/em&gt;, check if &lt;em&gt;value&lt;/em&gt; is contained in the Array ( equivalent of &lt;em&gt;-1 &lt; target.indexOf(value)&lt;/em&gt; )&lt;/li&gt;&lt;br /&gt;&lt;li&gt;if the target object is an &lt;em&gt;Object&lt;/em&gt;, check if &lt;em&gt;value&lt;/em&gt; is contained in one of its properties ( equivalent of &lt;em&gt;for/in { if(object[key] === value) return true; }&lt;/em&gt; ).&lt;br /&gt;I don't think nested objects should be checked as well and right now these are not ( same as native Array#indexOf ... if it's an array of arrays internal arrays values are ignored and that's how it should be for consistency reason )&lt;/li&gt;&lt;br /&gt;&lt;li&gt;if the target object is a &lt;em&gt;typeof "string"&lt;/em&gt;, check if &lt;em&gt;value&lt;/em&gt; is a subset of the target ( equivalent of &lt;em&gt;-1 &lt; target.indexOf(value)&lt;/em&gt; ).&lt;br /&gt;The Python logic on empty string is preserved since in JavaScript &lt;em&gt;"whateverStringEvenEmpty".indexOf("")&lt;/em&gt; is always 0&lt;/li&gt;&lt;br /&gt;&lt;li&gt;if the target property is a &lt;em&gt;typeof "number"&lt;/em&gt;, check if &lt;em&gt;value&lt;/em&gt; is a divisor of the &lt;em&gt;target&lt;/em&gt; ( as example, &lt;em&gt;(3).in(15) === true&lt;/em&gt; since 15 can be divided by 3) &lt;/li&gt;&lt;/ul&gt;I didn't came out with other "&lt;em&gt;sugarish cases&lt;/em&gt;" but feel free to propose some.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Compatibility&lt;/h3&gt;The "&lt;em&gt;curious fact&lt;/em&gt;" is that in &lt;em&gt;ES5&lt;/em&gt; there is &lt;strong&gt;no restrictions on an &lt;a href="http://es5.github.com/#x11.2.1"&gt;IdentifierName&lt;/a&gt;&lt;/strong&gt;.&lt;br /&gt;This is indeed different from an &lt;a href="http://es5.github.com/#x7.6"&gt;Identifier&lt;/a&gt;, where in latter &lt;em&gt;ReservedWord&lt;/em&gt; is not allowed.&lt;br /&gt;"&lt;em&gt;... bla, bla bla ...&lt;/em&gt;" ... right, the human friendly version of what I've just said is that &lt;em&gt;obj.in, obj.class, obj.for&lt;/em&gt; etc etc are all accepted identifiers names.&lt;br /&gt;Accordingly, to understand if the current browser is &lt;em&gt;ES5 specs compliant&lt;/em&gt; we &lt;em&gt;could&lt;/em&gt; do something like this:&lt;pre class="code"&gt;&lt;br /&gt;try {&lt;br /&gt;    var ES5 = !!Function("[].try");&lt;br /&gt;} catch(ES5) {&lt;br /&gt;    ES5 = !ES5;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;alert(ES5); // true or false&lt;br /&gt;&lt;/pre&gt;Back in topic, IE9 and updated Chrome, Firefox, Webkit, or Safari are all compatible with this syntax.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;New Possibilities&lt;/h3&gt;Do you like &lt;strong&gt;Ruby&lt;/strong&gt; syntax?&lt;pre class="code"&gt;&lt;br /&gt;// Ruby like instances creation (safe version)&lt;br /&gt;Function.prototype.new = function (&lt;br /&gt;    anonymous, // recycled function&lt;br /&gt;    instance,  // created instance&lt;br /&gt;    result     // did you know if you&lt;br /&gt;               // use "new function"&lt;br /&gt;               // and "function" returns&lt;br /&gt;               // an object the created&lt;br /&gt;               // instance is lost&lt;br /&gt;               // and RAM/CPU polluted&lt;br /&gt;               // for no reason?&lt;br /&gt;               // don't "new" if not necessary!&lt;br /&gt;) {&lt;br /&gt;    return function factory() {&lt;br /&gt;        &lt;br /&gt;        // assign prototype&lt;br /&gt;        anonymous.prototype = this.prototype;&lt;br /&gt;        &lt;br /&gt;        // create the instance inheriting prototype&lt;br /&gt;        instance = new anonymous;&lt;br /&gt;        &lt;br /&gt;        // call the constructor&lt;br /&gt;        result = this.apply(instance, arguments);&lt;br /&gt;        &lt;br /&gt;        // if constructor returned an object&lt;br /&gt;        return typeof result == "object" ?&lt;br /&gt;            // return it or return instance&lt;br /&gt;            // if result is null&lt;br /&gt;            result || instance&lt;br /&gt;            :&lt;br /&gt;            // return instance&lt;br /&gt;            // in all other cases&lt;br /&gt;            instance&lt;br /&gt;        ;&lt;br /&gt;    };&lt;br /&gt;}(function(){});&lt;br /&gt;&lt;br /&gt;// example&lt;br /&gt;function Person(name) {&lt;br /&gt;    this.name = name;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;var me = Person.new("WebReflection");&lt;br /&gt;alert([&lt;br /&gt;    me instanceof Person,       // true&lt;br /&gt;    me.name === "WebReflection" // true&lt;br /&gt;].join("\n"));&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Details on &lt;strong&gt;bad usage of new&lt;/strong&gt; a part, this is actually how I would use this method to boost up performances.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// Ruby like instances creation (fast version)&lt;br /&gt;Function.prototype.new = function (anonymous, instance) {&lt;br /&gt;    return function factory() {&lt;br /&gt;        anonymous.prototype = this.prototype;&lt;br /&gt;        instance = new anonymous;&lt;br /&gt;        this.apply(instance, arguments);&lt;br /&gt;        return instance;&lt;br /&gt;    };&lt;br /&gt;}(function(){});&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;cool?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Do Not Pollute Native Prototypes&lt;/h3&gt;It does not matter how cool and "&lt;em&gt;how much it makes sense&lt;/em&gt;", it is always considered a bad practices to pollute global, native, constructors prototypes.&lt;br /&gt;However, since in ES5 we have new possibilities, I would say that if everybody agrees on some specific case ... why not?&lt;br /&gt;&lt;em&gt;for/in&lt;/em&gt; loops can now be safe and some &lt;em&gt;ReservedWord&lt;/em&gt; can be the most semantic name to represent a procedure as demonstrated in this post.&lt;br /&gt;Another quick example?&lt;pre class="code"&gt;&lt;br /&gt;// after Function.prototype.new&lt;br /&gt;// after Person function declaration&lt;br /&gt;Object.defineProperty(Object.prototype, "class", {&lt;br /&gt;    enumerable: !1,&lt;br /&gt;    configurable: !1,&lt;br /&gt;    get: function () {&lt;br /&gt;        return this.__proto__.constructor;&lt;br /&gt;    }&lt;br /&gt;});&lt;br /&gt;&lt;br /&gt;var me = Person.new("WebReflection");&lt;br /&gt;&lt;br /&gt;// create instance out of an instance&lt;br /&gt;var you = me.class.new("Developer");&lt;br /&gt;&lt;br /&gt;alert([&lt;br /&gt;    you instanceof Person,   // true&lt;br /&gt;    you.name === "Developer" // true&lt;br /&gt;].join("\n"));&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;I can already see &lt;em&gt;Prototype3000&lt;/em&gt; farmework coming out with all these magic tricks in place :D&lt;br /&gt;Have fun with ES5 ;)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-8876301888613443340?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/8876301888613443340/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=8876301888613443340' title='7 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/8876301888613443340'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/8876301888613443340'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/08/overloading-in-operator.html' title='Overloading the in operator'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>7</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-4690787176702495806</id><published>2011-08-19T17:53:00.005+02:00</published><updated>2011-08-19T19:00:07.310+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='CoffeeShit'/><category scheme='http://www.blogger.com/atom/ns#' term='CoffeeScript'/><category scheme='http://www.blogger.com/atom/ns#' term='parody'/><title type='text'>CoffeeShit, The CoffeeScript Parody</title><content type='html'>&lt;a href="https://github.com/WebReflection/CoffeeShit#readme"&gt;&lt;img style="border:0" src="http://fuckn.es/s/coffeeshit.png" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;pre&gt;    ... because script happens!&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;This silly project does not want to offend the CoffeeScript creator neither any CoffeeScript user, hoping both have sense of humor :D&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;About&lt;/h3&gt;Every cult movie has one or more parodies ... well, every cult technology as well (or at least it should)!&lt;br /&gt;This idiotic project is &lt;strong&gt;&lt;a href="https://github.com/WebReflection/CoffeeShit"&gt;on github&lt;/a&gt;&lt;/strong&gt; with a better explanation, a suite of unit tests, and both source code and the partially manually minified one ( manually because I have discovered a nice bug with closure compiler and &lt;em&gt;eval&lt;/em&gt; there ... )&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;About The Name&lt;/h3&gt;You can &lt;a href="https://github.com/WebReflection/CoffeeShit/blob/master/src/CoffeeShit.js"&gt;check the library&lt;/a&gt; by yourself and realize I have used all worst possible practices in order to simulate a different syntax within the one allowed by JavaScript.&lt;br /&gt;Such &lt;em&gt;pile of shit&lt;/em&gt; &lt;strong&gt;I wrote&lt;/strong&gt; to mimic an excellent project as &lt;a href="http://jashkenas.github.com/coffee-script/"&gt;CoffeeScript&lt;/a&gt; is could not have a better name, imo.&lt;br /&gt;If you feel insulted by this idiotic experiment please let me know and I'll do my best to let people try it under a different name.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Example&lt;/h3&gt;&lt;pre class="code"&gt;&lt;br /&gt;// CoffeeScript&lt;br /&gt;square = (x) -&gt; x * x&lt;br /&gt;fill = (container, liquid = "coffee") -&gt;&lt;br /&gt;    "Filling the #{container} with #{liquid}..."&lt;br /&gt;mood = greatlyImproved if singing&lt;br /&gt;eat food for food in ['toast', 'cheese', 'wine']&lt;br /&gt;winner = yes if pick in [47, 92, 13]&lt;br /&gt;speed ?= 75&lt;br /&gt;&lt;br /&gt;// CoffeeShit&lt;br /&gt;square = 'x'['-&gt;']('x * x')&lt;br /&gt;fill = ['container', 'liquid = "coffee"']['-&gt;'](&lt;br /&gt;    'Filling the #{container} with #{liquid}...'&lt;br /&gt;)&lt;br /&gt;mood = greatlyImproved.if(singing)&lt;br /&gt;'eat(food)'.for('food').in(['toast', 'cheese', 'wine'])&lt;br /&gt;winner = yes.if(pick.in([47, 92, 13]))&lt;br /&gt;'speed'['?='](75)&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Many more in the landing page, even more inside unit tests file.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;I really could not resist :D&lt;br /&gt;This post aim is to let you write some comment, have fun with CoffeeShit!&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-4690787176702495806?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/4690787176702495806/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=4690787176702495806' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/4690787176702495806'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/4690787176702495806'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/08/coffeeshit-coffeescript-parody.html' title='CoffeeShit, The CoffeeScript Parody'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-7461690838632776876</id><published>2011-08-18T15:10:00.009+02:00</published><updated>2011-08-19T09:39:57.357+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='server'/><category scheme='http://www.blogger.com/atom/ns#' term='download'/><category scheme='http://www.blogger.com/atom/ns#' term='base64'/><category scheme='http://www.blogger.com/atom/ns#' term='link'/><category scheme='http://www.blogger.com/atom/ns#' term='html5'/><category scheme='http://www.blogger.com/atom/ns#' term='btoa'/><category scheme='http://www.blogger.com/atom/ns#' term='avoid'/><title type='text'>HTML5: How To Create Downloads On The Fly</title><content type='html'>this is a quick one I have implemented already in &lt;a href="http://fuckn.es"&gt;fuckn.es&lt;/a&gt; in the &lt;em&gt;create angry memory&lt;/em&gt; button logic ...&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The New Download Attribute&lt;/h3&gt;Hopefully soon, most updated browser will implement &lt;a href="http://www.whatwg.org/specs/web-apps/current-work/multipage/links.html#attr-hyperlink-download"&gt;the download attribute&lt;/a&gt; in hypertext links (aka: &amp;lt;a&amp;gt; tag)&lt;br /&gt;The quick summary is this one:&lt;br /&gt;&lt;blockquote&gt;The download attribute, if present, indicates that the author intends the hyperlink to be used for downloading a resource. The attribute may have a value; the value, if any, specifies the default filename that the author recommends for use in labeling the resource in a local file system.&lt;/blockquote&gt;&lt;br /&gt;And this is a basic example:&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;click here to&lt;br /&gt;&amp;lt;a&lt;br /&gt;    href=&amp;quot;resource234.txt&amp;quot;&lt;br /&gt;    download=&amp;quot;license.txt&amp;quot;&lt;br /&gt;&amp;gt;&lt;br /&gt;    download the license&lt;br /&gt;&amp;lt;/a&amp;gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;What Is Download For&lt;/h3&gt;Well, I am pretty sure you have read at least once in your life this kind of extra info beside a link:&lt;br /&gt;&lt;em&gt;right click to download the content and "Save As ..."&lt;/em&gt;&lt;br /&gt;Moreover, I am pretty sure you have created at least once in your server a page able to &lt;a href="http://devpro.it/code/72.html"&gt;force a generic file download&lt;/a&gt;.&lt;br /&gt;All these instructions and server side headers/files may disappear thanks to this new attribute, also because &lt;em&gt;there's no such thing as "right button" on touch screens&lt;/em&gt;, neither in some newer device pointer.&lt;br /&gt;If the file is meant to be download, it will ... cool?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Create Downloads On The Fly Via JavaScript&lt;/h3&gt;When I have read about it, I have instantly realized the potentials of this attribute combined with &lt;a href="http://en.wikipedia.org/wiki/Data_URI_scheme"&gt;inline data uri scheme&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Only HTML5 ?&lt;/h3&gt;Nope! Please note that many browsers let us already practice this technique. Some may open the file in a new blank page while some other may download directly the file as is for Chrome and the CSV example.&lt;br /&gt;As graceful degradation, the "&lt;em&gt;right click&lt;/em&gt;" procedure will still do the trick.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Downlaod Canvas As Image Example&lt;/h4&gt;First example is a classic one: &lt;em&gt;how to save a canvas snapshot as image via "click"&lt;/em&gt;.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// basic example&lt;br /&gt;function createDownloadLink(canvas, name) {&lt;br /&gt;    var a = document.createElement("a");&lt;br /&gt;    a.download = name;&lt;br /&gt;    a.title = "download snapshot";&lt;br /&gt;    a.href = canvas.toDataURL();&lt;br /&gt;    return a;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;// some paragraph in the page&lt;br /&gt;document.querySelector(&lt;br /&gt;    "p.snapshot"&lt;br /&gt;).appendChild(createDownloadLink(&lt;br /&gt;    document.querySelector("#game"),&lt;br /&gt;    "snapshot" + (-new Date) + ".png"&lt;br /&gt;));&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;When the user will tap/click on the link, the browser will simply start the download. &lt;strong&gt;No server side involved at all&lt;/strong&gt;!&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Save A Page As PDF&lt;/h4&gt;Thanks to &lt;a href="http://badassjs.com/post/708922912/pdf-js-create-pdfs-in-javascript"&gt;this technique&lt;/a&gt; we may use same trick to produce a PDF file out of whatever web page.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// basic example&lt;br /&gt;function createPDFLink(fileName) {&lt;br /&gt;    var doc = new pdf();&lt;br /&gt;    // whatever content you want to download&lt;br /&gt;    var a = document.createElement("a");&lt;br /&gt;    a.download = fileName;&lt;br /&gt;    a.title = "download as PDF";&lt;br /&gt;    a.href = doc.output('datauri',{"fileName":name});&lt;br /&gt;    return a;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;// some paragraph in the page&lt;br /&gt;document.querySelector(&lt;br /&gt;    "p.saveaspdf"&lt;br /&gt;).appendChild(createPDFLink(&lt;br /&gt;    "document-" + document.title + ".pdf"&lt;br /&gt;));&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Of course if the page content changes we can replace the old link with a freshly new created one.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Save Table As CSV&lt;/h4&gt;Well, another classic here, the csv format out of a table. This is a basic but &lt;strong&gt;working example&lt;/strong&gt; ;)&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;&amp;lt;script&amp;gt;&lt;br /&gt;// really basic example&lt;br /&gt;function tableToCSV(table) {&lt;br /&gt;    for (var&lt;br /&gt;        header = table.querySelectorAll(&amp;quot;tr th&amp;quot;),&lt;br /&gt;        rows = table.querySelectorAll(&amp;quot;tr td&amp;quot;),&lt;br /&gt;        hlength = header.length,&lt;br /&gt;        length = hlength + rows.length,&lt;br /&gt;        result = Array(hlength),&lt;br /&gt;        i = hlength,&lt;br /&gt;        j;&lt;br /&gt;        i &amp;lt; length; ++i&lt;br /&gt;    ) {&lt;br /&gt;        j = i % hlength;&lt;br /&gt;        j || result.push(&amp;quot;\n&amp;quot;);&lt;br /&gt;        result.push(rows[j].innerHTML);&lt;br /&gt;        ++j % hlength &amp;amp;&amp;amp; result.push(&amp;quot;,&amp;quot;);&lt;br /&gt;    }&lt;br /&gt;    i = 0;&lt;br /&gt;    while (i &amp;lt; hlength) {&lt;br /&gt;        result[i] = header[i].innerHTML + (&lt;br /&gt;            ++i &amp;lt; hlength ? &amp;quot;,&amp;quot; : &amp;quot;&amp;quot;&lt;br /&gt;        );&lt;br /&gt;    }&lt;br /&gt;    return result.join(&amp;quot;&amp;quot;);&lt;br /&gt;}&lt;br /&gt;this.onload = function () {&lt;br /&gt;    var a = document.body.appendChild(&lt;br /&gt;        document.createElement(&amp;quot;a&amp;quot;)&lt;br /&gt;    );&lt;br /&gt;    a.download = &amp;quot;table.csv&amp;quot;;&lt;br /&gt;    a.href = &amp;quot;data:text/csv;base64,&amp;quot; + btoa(&lt;br /&gt;        tableToCSV(document.querySelector(&amp;quot;table&amp;quot;))&lt;br /&gt;    );&lt;br /&gt;    a.innerHTML = &amp;quot;download csv&amp;quot;;&lt;br /&gt;};&lt;br /&gt;&amp;lt;/script&amp;gt;&lt;br /&gt;&amp;lt;table&amp;gt;&lt;br /&gt;    &amp;lt;tr&amp;gt;&lt;br /&gt;        &amp;lt;th&amp;gt;name&amp;lt;/th&amp;gt;&lt;br /&gt;        &amp;lt;th&amp;gt;age&amp;lt;/th&amp;gt;&lt;br /&gt;    &amp;lt;/tr&amp;gt;&lt;br /&gt;    &amp;lt;tr&amp;gt;&lt;br /&gt;        &amp;lt;td&amp;gt;Dan&amp;lt;/td&amp;gt;&lt;br /&gt;        &amp;lt;td&amp;gt;33&amp;lt;/td&amp;gt;&lt;br /&gt;    &amp;lt;/tr&amp;gt;&lt;br /&gt;    &amp;lt;tr&amp;gt;&lt;br /&gt;        &amp;lt;td&amp;gt;John&amp;lt;/td&amp;gt;&lt;br /&gt;        &amp;lt;td&amp;gt;32&amp;lt;/td&amp;gt;&lt;br /&gt;    &amp;lt;/tr&amp;gt;&lt;br /&gt;&amp;lt;/table&amp;gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Most likely we can test already above example even if the name won't probably be the chosen one.&lt;br /&gt;For safe base64 encode, compatible with UTF-8 pages, &lt;a href="http://devpro.it/javascript_id_214.html"&gt;have a look at this script&lt;/a&gt; ( &lt;em&gt;base64.encode()&lt;/em&gt; and &lt;em&gt;base64.decode()&lt;/em&gt; ).&lt;br /&gt;&lt;br /&gt;&lt;h3 id="download-link-compatibility"&gt;Compatibility&lt;/h3&gt;&lt;br /&gt;Different developers asked already about compatibility.&lt;br /&gt;As I have said before, we need to differentiate between "&lt;em&gt;download&lt;/em&gt;" attribute compatibility AND inline data uri link compatibility.&lt;br /&gt;In the first case I don't know browsers that will force the download with the specified name yet, but I'll update this section as soon as I know someone.&lt;br /&gt;In the latter case, IE9, Chrome, Firefox, Safari, Webkit based, and Opera seem to be already compatible.&lt;br /&gt;The main problem/limit I have spotted in &lt;em&gt;fuckn.es&lt;/em&gt; is the size of the data uri, in certain cases we may need a decent/fast machine otherwise we may end up killing RAM and CPU performances.&lt;br /&gt;IE8 is compatible as well except IE8 has limited data uri for CSS images, as example, and I expect same limit for this technique.&lt;br /&gt;Bear in mind when all browsers will be compatible, we will still have data stream limit problem, or better, really big files has to be parsed on the fly in one shot, no "&lt;em&gt;download progress&lt;/em&gt;" possibility.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;... now you know ... ;)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-7461690838632776876?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/7461690838632776876/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=7461690838632776876' title='6 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7461690838632776876'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7461690838632776876'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/08/html5-how-to-create-downloads-on-fly.html' title='HTML5: How To Create Downloads On The Fly'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>6</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-2154300886879161724</id><published>2011-08-17T15:00:00.004+02:00</published><updated>2011-08-18T10:37:50.941+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JSON'/><category scheme='http://www.blogger.com/atom/ns#' term='objects'/><category scheme='http://www.blogger.com/atom/ns#' term='JSONH'/><category scheme='http://www.blogger.com/atom/ns#' term='Collection'/><category scheme='http://www.blogger.com/atom/ns#' term='hybrid'/><title type='text'>JSONH And Hybrid JS Objects</title><content type='html'>I have &lt;a href="http://webreflection.blogspot.com/2011/08/last-version-of-json-hpack.html"&gt;already described JSONH&lt;/a&gt; and now I also have the proof that it's &lt;strong&gt;as safe as native JSON&lt;/strong&gt; is but on average &lt;strong&gt;2X faster&lt;/strong&gt; than native JSON operations with both &lt;a href="http://jsperf.com/jsonh/3"&gt;small&lt;/a&gt; (10 objects), &lt;a href="http://jsperf.com/jsonh/2"&gt;medium&lt;/a&gt; (100 objects), and &lt;a href="http://jsperf.com/jsonh/"&gt;massive&lt;/a&gt; (5000 objects and not a real world case, just a stress test to see how much JSONH scales) homogenous collections.&lt;br /&gt;Wherever it's not faster it's just "&lt;em&gt;as fast&lt;/em&gt;" but the best part is that it seems to be always faster on slower machines ( mobile ).&lt;br /&gt;Moreover, the 5000 objects stress example shows that &lt;em&gt;JSONH.stringify()&lt;/em&gt; produces a string with 54% of original JSON.stringify() size so here the summary: JSONH is faster on both compression and decompression plus it produces smaller output&lt;br /&gt;&lt;a href="http://ragefac.es/"&gt;&lt;img width="260" title="fuckyeah" src="http://ragefac.es/faces/b62a5a382db3f33b046af9609e1d8bfb.png" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;yeah but ... what About Hybrid Objects&lt;/h3&gt;To start with, if you don't recognize/understand what is an homogenous collection and ask me: "&lt;i&gt;what about nested objects?&lt;/i&gt;", all I can do is to point you out that &lt;a href="http://michaux.ca/articles/json-db-a-compressed-json-format"&gt;Peter Michaux&lt;/a&gt; explained this years before me.&lt;br /&gt;Have a look there and please come back after the "&lt;i&gt;aaaaahh, got it: right!&lt;/i&gt;"&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Hybrid Objects&lt;/h4&gt;Nowadays JSON is used everywhere but not everywhere with homogeneous collections. A simple example to screw up JSONH possibility is an object like this:&lt;pre class="code"&gt;&lt;br /&gt;// result of a RESTful service, Ajax, query&lt;br /&gt;// once again about generic articles: book!&lt;br /&gt;var result = {&lt;br /&gt;    category: "books",&lt;br /&gt;    subcategory: "fantasy",&lt;br /&gt;    description: [&lt;br /&gt;        {&lt;br /&gt;            title: "The Lord Of The Rings",&lt;br /&gt;            description: "Learn about the darkness"&lt;br /&gt;        }, {&lt;br /&gt;            title: "The Holy Bible",&lt;br /&gt;            description: "Learn about both light and darkness"&lt;br /&gt;        },&lt;br /&gt;        // all other results out of this list&lt;br /&gt;    ]&lt;br /&gt;};&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;If we receive an object with one or more properties containing an homogeneous collection, as is &lt;em&gt;description&lt;/em&gt; in above example, we may already decide to use JSONH advantages.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;&lt;a href="https://github.com/WebReflection/JSONH"&gt;JSONH&lt;/a&gt; On Hybrid Objects&lt;/h4&gt;It's that easy!&lt;pre class="code"&gt;&lt;br /&gt;// before we send/store/write data on output&lt;br /&gt;result.description = JSONH.pack(result.description);&lt;br /&gt;print(JSON.stringify(result));&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;If the client is aware about the fact one or more specific property is an homogeneous collection, to obtain the original object we can do this:&lt;pre class="code"&gt;&lt;br /&gt;// stringifiedResult as XHR responseText&lt;br /&gt;var obj = JSON.parse(stringifiedResult);&lt;br /&gt;obj.description = JSONH.unpack(obj.description);&lt;br /&gt;&lt;br /&gt;// or simply via JSONP callback&lt;br /&gt;data.description = JSONH.unpack(data.description);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;For the same reason JSONH is faster than JSON, this operation will grant us less bandwidth to both send or receive objects, and faster conversion performances.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;I am willing to think soon about a possible schema able to describe homogeneous collections properties out of an object ... a sort of JSONH "mapper" to automate the procedure on both server side and client side and any suggestion will be more than welcome.&lt;br /&gt;At least so far we know already how to adopt this solution :)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-2154300886879161724?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/2154300886879161724/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=2154300886879161724' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/2154300886879161724'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/2154300886879161724'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/08/jsonh-and-hybrid-js-objects.html' title='JSONH And Hybrid JS Objects'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-7708630796373044243</id><published>2011-08-16T16:00:00.007+02:00</published><updated>2011-08-18T11:10:51.052+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='unpacked'/><category scheme='http://www.blogger.com/atom/ns#' term='JSON'/><category scheme='http://www.blogger.com/atom/ns#' term='homogeneous'/><category scheme='http://www.blogger.com/atom/ns#' term='packed'/><category scheme='http://www.blogger.com/atom/ns#' term='hpack'/><category scheme='http://www.blogger.com/atom/ns#' term='Collection'/><title type='text'>Last Version Of JSON Hpack</title><content type='html'>&lt;h3&gt;Update&lt;/h3&gt; created &lt;a href="https://github.com/WebReflection/JSONH"&gt;github repository&lt;/a&gt; with (currently) JavaScript, PHP5 and Python versions.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Update&lt;/strong&gt; after quick chat on twitter with &lt;a href="https://twitter.com/devongovett"&gt;@devongovett&lt;/a&gt; who pointed out there is a similar standard called &lt;a href="https://gist.github.com/1039559"&gt;JSONDB&lt;/a&gt; I have created a &lt;a href="http://www.3site.eu/examples/json.hpack/test/JSONHF.js"&gt;JSONH(Flat) version&lt;/a&gt;. It looks &lt;a href="http://jsperf.com/jsonh/2"&gt;slightly faster&lt;/a&gt; on mobile so I may opt for this one rather than Array of keys at index 0.&lt;br /&gt;The whole array is flat and it changes from &lt;em&gt;[{a:"A"},{a:"B"}]&lt;/em&gt; to &lt;em&gt;[1,"a","A","B"]&lt;/em&gt; where the empty collection would be &lt;em&gt;[0]&lt;/em&gt; rather than &lt;em&gt;[[]]&lt;/em&gt;.&lt;br /&gt;&lt;br /&gt;Also more details here on how to &lt;a href="http://webreflection.blogspot.com/2011/08/jsonh-and-hybrid-js-objects.html"&gt;JSONH Hybrid JS Objects&lt;/a&gt;.&lt;br /&gt;&lt;hr /&gt;&lt;br /&gt;&lt;br /&gt;A while ago &lt;a href="http://webreflection.blogspot.com/2009/05/ajax-better-than-flash-amf-optimized.html"&gt;I proposed&lt;/a&gt; a &lt;a href="http://tech.groups.yahoo.com/group/json/message/1258"&gt;homogeneous collections&lt;/a&gt; &lt;a href="http://webreflection.blogspot.com/2009/05/re-introduction-to-jsonhpack.html"&gt;optimizer&lt;/a&gt; nick named &lt;a href="https://github.com/WebReflection/json.hpack"&gt;JSON.hpack&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;What I wasn't expecting is that actually different projects and developers adopted this technique to shrink down JSON size.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Basic Advantage Of JSON.hpack&lt;/h3&gt;Gzip and deflate work really good with repeated chunks of strings and this is why homogeneous collections have really good compression ratio there.&lt;br /&gt;However, gzip and deflate compression does not come for free!&lt;br /&gt;If we compress everything on server side we can easily test the CPU overload compared with uncompressed data.&lt;br /&gt;Via JSON.hpack we can still serve small or huge amount of &lt;strong&gt;dynamic and static data without&lt;/strong&gt; necessarily use &lt;strong&gt;realtime compression&lt;/strong&gt;.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Basic Notions On Compressors&lt;/h3&gt;There is no ideal algorithm yet for compressed data, any of them has pros and cons.&lt;br /&gt;A really good compression ratio may cost a lot and the algorithm is efficient if at least decompression is fast. 7-Zip is one example, it takes more than normal zip to create a single file, but final ratio is usually much better and decompression extremely fast.&lt;br /&gt;An incremental compressor as GIF is is both fast to encode and fast to decode. However, it's average compression ratio is really poor compared with PNG, which again is not fast as GIF to encode, but almost as fast as GIF to decode and capable of bringing much more complex data inside.&lt;br /&gt;On the client side we may like a truly fast compressor in order to send data to the server where more horses power can decompress in a reasonable time. Still servers have not unlimited resources.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;My Latest Improvements Over JSON.hpack&lt;/h3&gt;&lt;br /&gt;On the web is all about network layer latency, completely unpredictable specially in these smartphones/pads days.&lt;br /&gt;We also need to consider high traffic, if things go really well, and most important mobile platforms computation power, basically the equivalent of a Pentium 3 with a GeForce card from 2001.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Which Is The Best Compromise&lt;/h4&gt;The original version of JSON.hpack is able to understand which compression level is the best one for the current collection of objects. Unfortunately this is slow both on the server side and even more on the client side.&lt;br /&gt;In my opinion an intermediate layer as JSON.hpack is should &lt;strong&gt;bring advantages as fast as possible&lt;/strong&gt; in both &lt;strong&gt;client and server&lt;/strong&gt;.&lt;br /&gt;I probably failed the first time because I was more focused on &lt;em&gt;coolness&lt;/em&gt; rather than &lt;em&gt;efficiency&lt;/em&gt;.&lt;br /&gt;As example, if it takes 3X CPU load to save 5% of bytes compared with the most basic compression ratio, something is wrong because it's simply not worth it.&lt;br /&gt;As summary, the best compromise for the latest version of this compressor is to be freaking fast with small overhead and providing a good average compression ratio.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Welcome JSONH&lt;/h3&gt;In a single call this object is able to pack and unpack homogeneous collections &lt;strong&gt;&lt;a href="http://www.3site.eu/examples/json.hpack/test/latest.html"&gt;faster than native JSON&lt;/a&gt;&lt;/strong&gt; and specially on mobile platforms.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;How Is It Possible&lt;/h4&gt;To be honest I have no idea and I was surprised as well. All I could think about is the fact that JSONH makes data &lt;em&gt;flat&lt;/em&gt; which means no recursions per each object in the original list.&lt;br /&gt;This seems to boost up performances while packing and make JSON.parse life easier while unpacking.&lt;br /&gt;The extreme simplification of the algorithm may have helped a lot as well.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;JSONH Source Code&lt;/h4&gt;&lt;a href="https://github.com/WebReflection/JSONH"&gt;now on github&lt;/a&gt;!&lt;br /&gt;&lt;strike&gt;And I had no time to create the equivalent C#, PHP, and Python version&lt;/strike&gt;.&lt;br /&gt;In any case you can see how simple is the logic and I bet anybody can easily reproduce those couple of loops in whatever programming language it is.&lt;br /&gt;The minzipped size is 323 bytes but advantages over network calls can be massive. As example, if we check the console and the converted size in the &lt;a href="http://www.3site.eu/examples/json.hpack/test/latest.html"&gt;test page&lt;/a&gt;, we can see the JSONH version of the same collection is &lt;strong&gt;54%&lt;/strong&gt; smaller ... and for a faster stringify and parse? ... it cannot be that good, isn't it :)&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;JSONH Is Suitable For&lt;/h3&gt;&lt;ul&gt;&lt;br /&gt;&lt;li&gt;any RESTful API that returns homogenous collections&lt;/li&gt;&lt;br /&gt;&lt;li&gt;gzip on the fly costs too much due high traffic&lt;/li&gt;&lt;br /&gt;&lt;li&gt;map applications and routes, &lt;em&gt;[{"latitude":1.23,"longitude":5.67},{"latitude":2.23,"longitude":6.67}]&lt;br /&gt;&lt;/em&gt; will be &lt;em&gt;[["latitude","longitude"],1.23,5.67,2.23,6.67]&lt;/em&gt;&lt;/li&gt;&lt;br /&gt;&lt;li&gt;any other case I am not thinking about right now&lt;/li&gt;&lt;br /&gt;&lt;/ul&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;It is good to take old projects created a while ago and think what could be done better in current days. It's both about re-thinking with different skills and experience over real world cases. I am not sure I made everybody happy with this latest version but I am pretty sure I won't ask client or server side to be slower than native JSON + native gzip compression since at that point all advantages will be simply lost.&lt;br /&gt;This revisited version of JSONH is surprisingly faster, smaller, and easier to implement/maintain than precedent one so ... enjoy if you need it ;)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-7708630796373044243?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/7708630796373044243/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=7708630796373044243' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7708630796373044243'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7708630796373044243'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/08/last-version-of-json-hpack.html' title='Last Version Of JSON Hpack'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-2412233721391045648</id><published>2011-08-14T17:05:00.008+02:00</published><updated>2011-08-18T13:26:38.395+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='CDN'/><category scheme='http://www.blogger.com/atom/ns#' term='loader'/><category scheme='http://www.blogger.com/atom/ns#' term='LAB.js'/><category scheme='http://www.blogger.com/atom/ns#' term='yal.js'/><title type='text'>Once Again On Script Loaders</title><content type='html'>It's a &lt;a href="https://github.com/paulirish/html5-boilerplate/issues/28"&gt;long&lt;/a&gt; &lt;a href="http://blog.getify.com/2010/12/on-script-loaders/"&gt;story&lt;/a&gt; I would like to summarize in few concrete points ...&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Three Ways To Include A Script In Your Page&lt;/h3&gt;First of all, you may not need loaders at all.&lt;br /&gt;Most likely you may need an &lt;em&gt;easy to go&lt;/em&gt; and &lt;em&gt;cross platform&lt;/em&gt; build process, and &lt;a href="https://code.google.com/p/javascript-builder/"&gt;JSBuilder&lt;/a&gt; is only one of them.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;The Most Common Practice&lt;/h4&gt;This way lets users download and visualize content first but it lets developers start the JS logic ASAP as well without mandatory need to set &lt;em&gt;DOMContentLoaded&lt;/em&gt; or &lt;em&gt;onload&lt;/em&gt; event.&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;&amp;lt;!doctype html&amp;gt;&lt;br /&gt;    &amp;lt;head&amp;gt;&lt;br /&gt;        &amp;lt;!-- head content here --&amp;gt;&lt;br /&gt;    &amp;lt;/head&amp;gt;&lt;br /&gt;    &amp;lt;body&amp;gt;&lt;br /&gt;        &amp;lt;!-- body content here --&amp;gt;&lt;br /&gt;        &amp;lt;script src=&amp;quot;app.minzipped.js&amp;quot;&amp;gt;/* app here */&amp;lt;/script&amp;gt;&lt;br /&gt;    &amp;lt;/body&amp;gt;&lt;br /&gt;&amp;lt;/html&amp;gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;The "May Be Better" Practice&lt;/h4&gt;I keep saying that a web application that does not work without JavaScript should never be accessed by a user. As example, if a form won't submit without JavaScript what's the point to show it before it can possibly work? If your page strongly depends on JavaScript don't be afraid to let the user wait slightly more before the layout is visualized. The alternative is a broken experience as &lt;em&gt;welcome&lt;/em&gt;. Accordingly, use the &lt;em&gt;DOMContentLoaded&lt;/em&gt; listener over this ordered layout:&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;&amp;lt;!doctype html&amp;gt;&lt;br /&gt;    &amp;lt;head&amp;gt;&lt;br /&gt;        &amp;lt;!-- head content here --&amp;gt;&lt;br /&gt;        &amp;lt;script src=&amp;quot;app.minzipped.js&amp;quot;&amp;gt;/* app here */&amp;lt;/script&amp;gt;&lt;br /&gt;    &amp;lt;/head&amp;gt;&lt;br /&gt;    &amp;lt;body&amp;gt;&lt;br /&gt;        &amp;lt;!-- body content here --&amp;gt;&lt;br /&gt;    &amp;lt;/body&amp;gt;&lt;br /&gt;&amp;lt;/html&amp;gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;If you don't trust the DOMContentLoaded listener you can combine both layouts:&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;&amp;lt;!doctype html&amp;gt;&lt;br /&gt;    &amp;lt;head&amp;gt;&lt;br /&gt;        &amp;lt;!-- head content here --&amp;gt;&lt;br /&gt;        &amp;lt;script src=&amp;quot;app.minzipped.js&amp;quot;&amp;gt;/* app here */&amp;lt;/script&amp;gt;&lt;br /&gt;    &amp;lt;/head&amp;gt;&lt;br /&gt;    &amp;lt;body&amp;gt;&lt;br /&gt;        &amp;lt;!-- body content here --&amp;gt;&lt;br /&gt;        &amp;lt;script&amp;gt;initApp();&amp;lt;/script&amp;gt;&lt;br /&gt;    &amp;lt;/body&amp;gt;&lt;br /&gt;&amp;lt;/html&amp;gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;The Optional "defer" Attribute&lt;/h4&gt;We can eventually try to avoid the blocking problem using a defer attribute. However, this attribute is not yet widely supported cross browser and the result may be unexpected.&lt;br /&gt;Since this attribute is basically telling the browser to do not block downloads, in the very next future it could be specified both on head script or before the end of the body.&lt;br /&gt;Everything I have said about possible broken UX is still valid so ... use carefully.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;The Loading Practice&lt;/h4&gt;Classic example is &lt;a href="http://twitter.com/"&gt;twitter&lt;/a&gt; on mobile browsers and any &lt;em&gt;native&lt;/em&gt; application with a &lt;em&gt;loading&lt;/em&gt; bootstrap screen. Also Flash based websites use this technique since ages and users are used to it.&lt;br /&gt;If the amount of javascript plus CSS and assets is massive, both precedent techniques will fail.&lt;br /&gt;The first one will fail because the user doesn't know when the script will be loaded plus it's blocking so the page won't respond. Bye bye user.&lt;br /&gt;The second approach will result into a too long waiting time over a blank page ... bye bye user.&lt;br /&gt;This &lt;em&gt;loading&lt;/em&gt; approach will entertain the user for a little while, it will be lightweight, fast to visualize, and it can hold the user up to "&lt;i&gt;5 seconds&lt;/i&gt;" with cleared cache ( and hopefully much less next time with cache but if more we should really think to split the logic and lazy load as much as possible ).&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;&amp;lt;!doctype html&amp;gt;&lt;br /&gt;    &amp;lt;head&amp;gt;&lt;br /&gt;        &amp;lt;!-- head content here --&amp;gt;&lt;br /&gt;        &amp;lt;!-- most basic CSS --&amp;gt;&lt;br /&gt;    &amp;lt;/head&amp;gt;&lt;br /&gt;    &amp;lt;body&amp;gt;&lt;br /&gt;        &amp;lt;!-- most basic content --&amp;gt;&lt;br /&gt;        &amp;lt;!-- &amp;quot;animated gif&amp;quot; or loader spin --&amp;gt;&lt;br /&gt;        &amp;lt;script src=&amp;quot;bigstuff.minzipped.js&amp;quot;&amp;gt;/* code */&amp;lt;/script&amp;gt;&lt;br /&gt;        &amp;lt;!-- optional BIG CSS --&amp;gt;&lt;br /&gt;    &amp;lt;/body&amp;gt;&lt;br /&gt;&amp;lt;/html&amp;gt;&lt;br /&gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;This page should be as attractive as possible and no interaction that depends on JavaScript should be shown.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Why Scripts Loaders&lt;/h3&gt;Because an articulated website may have articulated logic split in different files.&lt;br /&gt;The main page may rely into &lt;em&gt;jQuery, commonLogic, mainPageLogic&lt;/em&gt;.&lt;br /&gt;Any sub section in the site may depend on &lt;em&gt;jQuery, commonLogic, subSectionLogic, adHocSectionLogic, etc&lt;/em&gt;.&lt;br /&gt;The build approach will fail big time here because every page will contain a &lt;strong&gt;different script&lt;/strong&gt; to download in all its variants.&lt;br /&gt;Moreover, thanks to CDN some library can be cached cross domain, including as example jQuery from that CDN.&lt;br /&gt;In this scenario a script loader is the best solution:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;$LAB&lt;br /&gt;    .script(&amp;quot;http://commoncdn.com/jquery&amp;quot;)&lt;br /&gt;    .script(&amp;quot;commonLogic.js&amp;quot;)&lt;br /&gt;    .wait()&lt;br /&gt;    .script(&amp;quot;subSectionLogic.js&amp;quot;)&lt;br /&gt;    .wait()&lt;br /&gt;    .script(&amp;quot;adHocSectionLogic.js&amp;quot;)&lt;br /&gt;    .wait(function () {&lt;br /&gt;        // eventually ready to go&lt;br /&gt;        // in this section&lt;br /&gt;    })&lt;br /&gt;;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Above example is based on &lt;a href="http://labjs.com/"&gt;LAB.js&lt;/a&gt;, a widely adopted library I have actually indirectly contributed as well solving one conflict with &lt;em&gt;jQuery.ready()&lt;/em&gt; method.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;script() and wait()&lt;/h4&gt;LAB.js has been created with performances in mind where every script will be pre downloaded as soon as it's defined in the chained logic.&lt;br /&gt;The &lt;em&gt;wait()&lt;/em&gt; method is a sort of "&lt;em&gt;JS interpretation break point&lt;/em&gt;" and it's really useful when a script depends on another script.&lt;br /&gt;Let's say &lt;em&gt;commonLogic&lt;/em&gt; is just a set of functions while &lt;em&gt;subSectionLogic&lt;/em&gt; starts with a &lt;em&gt;jQuery.ready(function () { ... })&lt;/em&gt; call, LAB.js will ensure that latter script won't be executed until jQuery is ready ... got it?&lt;br /&gt;LAB.js size once minzipped is about 2.1Kb and the best way to use it is to include LAB.js as very first script in whatever page.&lt;br /&gt;AFAIK LAB.js is not yet hosted in any major CDN but I do believe that will happen soon.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Preload Compatibility&lt;/h4&gt;LAB.js uses different techniques to ensure both pre downloads and &lt;em&gt;wait()&lt;/em&gt; behavior. Unfortunately some adopted fallback looks inevitably weak to me.&lt;br /&gt;As example, I am not a big fun of "&lt;em&gt;empty setTimeouts&lt;/em&gt;" solutions since these are used as &lt;a href="https://github.com/getify/LABjs/blob/master/LAB.src.js#L103"&gt;workaround&lt;/a&gt; over &lt;a href="https://github.com/getify/LABjs/blob/master/LAB.src.js#L115"&gt;unpredictable behaviors&lt;/a&gt;.&lt;br /&gt;&lt;strike&gt;One of these behaviors is the &lt;em&gt;readyState&lt;/em&gt; script property that on "&lt;em&gt;complete&lt;/em&gt;" state may have or may have not already interpreted the script on "&lt;em&gt;onreadystatechange&lt;/em&gt;" notification.&lt;/strike&gt;&lt;br /&gt;If we have a really slow power machine, as my netbook is, the timeout used to decide that the script has been already parsed may not be enough.&lt;br /&gt;I don't want to bother you with details, I simply would like you to understand why I came out with an alternative loader.&lt;br /&gt;Before I reach that point I wanna show an alternative technique to get rid of &lt;em&gt;wait()&lt;/em&gt; calls.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Update&lt;/strong&gt;&lt;br /&gt;It looks like few setTimeout calls will be removed soon plus apparently the setTimeout I pointed out has nothing to do with wait: my bad.&lt;br /&gt;In any case I don't fancy empty timers plus LAB.js logic is focused on cross browser parallel pre-downloads and for this reason a bit more bigger in size than all I needed for my purpose.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Avoiding &lt;em&gt;wait()&lt;/em&gt; Calls&lt;/h3&gt;JavaScript let us successfully download and parse scripts like this without problems:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;function initApplication() {&lt;br /&gt;    jQuery.ready(function () {&lt;br /&gt;        // whatever we need to do&lt;br /&gt;    });&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Please note that &lt;strong&gt;no error&lt;/strong&gt; will be thrown even if &lt;strong&gt;jQuery has not been loaded yet&lt;/strong&gt;.&lt;br /&gt;The only way to have an error is to invoke the function &lt;em&gt;initApplication()&lt;/em&gt; without jQuery library in the global scope.&lt;br /&gt;In few words, we are not in &lt;em&gt;Java&lt;/em&gt; or &lt;em&gt;C#&lt;/em&gt; world where the compiler will argue if some namespace is accessed in any defined method and not present/included as dependency before ... we are in &lt;em&gt;JavaScript&lt;/em&gt;, much cooler, isn't it? ;)&lt;br /&gt;Accordingly, if the current page initialization is wrapped in a single function we could simply use a single wait call at the end.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;$LAB // no direct jQuery calls in the global scope&lt;br /&gt;    .script(&amp;quot;http://commoncdn.com/jquery&amp;quot;)&lt;br /&gt;    .script(&amp;quot;commonLogic.js&amp;quot;)&lt;br /&gt;    .script(&amp;quot;subSectionLogic.js&amp;quot;)&lt;br /&gt;    .script(&amp;quot;adHocSectionLogic.js&amp;quot;)&lt;br /&gt;    .wait(function () {&lt;br /&gt;        initApplication();&lt;br /&gt;    })&lt;br /&gt;;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The potential &lt;em&gt;wait()&lt;/em&gt; problem I am worried about is still there but at least in a single exit point rater than distributed through the whole loading process ... still bear with me please.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;The Namespace Problem&lt;/h4&gt;&lt;br /&gt;The generic init function can be part of a namespace as well. If we have namespaces the problem is different 'cause we cannot assign &lt;em&gt;my.namespace.logic.init = function () {}&lt;/em&gt; before &lt;em&gt;my.namespace&lt;/em&gt; object has been defined.&lt;br /&gt;In this case we either create a global function for each namespace initialization/assignment or we impose a &lt;em&gt;wait()&lt;/em&gt; call between every included namespace based file.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;&lt;a href="http://code.google.com/p/yal/"&gt;yal.js&lt;/a&gt; - Yet Another ( JavaScript ) Loader&lt;/h3&gt;&lt;br /&gt;&lt;strong&gt;Update&lt;/strong&gt;&lt;br /&gt;&lt;a href="https://github.com/WebReflection/yal.js"&gt;yal.js now on github&lt;/a&gt;&lt;br /&gt;&lt;hr /&gt;&lt;br /&gt;As written in &lt;a href="http://www.3site.eu/yal/"&gt;yal.js&lt;/a&gt; landing page I have been dealing with JS loaders for a while.&lt;br /&gt;This library created a sort of "&lt;i&gt;little twitter war&lt;/i&gt;" between me and &lt;a href="https://twitter.com/getify"&gt;@getify&lt;/a&gt; where Kyle main arguments were "&lt;em&gt;why another loader?&lt;/em&gt;" followed by "&lt;em&gt;LAB.js has better performances&lt;/em&gt;".&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Why yal.js&lt;/h4&gt;It's really a tiny script that took me 1 hour tests included plus 20 minutes of refactoring in order to implement a sort of "&lt;em&gt;forced preload&lt;/em&gt;" alternative ( which kinda works but I personally don't like and neither does Kyle ).&lt;br /&gt;yal.js is &lt;strong&gt;just an alternative&lt;/strong&gt; to LAB.js and we all like alternatives, don't we?&lt;br /&gt;The main focus of yal.js is being as small and as cross browser as possible using &lt;abbr title="Keep It Simple, Stupid"&gt;KISS&lt;/abbr&gt; and &lt;abbr title="You Aint Gonna Need It"&gt;YAGNI&lt;/abbr&gt; principles.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;&lt;strike&gt;No Empty Timers&lt;/strike&gt; Essential Script Logic&lt;/h4&gt;yal.js is based on script "&lt;em&gt;onload&lt;/em&gt;" event which behavior is already defined as standard and it's widely compatible.&lt;br /&gt;If not usable in some older browser, the more reliable "&lt;em&gt;loaded&lt;/em&gt;" state of &lt;em&gt;readyState&lt;/em&gt; property is used instead. This state comes always after the "&lt;em&gt;loading&lt;/em&gt;" or "&lt;em&gt;complete&lt;/em&gt;" one.&lt;br /&gt;I could not trigger any crash or problem wit this approach and together with next point no need to use unpredictable timers.&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Simplified Wait Logic&lt;/h4&gt;In the basic version of the script any &lt;em&gt;wait()&lt;/em&gt; call will block other scripts. These won't be pre downloaded until the previous call has been completed.&lt;br /&gt;However, if we consider we may not even need wait calls:&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;yal // no direct jQuery calls in the global scope&lt;br /&gt;    .script(&amp;quot;http://commoncdn.com/jquery&amp;quot;)&lt;br /&gt;    .script(&amp;quot;commonLogic.js&amp;quot;)&lt;br /&gt;    .script(&amp;quot;subSectionLogic.js&amp;quot;)&lt;br /&gt;    .script(&amp;quot;adHocSectionLogic.js&amp;quot;)&lt;br /&gt;    .wait(function () {&lt;br /&gt;        initApplication();&lt;br /&gt;    })&lt;br /&gt;;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;yal will perform &lt;strong&gt;parallel downloads&lt;/strong&gt; same way LAB.js does and, being yal just 1.5Kb smaller, performances will be slightly better on yal rather than LAB.js&lt;br /&gt;Also for my bad experience with "&lt;em&gt;complete&lt;/em&gt;" state, I feel a bit more secure with the fact that when &lt;em&gt;wait()&lt;/em&gt; is invoked in yal.js, everything before has been surely already interpreted and executed ( but please prove me wrong if you want with a concrete example I can test online, thanks )&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Just What I Need&lt;/h4&gt;For my random and sporadic personal projects yal.js fits all my requirements. I do not use the &lt;em&gt;forced parallel downloads&lt;/em&gt; and I don't care. I have asked Kyle to be able to grab a subset of LAB.js getting rid of all extra features surely useful for all possible cases out there but totally unnecessary for mine. Unfortunately that would not have happened any soon so I created the simplest solution for all I personally needed.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;&lt;br /&gt;I am actually sorry Kyle took my little loader as a "&lt;em&gt;non sense waste of time&lt;/em&gt;" and if that's what you think as well or if you need much more from a loader, feel free to ignore it and go happily with LAB.js&lt;br /&gt;Also I am not excluding that the day LAB.js will be in any major CDN I will start using it since at that point there won't be any overhead at all and cross domain.&lt;br /&gt;&lt;br /&gt;Finally, in this post I have tried to summarize different techniques and approaches to solve a very common problem in this RIA era, hope you appreciated.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-2412233721391045648?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/2412233721391045648/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=2412233721391045648' title='9 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/2412233721391045648'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/2412233721391045648'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/08/once-again-on-script-loaders.html' title='Once Again On Script Loaders'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>9</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-7022869700987758694</id><published>2011-08-13T09:11:00.017+02:00</published><updated>2011-08-17T08:33:08.361+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='notification'/><category scheme='http://www.blogger.com/atom/ns#' term='JSONP'/><category scheme='http://www.blogger.com/atom/ns#' term='static'/><category scheme='http://www.blogger.com/atom/ns#' term='CDN'/><category scheme='http://www.blogger.com/atom/ns#' term='request'/><title type='text'>How To JSONP A Static File</title><content type='html'>&lt;strong&gt;Update&lt;/strong&gt; I have discussed this object a part and I agree that the url could be used as unique id as well.&lt;br /&gt;In this case the server should use the static url as unique id:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;StaticJSONP.notify("http://cdn.com/static/article/id.js",{..data..});&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;So that on client side we can use the simplified signature:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;StaticJSONP.request(&lt;br /&gt;    "http://cdn.com/static/article/id.js",&lt;br /&gt;    function (uid, data) {&lt;br /&gt;    }&lt;br /&gt;);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The callback will receive the &lt;em&gt;uid&lt;/em&gt; in any case so that we can create a single callback and handle behaviors accordingly.&lt;br /&gt;The &lt;a href="http://devpro.it/javascript_id_217.html"&gt;script has been updated&lt;/a&gt; in order to accept 2 arguments but, if necessary, the explicit unique id is still supported.&lt;br /&gt;&lt;hr /&gt;&lt;br /&gt;&lt;br /&gt;Under the list of "&lt;em&gt;incomplete and never posted stuff&lt;/em&gt;" I found this article which has been eventually reviewed.&lt;br /&gt;I know it's "&lt;i&gt;not that compact&lt;/i&gt;" but I really would like you to follow the reason I thought about a solution to a not so common, but quite nasty, problem.&lt;br /&gt;&lt;br /&gt;Back in 2001, my early attempts to include callbacks remotely were based on server side runtime compilation of some JavaScript data passed through a single function.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;&amp;lt;?php // demo purpose only code&lt;br /&gt;&lt;br /&gt;// do something meaningful with server data&lt;br /&gt;&lt;br /&gt;// create runtime the output data&lt;br /&gt;$output = &amp;apos;{&amp;apos;;&lt;br /&gt;foreach ($data as $key =&amp;gt; $value) {&lt;br /&gt;    $output .= $key.&amp;apos;:&amp;quot;&amp;apos;.$value.&amp;apos;&amp;quot;&amp;apos;;&lt;br /&gt;}&lt;br /&gt;$output .= &amp;apos;}&amp;apos;;&lt;br /&gt;&lt;br /&gt;echo &amp;apos;jsCallback(&amp;apos;.$output.&amp;apos;)&amp;apos;;&lt;br /&gt;&lt;br /&gt;?&amp;gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Above technique became deprecated few years ago thanks to the widely adopted &lt;strong&gt;JSON&lt;/strong&gt; protocol and its hundreds of programming languages native/coded implementations.&lt;br /&gt;Moreover, above technique became &lt;em&gt;the wrong way to do it&lt;/em&gt; thanks to a definitively better solution as &lt;a href="http://webreflection.blogspot.com/2011/02/all-you-need-for-jsonp.html"&gt;JSONP&lt;/a&gt; has been since the very beginning.&lt;br /&gt;Here an example of what JSONP services do today:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;&amp;lt;?php // still demo purpose only code&lt;br /&gt;&lt;br /&gt;echo $_GET[&amp;apos;callback&amp;apos;].&amp;apos;(&amp;apos;.json_encode($data).&amp;apos;)&amp;apos;;&lt;br /&gt;&lt;br /&gt;?&amp;gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;JSONP Advantages&lt;/h3&gt;The callback parameter is defined on the client side, which means it can be "&lt;i&gt;namespaced&lt;/i&gt;" or it can be unique per each JSONP request.&lt;br /&gt;If we consider the first example every script in the page should rely into a single global &lt;em&gt;jsCallback&lt;/em&gt; function.&lt;br /&gt;At that time I was using my code and my code only so problems like &lt;em&gt;conflicts&lt;/em&gt; or the possibility that another library would have defined a different &lt;em&gt;jsCallback&lt;/em&gt; in the global scope were not existent.&lt;br /&gt;Today I still use "&lt;i&gt;my code and my code only&lt;/i&gt;" :D when it comes to my personal projects, but at least I am more than ever aware about multiple libraries conflicts the primordial technique may cause, even if all these libraries are my own one.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;JSONP Disadvantages&lt;/h3&gt;Well, the same reason that makes JSONP powerful and more suitable technique, is the one that could make JSONP the &lt;strong&gt;wrong solution&lt;/strong&gt;.&lt;br /&gt;If we still consider the first code example, nobody could stop me to be "&lt;i&gt;really smart&lt;/i&gt;" and &lt;strong&gt;precompile&lt;/strong&gt; that file into a static one.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// static_service.js by cronjob 2011-08-14T10:00:00.000Z&lt;br /&gt;jsCallback({category:'post',author:'WebReflection',title:'JSONP Limits'});&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;While precompiled static content may be or may be not what we need for our application/service, it is clear that if no server side language is involved the common JSONP approach will fail due limitations of "&lt;em&gt;the single exit point&lt;/em&gt;" any callback in the main page depends on: the &lt;em&gt;jsCallback&lt;/em&gt; function.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Advantages Of Precompiled Static Files&lt;/h3&gt;The fastest way to serve a file from a generic domain is a static one.&lt;br /&gt;A static file can be both cached into disk memory, rather than be seek and retrieved each time, or directly into server RAM.&lt;br /&gt;Also a static file does not require any programming language involved at all and the only code that will be executed will eventually be the one in charge of serving the file over the network, aka: the HTTP Server.&lt;br /&gt;The most common real world example about static files is represented by a generic &lt;strong&gt;CDN&lt;/strong&gt; where the purpose is indeed to support as many requests per second as possible and where static files are most likely the solution.&lt;br /&gt;The only extra code that would be eventually involved is the one in charge of statistics on the HTTP Server layer but every file can be easily mirrored or stored in any sort of RAID configuration and be served as fast as possible.&lt;br /&gt;&lt;br /&gt;Another real world example could be a system like blogger.com where pages do not necessarily need to be served dynamically.&lt;br /&gt;Most of the content in whatever blog system can be precompiled runtime and many services/blog applications are doing it indeed.&lt;br /&gt;&lt;br /&gt;Same is for any other application/service that does not require real times data computations and different cron job behind the scene are in charge of refreshing the content every N minutes or more.&lt;br /&gt;If we think about any big traffic website we could do this basic analysis:&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;# really poor/basic web server performances analysis&lt;br /&gt;&lt;br /&gt;# cost of realtime computation&lt;br /&gt;1% of average CPU + RAM + DISK ACCESS per each user&lt;br /&gt;# performances&lt;br /&gt;MAX_USERS = 100;&lt;br /&gt;AVERAGE_MAX_USERS = 100;&lt;br /&gt;&lt;br /&gt;# cost of a threaded cron job&lt;br /&gt;20% of average CPU + RAM + DISK ACCESS per iteration&lt;br /&gt;# cost of static file serving&lt;br /&gt;0.1% of CPU + RAM + DISK ACCESS per user&lt;br /&gt;# performances&lt;br /&gt;MAX_USERS_NOCRON = 1000;&lt;br /&gt;MAX_USERS_WHILECRON = 800; # MAX_USERS_NOCRON - 20%&lt;br /&gt;AVERAGE_MAX_USERS = 900;&lt;br /&gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;If we consider that we may chose to delegate the cronjob to a server a part behind the intranet and the only operation per each changed static file will be a &lt;em&gt;LOCK FILE $f EXCLUSIVE, WRITE NEW CONTENT INTO $f, UNLOCK FILE $f EXCLUSIVE&lt;/em&gt; so that basically only the DISK ACCESS will be involved, we can even increase AVERAGE_MAX_USERS to 950 or more.&lt;br /&gt;I know this is a sort of off topic and virtual/conceptual analysis but please bear with me, I will bring you there soon.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Static Content And RESTful APIs&lt;/h3&gt;There is a huge amount of services out there based on JSONP. Many of them requires realtime but many probably do not. Specially in latter case, I bet nobody is implementing the technique I am going to describe.&lt;br /&gt;&lt;h4&gt;A Real World Example&lt;/h3&gt;Let's imagine I work for Amazon and I am in charge of the RESTful API able to provide any sort of article related data.&lt;br /&gt;If we think about it, a generic online shopping cart article is nothing more than a group of static info that will rarely change much during the day, the week, the month, or even the year.&lt;br /&gt;Do online users really need to be notified realitme and per each request about current user rating, reviews, related content, article description, author, and any sort of "&lt;em&gt;doesn't change so frequently&lt;/em&gt;" related to the article itself? NO.&lt;br /&gt;The only field that should be as much updated as possible is the price but still, does the price change so frequently during the lifecycle of an Amazon article? NO.&lt;br /&gt;Can my infrastructure be so smart that if, and only if, a single field of this article is change the related static file could be updated so that everybody will receive instantly the new info? YES.&lt;br /&gt;... but how can do that if JSONP does not scale with static files ?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;My StaticJSONP Proposal&lt;/h3&gt;The only difference from a normal JSONP request is that passing through the callback call any sort of library should be able to be notified.&lt;br /&gt;Being the client side library in charge of creating the requested url and having the same library knowledge about what is going to be received and before what is going to ask, all this library needs is to be synchronized with the unique id the static server file will invoke. I am going to tell you more but as quick preview, this is how the static server file will look:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;StaticJSONP.notify("unique_request_id", {the:response_data});&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Server Side Structure Example&lt;/h4&gt;Let's say we would like to keep the folder structure as clear as possible. In this Amazon example we can think about splitting articles by categories.&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;# / as web server root&lt;br /&gt;&lt;br /&gt;/book/102304.js # the book id&lt;br /&gt;/book/102311.js&lt;br /&gt;/book/102319.js&lt;br /&gt;&lt;br /&gt;/gadgets/1456.js&lt;br /&gt;/gadgets/4567.js&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;A well organized folder structure will result in both better readability for humans and easier access for most common filesystems.&lt;br /&gt;Every pre compiled file on the list will contain a call to the global &lt;em&gt;StaticJSONP&lt;/em&gt; object, e.g.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// book id 102311&lt;br /&gt;StaticJSONP.notify("amazon_apiv2_info_book_102311",{...data...});&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h4&gt;The &lt;a href="http://devpro.it/code/217.html"&gt;StaticJSONP&lt;/a&gt; Object&lt;/h4&gt;The main, and only, purpose of this tiny piece of script that almost fits in a tweet once &lt;abbr title="minified and gzipped"&gt;minzipped&lt;/abbr&gt; (&lt;em&gt;282 bytes&lt;/em&gt;) is to:&lt;ul&gt;&lt;br /&gt;    &lt;li&gt;let any library, framework, custom code, be able to request a static file&lt;/li&gt;&lt;br /&gt;    &lt;li&gt;avoid multiple scripts injection / concurrent JSONP for the same file if this has not been notified yet&lt;/li&gt;&lt;br /&gt;    &lt;li&gt;notify any registered callback with the result&lt;/li&gt;&lt;br /&gt;&lt;/ul&gt;&lt;br /&gt;Here an example of a StaticJSONP interaction on the client side:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var&lt;br /&gt;    // just as example&lt;br /&gt;    result = [],&lt;br /&gt;&lt;br /&gt;    // library 1&lt;br /&gt;    client1 = function (uri, uid, delay) {&lt;br /&gt;        function exec() {&lt;br /&gt;            StaticJSONP.request(uri, uid, function (uid, evt) {&lt;br /&gt;                result.push("client1: " + evt.data);&lt;br /&gt;            });&lt;br /&gt;        }&lt;br /&gt;        delay ?&lt;br /&gt;            setTimeout(exec, delay) :&lt;br /&gt;            exec()&lt;br /&gt;        ;&lt;br /&gt;    },&lt;br /&gt;&lt;br /&gt;    // library 2&lt;br /&gt;    client2 = function (uri, uid, delay) {&lt;br /&gt;        function exec() {&lt;br /&gt;            StaticJSONP.request(uri, uid, function (uid, evt) {&lt;br /&gt;                result.push("client2: " + evt.data);&lt;br /&gt;            });&lt;br /&gt;        }&lt;br /&gt;        delay ?&lt;br /&gt;            setTimeout(exec, delay) :&lt;br /&gt;            exec()&lt;br /&gt;        ;&lt;br /&gt;    }&lt;br /&gt;;&lt;br /&gt;// library 1 does its business&lt;br /&gt;client1("static/1.js", "static_service_1", 250);&lt;br /&gt;// so does library 2&lt;br /&gt;client2("static/2.js", "static_service_2", 250);&lt;br /&gt;&lt;br /&gt;setTimeout(function () {&lt;br /&gt;    // suddenly both requires same service/file&lt;br /&gt;    client1("static/3.js", "static_service_3", 0);&lt;br /&gt;    client2("static/3.js", "static_service_3", 0);&lt;br /&gt;    &lt;br /&gt;    setTimeout(function () {&lt;br /&gt;        alert(result.join("\n"));&lt;br /&gt;    }, 500);&lt;br /&gt;}, 1000);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;It is possible to test the &lt;a href="http://www.3site.eu/StaticJSONP/"&gt;live demo&lt;/a&gt; ... just wait a little bit and you will see this alert:&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;// order may be different accordingly&lt;br /&gt;// with website response time x file&lt;br /&gt;client1: 1&lt;br /&gt;client2: 2&lt;br /&gt;client1: 3&lt;br /&gt;client2: 3&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;If you monitor network traffic you will see that &lt;strong&gt;static/3.js is downloaded only once&lt;/strong&gt;.&lt;br /&gt;If the response is really big and the connection not so good ( 3G or worse than 3G ) it may happen that same file is required again while the first request is not finished yet.&lt;br /&gt;Since the whole purpose of StaticJSONP is to simplify server side life any redundant request will be avoided on the client side.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Unique ID ... &lt;/h3&gt;StaticJSONP can be easily integrated together with normal JSONP service.&lt;br /&gt;As example, if we need to obtain the list of best sellers, assuming this list is not static due too frequent changes, we can do something like this:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// this code is an example purpose only&lt;br /&gt;// it won&amp;apos;t work anywhere&lt;br /&gt;&lt;br /&gt;// JSONP callback to best sellers&lt;br /&gt;JSONP(&amp;quot;http://amazon/restful/books/bestSellers&amp;quot;, function (evt) {&lt;br /&gt;    // the evt contains a data property&lt;br /&gt;    var data = evt.data;&lt;br /&gt;&lt;br /&gt;    // data is a list of books title and ids&lt;br /&gt;    for (var i = 0, li = []; i &amp;lt; data.length; i++) {&lt;br /&gt;        li[i] = &amp;apos;&amp;lt;a href=&amp;quot;javascript:getBookInfo(&amp;apos; + data[i].id + &amp;apos;)&amp;quot;&amp;gt;&amp;apos; + data[i].title + &amp;apos;&amp;lt;/a&amp;gt;&amp;apos;;&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    // show the content&lt;br /&gt;    document.body.innerHTML = &amp;apos;&amp;lt;ul&amp;gt;&amp;lt;li&amp;gt;&amp;apos; + li.join(&amp;apos;&amp;lt;/li&amp;gt;&amp;lt;li&amp;gt;&amp;apos;) + &amp;apos;&amp;lt;/li&amp;gt;&amp;lt;/ul&amp;gt;&amp;apos;;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;});&lt;br /&gt;&lt;br /&gt;// the function to retrieve more info&lt;br /&gt;function getBookInfo(book_id) {&lt;br /&gt;    StaticJSONP.request(&lt;br /&gt;        &lt;br /&gt;        // the url to call&lt;br /&gt;        &amp;quot;http://amazon/restful/static/books/&amp;quot; + book_id + &amp;quot;.js&amp;quot;,&lt;br /&gt;&lt;br /&gt;        // the unique id accordingly with the current RESTful API&lt;br /&gt;        &amp;quot;amazon_apiv2_info_book_&amp;quot; + book_id,&lt;br /&gt;&lt;br /&gt;        // the callback to execute once the server respond&lt;br /&gt;        function (uid, evt) {&lt;br /&gt;            // evt contain all book related data&lt;br /&gt;            // we can show it wherever we want&lt;br /&gt;        }&lt;br /&gt;    );&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Now just imagine how many users in the world are performing similar requests right now to the same list of books, being best sellers ... &lt;br /&gt;&lt;br /&gt;&lt;h4&gt;Unique ID Practices&lt;/h3&gt;It is really important to understand the reason StaticJSONP requires a unique id.&lt;br /&gt;First of all it is not possible, neither convenient, to "&lt;i&gt;magically retrieve it from the url&lt;/i&gt;" because any RESTful API out there may have a "&lt;i&gt;different shape&lt;/i&gt;".&lt;br /&gt;The unique id is a sort of trusted, pre-agreeded, and aligned information the client side library must be aware of since there is no way to change it on the server side, being the file created statically.&lt;br /&gt;It is also important to &lt;strong&gt;prefix&lt;/strong&gt; the id so that debugging will be easier on client side.&lt;br /&gt;However, the combination to generate the unique id itself may be already ... well, unique, so it's up to us on both client and server side to define it in a possibly consistent way.&lt;br /&gt;The reason I did not use the whole &lt;em&gt;uri + id&lt;/em&gt; info on StaticJSONP request method is simple:&lt;br /&gt;if both gadgets/102.js and books/102.js contains a unique &lt;em&gt;102&lt;/em&gt; id there is no way on the client side to understand which article has been required and both gadgets and books registered callbacks will be notified, one out of two surely with the wrong data.&lt;br /&gt;It's really not complicated to &lt;em&gt;namespace&lt;/em&gt; a unique id prefix and this should be the way to go imho.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Conclusion&lt;/h3&gt;It's usually really difficult to agree unanimously to a solution for a specific problem and I am not expecting that from tomorrow everyone will adopt this technique to speed up server side file serving over common "&lt;i&gt;JSONP queries&lt;/i&gt;" but I hope you understood the reason this approach may be needed and also how to properly implement a solution that does not cause client side conflicts, that scales, that does not increase final application size in any relevant way, and it's ready to go for that day when, and if, you gonna need it. Enjoy&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-7022869700987758694?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/7022869700987758694/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=7022869700987758694' title='7 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7022869700987758694'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7022869700987758694'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/08/how-to-jsonp-static-file.html' title='How To JSONP A Static File'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>7</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-3361469875507844468</id><published>2011-08-08T17:03:00.046+02:00</published><updated>2011-08-09T18:24:21.518+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='default'/><category scheme='http://www.blogger.com/atom/ns#' term='correct'/><category scheme='http://www.blogger.com/atom/ns#' term='way'/><category scheme='http://www.blogger.com/atom/ns#' term='assignment'/><title type='text'>Please Stop Reassigning For No Reason!</title><content type='html'>I swear it &lt;strike&gt;is&lt;/strike&gt; was a short one but a &lt;em&gt;must write&lt;/em&gt; and yes, once again, since I keep seeing this kind of mistake everywhere!&lt;br /&gt;This is not about JavaScript, this is about programming whatever language you want ... if you do this, you are doing it wrong!&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Problem&lt;/h3&gt;JS Engines developers are &lt;i&gt;desperate&lt;/i&gt;! They are even posting &lt;a href="http://www.slideshare.net/newmovie/know-yourengines-velocity2011"&gt;how to help JIT compilers to go faster&lt;/a&gt; and developers seem to be so lazy that even most basic good practices are avoided.&lt;br /&gt;&lt;br /&gt;Performances a part, &lt;strong&gt;this pattern can be also dangerous&lt;/strong&gt;, specially in this &lt;em&gt;ES5&lt;/em&gt; era where getters and setters are extremely common, specially on mobile browsers where nobody cares about IE gap.&lt;br /&gt;&lt;br /&gt;I am looking at you only if you are still writing something like this in your code:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;window.whatever = window.whatever || {&lt;br /&gt;    /* the whatever it is, object, function, anything */&lt;br /&gt;};&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;where &lt;em&gt;window&lt;/em&gt; is just the generic object example.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;OMG, What Can Be Wrong ...&lt;/h3&gt;&lt;strong&gt;Everything!&lt;/strong&gt; Any object property could be a native or user defined setter. In this case above technique is invoking the potential setter passing through the potential getter.&lt;br /&gt;This simply means that:&lt;ul&gt;&lt;br /&gt;        &lt;li&gt;accordingly to the task, we are asking N extra computations or function invokes for no reason&lt;/li&gt;&lt;br /&gt;        &lt;li&gt;the setter may accept something different from what the getter returns. If this is true, result could be an error, rather than a "&lt;i&gt;smart assignment&lt;/i&gt;"&lt;/li&gt;&lt;br /&gt;        &lt;li&gt;if the setter was set already and it was a &lt;em&gt;lazy re-assignment&lt;/em&gt; logic, we are avoiding lazy assignment features/logic requiring it's execution instantly and, once again, without any reason&lt;/li&gt;&lt;br /&gt;        &lt;li&gt;if the object has &lt;strong&gt;getter only&lt;/strong&gt; the operation will throw an &lt;strong&gt;error while setting&lt;/strong&gt;&lt;/li&gt;&lt;br /&gt;&lt;/ul&gt;&lt;br /&gt;No getters or setters? It does not matter since in this way any property has to be retrieved and, if present, has to be reassigned to itself.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;How JavaScript Engines Work&lt;/h3&gt;Thanks for asking. Let's imagine every object refers behind the scene to a stack of strings representing the list of properties. This stacks is used to know if &lt;em&gt;object.hasOwnProperty("propertyName")&lt;/em&gt; or if &lt;em&gt;"propertyName" in object&lt;/em&gt; is present. Once decided if the object can access the propertyName, a sort of &lt;em&gt;-1 &lt; objectProperties.indexOf("propertyName")&lt;/em&gt; procedure, the property has to be retrieved and eventually unboxed. Once this part is complete, the reassignment does not care much about the same property. Here comes the &lt;em&gt;propertyName to propertyValue&lt;/em&gt; procedure which most likely will "erase" the older reference to reassign the new one. Even if the engine is truly smart, all possible checks/logics about memory address for the value and property name for the object has to be executed.&lt;br /&gt;If you don't believe me you can simply check the &lt;a href="http://google.com/codesearch#OAMlx_jo-ck/src/third_party/WebKit/Source/JavaScriptCore/API/JSObjectRef.cpp&amp;exact_package=chromium&amp;type=cs"&gt;Webkit engine Object source code&lt;/a&gt; and compare operations needed to set and get VS JSObjectHasProperty, basically just a call to &lt;em&gt;jsObject-&gt;hasProperty&lt;/em&gt; rather than a whole logic moved via JSObjectGetProperty plus JSObjectSetProperty, and of course, invoking hasProperty as well.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;How To Do The Same Better And Faster&lt;/h3&gt;&lt;pre class="code"&gt;&lt;br /&gt;"whatever" in window || (window.whatever = {&lt;br /&gt;    /* the whatever it is, object, function, anything */&lt;br /&gt;});&lt;br /&gt;&lt;br /&gt;// eventually easier to shortcut via minifier&lt;br /&gt;var key = "whatever";&lt;br /&gt;key in window || (window[key] = {&lt;br /&gt;    /* the whatever it is, object, function, anything */&lt;br /&gt;});&lt;br /&gt;&lt;br /&gt;// eventually easier to use but requires potentially extra memory&lt;br /&gt;// 'cause the assignment has to be created in any case&lt;br /&gt;// and it can't be ignored as it could be with precedent examples&lt;br /&gt;function setDefault(object, key, value) {&lt;br /&gt;    key in object || (object[key] = value);&lt;br /&gt;    // here we can play with the returned value&lt;br /&gt;    // I chose the function itself but it can be anything&lt;br /&gt;    // or nothing if you prefer&lt;br /&gt;    return setDefault;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;setDefault(&lt;br /&gt;    window, "whatever", {}&lt;br /&gt;)(&lt;br /&gt;    window, "somethingElse", function(){}&lt;br /&gt;)(&lt;br /&gt;    window, "howCoolIsIt", "very cool!"&lt;br /&gt;);&lt;br /&gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The reason it's better is simple: &lt;strong&gt;no setters or getters invoked plus no redundant+superfluous operations performed over *reassignment*&lt;/strong&gt;. Above snippet will simply invoke &lt;em&gt;JSObjectHasProperty&lt;/em&gt; and &lt;em&gt;jsObject-&gt;hasProperty&lt;/em&gt; so that the whole setter logic will be executed only if necessary and in any case no getter logic will ever be involved ... got it?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;It Does Not Work&lt;/h3&gt;Oh ... Really? &lt;a href="http://webreflection.blogspot.com/2010/09/opera-inevitably-unexpected.html"&gt;Most likely it's a browser bug&lt;/a&gt; you should file ASAP and even most likely a new feature not there yet. The in operator should always work as expected indeed with or without inheritance involved.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var o = Object.defineProperty({}, "test", {&lt;br /&gt;    enumerable: false,&lt;br /&gt;    writable: false,&lt;br /&gt;    configurable: false,&lt;br /&gt;    value: "OK"&lt;br /&gt;});&lt;br /&gt;&lt;br /&gt;alert("test" in o &amp;&amp; o.test); // ... guess what ...&lt;br /&gt;// OK&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Since defined properties respect the &lt;em&gt;in&lt;/em&gt; operator, nobody blocks us to define them using same pattern.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;"prop" in object || Object.defineProperty(&lt;br /&gt;    object, "prop", descriptor&lt;br /&gt;);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;I Have To Do Refactoring&lt;/h3&gt;Good, so start with this RegExp to search the evil code in all your failes:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;/([$_0-9a-zA-Z]+(?:\.[$_0-9a-zA-Z]+|\[[$_0-9a-zA-Z]+\]))\s*=\s*\1/&lt;br /&gt;    .test(fileText)&lt;br /&gt;&lt;br /&gt;// or suggested by @joseanpg&lt;br /&gt;/([$\w]+(?:\.[$\w]+|\[[$\w]+\]))\s*=\s*\1(?:[\s\|&amp;,;]|$)/m&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;and modify accordingly. The replace RegExp requires unfortunately the end of the assignment so it may be weak.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;I Kill A Kitten Each Time I Read That&lt;/h3&gt;This is what happens if you don't start &lt;em&gt;now&lt;/em&gt; with the right way so, please, &lt;a href="http://images.cheezburger.com/imagestore/2011/3/29/eacf7376-3d7a-4ff0-93d6-e42fdee50350.jpeg"&gt;THINK ABOUT KITTENS&lt;/a&gt;!&lt;br /&gt;&lt;br /&gt;&lt;img width="380" src="http://images.cheezburger.com/imagestore/2011/3/29/eacf7376-3d7a-4ff0-93d6-e42fdee50350.jpeg" /&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Update On Alternative Ways&lt;/h3&gt;As &lt;a href="http://twitter.com/diegoperini"&gt;@diegoperini&lt;/a&gt; pointed out in &lt;a href="http://twitter.com/#!/diegoperini/status/8392442407"&gt;this tweet&lt;/a&gt; another way to avoid the setter is:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;window.propertyName || (window.propertyName = {&lt;br /&gt;    /* the whatever value */&lt;br /&gt;});&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;However, above technique still invokes the getter, either defined by the user or behind the JavaScript scene ( in core ).&lt;br /&gt;My first suggestion avoids "empty getters" so even if this latter technique may be considered a better approach, it can still suffers or imply side effects.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Update On False Positives&lt;/strong&gt;&lt;br /&gt;As Diego pointed out the &lt;em&gt;"prop" in obj&lt;/em&gt; may result into a false positive if &lt;em&gt;obj.prop&lt;/em&gt; is assigned but it is &lt;em&gt;falsy&lt;/em&gt;. I consider this really an edge case and even such pattern will be error prone if the value is &lt;i&gt;truish&lt;/i&gt; but not the expected one.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;this.prop || (this.prop = {});&lt;br /&gt;&lt;br /&gt;// now imagine before&lt;br /&gt;this.prop = true;&lt;br /&gt;&lt;br /&gt;// bye bye library&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;There is actually no easy or fast enough way to compare two clones runtime in order to understand if the assigned object is the one expected. Also at that point this extra overhead would be unnecessary since re-assignment will be just faster.&lt;br /&gt;At the end of the day it's up to us to be as safe as possible still preserving common sense and good programming logic but don't tell me I am talking about premature optimizations because all I am talking about is &lt;strong&gt;logic&lt;/strong&gt; over a pattern that is similar in size with the one I am suggesting but it's completely different in therms of required operations and destroyed possibilities.&lt;br /&gt;&lt;br /&gt;We should never abuse bad practices behind the "&lt;em&gt;premature&lt;/em&gt;" flag!&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Update With Benchmark&lt;/h3&gt;&lt;br /&gt;As asked via comments, I have created a &lt;a href="http://jsperf.com/in-operator"&gt;jsperf benchmark&lt;/a&gt;. Please &lt;strong&gt;bear in mind&lt;/strong&gt; the used test is &lt;strong&gt;not a real use case&lt;/strong&gt; while described problems are still the same I have been talking about in this post.&lt;br /&gt;JIT compilers may optimize repeated code and this is most likely what happens with the &lt;em&gt;commonPattern&lt;/em&gt; approach.&lt;br /&gt;I love the fact the benchmark basically proves me wrong, when getters and setters are not involved on JS side, because it's kinda illogical accordingly with browsers implementations.&lt;br /&gt;Said that, if anybody from Chrome development would be so kind to comment why re-assignment is faster than just &lt;em&gt;in&lt;/em&gt; it would be really nice.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Conclusions&lt;/h3&gt;100000 VS 2000000 ops for non real cases are not so useful to analyze but what should be underlined is that specially with getters and setter the &lt;em&gt;in operator&lt;/em&gt; is both &lt;strong&gt;faster and safer&lt;/strong&gt; cross browser and cross platform.&lt;br /&gt;&lt;br /&gt;As example, there is only one proper way to shim &lt;a href="https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Array/isArray"&gt;Array.isArray&lt;/a&gt;.&lt;br /&gt;If we use &lt;em&gt;return typeof obj.length == "number"&lt;/em&gt; rather than &lt;em&gt;toString.call(obj) == "[object Array]"&lt;/em&gt;we will surely go faster but we will do it totally wrong as well.&lt;br /&gt;&lt;br /&gt;Last note about Webkit, we have to deal with it since it has the majority of mobile browsing market share. Special case is webOS which implements V8 rather than JSC but still, don't be blind in front of millions, just understand side effects the common pattern could cause against the right way to know if a property has been set already.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-3361469875507844468?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/3361469875507844468/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=3361469875507844468' title='25 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/3361469875507844468'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/3361469875507844468'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/08/please-stop-reassigning-for-no-reason.html' title='Please Stop Reassigning For No Reason!'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>25</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-1875021088055575066</id><published>2011-08-01T15:18:00.003+02:00</published><updated>2011-08-01T15:25:16.055+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='bookmarklet'/><category scheme='http://www.blogger.com/atom/ns#' term='bit.ly'/><title type='text'>bit.ly bookmarklet</title><content type='html'>&lt;a href="http://bitly.com/"&gt;bit.ly&lt;/a&gt; offers a proper sidebar bookmarklet but you need to sign in so, if you are really lazy and you want an easy way to shorten whatever page you are visiting, drag and drop next link into bookmarks and click it once whenever you want.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;&lt;a href="javascript:(function(){var a=window,b=a.document,d=b.documentElement,e=b.createElement(&amp;quot;script&amp;quot;),c=&amp;quot;_&amp;quot;+ +new Date;a[c]=function(b){try{delete a[c]}catch(f){a[c]=null}d.removeChild(e);prompt(&amp;quot;shortened by WebReflection bit.ly bookmarklet&amp;quot;,b.data.url)};d.insertBefore(e,d.lastChild).src=&amp;quot;http://api.bitly.com/v3/shorten&amp;quot;.concat(&amp;quot;?format=json&amp;quot;,&amp;quot;&amp;amp;domain=j.mp&amp;quot;,&amp;quot;&amp;amp;longUrl=&amp;quot;,encodeURIComponent(location),&amp;quot;&amp;amp;login=&amp;quot;,&amp;quot;webreflection&amp;quot;,&amp;quot;&amp;amp;apiKey=&amp;quot;,&amp;quot;R_f26ae58d16ddd80f358f679faa97d9b8&amp;quot;,&amp;quot;&amp;amp;callback=&amp;quot;,c)}());" name="bit.ly shortener"&gt;bit.ly shortener&lt;/a&gt;&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;enjoy :)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-1875021088055575066?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/1875021088055575066/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=1875021088055575066' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/1875021088055575066'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/1875021088055575066'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/08/bitly-bookmarklet.html' title='bit.ly bookmarklet'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-822257175345120902</id><published>2011-07-29T14:24:00.004+02:00</published><updated>2011-07-29T14:51:13.882+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='limit'/><category scheme='http://www.blogger.com/atom/ns#' term='arguments'/><category scheme='http://www.blogger.com/atom/ns#' term='apply'/><category scheme='http://www.blogger.com/atom/ns#' term='fromCharCode'/><category scheme='http://www.blogger.com/atom/ns#' term='String'/><title type='text'>About JavaScript apply arguments limit</title><content type='html'>Just a quick one from ECMAScript ml ... it is true that browsers may have a limited number of arguments per function. This may be actually a problem, specially when we use &lt;em&gt;apply&lt;/em&gt; to invoke a generic function that accepts arbitrary number of arguments.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;String.fromCharCode&lt;/h3&gt;This is a classic example that could fail with truly big collection of &lt;em&gt;char codes&lt;/em&gt; and here my suggestion to avoid such limit:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var fromCharCode = (function ($fromCharCode, MAX_LENGTH) {&lt;br /&gt;    // (C) WebReflection - DO THE FUCK YOU WANT LICENSE&lt;br /&gt;    return function fromCharCode(code) {&lt;br /&gt;        typeof code == "number" &amp;&amp; (code = [code]);&lt;br /&gt;        for (var&lt;br /&gt;            result = [],&lt;br /&gt;            i = 0,&lt;br /&gt;            length = code.length;&lt;br /&gt;            i &lt; length; i += MAX_LENGTH&lt;br /&gt;        ) {&lt;br /&gt;            result.push($fromCharCode.apply(null, code.slice(i, i + MAX_LENGTH)));&lt;br /&gt;        }&lt;br /&gt;        return result.join("");&lt;br /&gt;    };&lt;br /&gt;}(String.fromCharCode, 2048));&lt;br /&gt;&lt;br /&gt;// example&lt;br /&gt;alert(fromCharCode(80)); // P&lt;br /&gt;alert(fromCharCode([80, 81, 82, 83, 84])); // PQRST&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The revisited version accepts directly an array and performs the call &lt;em&gt;ceil(codes.length / MAX_LENGTH)&lt;/em&gt; times.&lt;br /&gt;Performances impact will be irrelevant while bigger Arrays will be parsed, hopefully, without problems.&lt;br /&gt;If we still have problems we should never forget that userAgents may have a limited amount of available RAM so ... split the task or the operation or stream it.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;It's not that difficult to apply same concept with whatever function may suffer the &lt;em&gt;apply&lt;/em&gt; and number of arguments limits: just define a maximum amount of arguments, in this case 2048, so that the task will be distributed without problems.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-822257175345120902?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/822257175345120902/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=822257175345120902' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/822257175345120902'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/822257175345120902'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/07/about-javascript-apply-arguments-limit.html' title='About JavaScript apply arguments limit'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-6012308990318567023</id><published>2011-07-28T09:11:00.011+02:00</published><updated>2011-07-28T10:25:10.401+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='Application'/><category scheme='http://www.blogger.com/atom/ns#' term='CSS3'/><category scheme='http://www.blogger.com/atom/ns#' term='fuckn.es'/><category scheme='http://www.blogger.com/atom/ns#' term='stand alone'/><category scheme='http://www.blogger.com/atom/ns#' term='embedded'/><category scheme='http://www.blogger.com/atom/ns#' term='html5'/><title type='text'>because shit happens</title><content type='html'>When you spend half week of holidays recovering because of a dislocated shoulder, when you come back and spend 1 month recovering after a shoulder surgery, or for any other smaller or bigger &lt;i&gt;shitty&lt;/i&gt; situation life could offer us, there is now a customisable way to express our anger: &lt;a href="http://fuckn.es/index.php"&gt;fuckn.es&lt;/a&gt; !&lt;br /&gt;&lt;br /&gt;&lt;iframe src="http://fuckn.es" width="360" height="380" style="border:1px solid silver"&gt;&lt;/iframe&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;100% Embedded HTML5 Application&lt;/h3&gt;One project that always fascinated me is &lt;a href="http://www.py2exe.org/"&gt;py2exe&lt;/a&gt;, an utility able to convert whole python applications into a single executable file.&lt;br /&gt;This concept is similar in OS X Applications, where everything is transparently contained in a single file.&lt;br /&gt;I have tried to reproduce a similar concept with this &lt;strong&gt;stand alone web page application&lt;/strong&gt; where the manifest is hilariously the only external dependency, totally superfluous but necessary for mobile devices.&lt;br /&gt;In any case, fuckn.es is a portable, "&lt;em&gt;copy and paste source ready to go&lt;/em&gt;", cross platform tiny app, where rather than &lt;em&gt;#! /bin/sh&lt;/em&gt; at first line, the user should simply double click it and run within a (modern) browser.&lt;br /&gt;All images, sounds, and obviously CSS, HTML, and JavaScript are included. This surely avoid advantage of self updated web apps but nobody could stop me to implement a simple &lt;a href="http://webreflection.blogspot.com/2011/02/all-you-need-for-jsonp.html"&gt;JSONP&lt;/a&gt; call to the website to compare versions:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// current version&lt;br /&gt;var current = "0.0.1";&lt;br /&gt;&lt;br /&gt;// update notification example&lt;br /&gt;JSONP("http://fuckn.es/?v=" + current + "&amp;fn", function(latest) {&lt;br /&gt;    if (latest != current) {&lt;br /&gt;        if (confirm(&lt;br /&gt;            "New version " + latest + " available.\nWant to update?"&lt;br /&gt;        )) {&lt;br /&gt;            location.herf = "http://fuckn.es";&lt;br /&gt;        }&lt;br /&gt;    }&lt;br /&gt;});&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Mobile Oriented Navigation&lt;/h3&gt;While the app works in both Desktop and Mobile browsers, latter are surely more friendly with the implemented navigation / interaction.&lt;br /&gt;The whole app can be managed with &lt;em&gt;touches and gestures&lt;/em&gt;:&lt;ul&gt;&lt;li&gt;touch the body to see the anger in action (one up to three seconds)&lt;/li&gt;&lt;br /&gt;&lt;li&gt;tap one of the top buttons to access internal sections&lt;/li&gt;&lt;br /&gt;&lt;li&gt;swipe sections to change them or tap other sections for faster tab scrolling&lt;/li&gt;&lt;br /&gt;&lt;li&gt;scroll sections if these do not fit on the device screen&lt;/li&gt;&lt;br /&gt;&lt;li&gt;interact with fields by selecting them, no need to explicitly apply changes&lt;/li&gt;&lt;br /&gt;&lt;li&gt;tap again the current opened section to close it and eventually see changes applied&lt;/li&gt;&lt;/ul&gt;All of this is surely experimental but it was fun to create such mobile friendly interface that is usable through mouse and trackpad as well .... you know, specially on Mac we are getting used to act via gestures and I am pretty sure this website won't be the first one that interact more like an iPad app on bigger screens.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Current and future HTML5 capabilities&lt;/h3&gt;fuckn.es tiny app is based on many HTML5 concepts such &lt;a href="http://www.w3.org/TR/FileAPI/"&gt;File API&lt;/a&gt;, &lt;a href="https://dvcs.w3.org/hg/audio/raw-file/tip/webaudio/specification.html"&gt;Audio&lt;/a&gt;, more related to the &lt;em&gt;audio&lt;/em&gt; element, &lt;a href="http://www.w3.org/TR/CSS/"&gt;CSS3&lt;/a&gt;, and soon coming &lt;a href="http://www.w3.org/TR/2009/WD-webstorage-20090423/"&gt;Web Storage&lt;/a&gt; to make changes persistent. I did not bother myself to make a fully cross browser app since one of these days all major browsers should support these features, including the &lt;em&gt;input with capture microphone&lt;/em&gt;, right now usable to customise the audio providing a valid source.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;JSONP Based Setup&lt;/h3&gt;The whole logic is based in a single &lt;em&gt;fucknes&lt;/em&gt; function call, passing an object such:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;fucknes({&lt;br /&gt;    color: "#F00",&lt;br /&gt;    background: "#333",&lt;br /&gt;    text: "OMG",&lt;br /&gt;    audio: [&lt;br /&gt;        "base64encodedSource1",&lt;br /&gt;        "base64encodedSource2",&lt;br /&gt;        "base64encodedSourceN"&lt;br /&gt;    ],&lt;br /&gt;    image: {&lt;br /&gt;        "00": "base64encodedImage00",&lt;br /&gt;        "10": "base64encodedImage10",&lt;br /&gt;        "11": "base64encodedImage11",&lt;br /&gt;        "30": "base64encodedImage30",&lt;br /&gt;        "31": "base64encodedImage31",&lt;br /&gt;        "60": "base64encodedImage60",&lt;br /&gt;        "61": "base64encodedImage61"&lt;br /&gt;    }&lt;br /&gt;});&lt;br /&gt;&lt;/pre&gt;The same concept is used to restore a previous or custom state file via &lt;em&gt;record&lt;/em&gt; section and soon I will put an extra input able to JSONP online a custom configuration. Of course this app makes sense if people will start customise and distribute &lt;em&gt;angers&lt;/em&gt; all over the net :)&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Inline Download&lt;/h3&gt;As soon as W3C committed the &lt;a href="http://www.whatwg.org/specs/web-apps/current-work/multipage/links.html#attr-hyperlink-download"&gt;link download property&lt;/a&gt; I have thought: &lt;em&gt;how cool is that, I can create a base64 version of a text or whatever it is and set the filename into the download property&lt;/em&gt; ... and this is what I have done. There are no browsers yet compatible with the download property so right now if we create a snapshot of the current configuration we need to "&lt;em&gt;right click&lt;/em&gt;" and &lt;em&gt;save as&lt;/em&gt;, the result will be a &lt;em&gt;text/plain&lt;/em&gt; file directly decoded for us by our browser.&lt;br /&gt;This is the first time I see such technique to avoid big post or redirect to the server in order to download something for the client and as solution it seems pretty damn cool, isn't it?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;No Server Code Involved At All&lt;/h3&gt;The last cool part is that the whole app can be used within the html file itself, there is no need of the server side and once these apps will be able to run in a &lt;em&gt;trusted&lt;/em&gt; mode, same as native apps do, through the FileReader API, the Web SQL Storage or similar, and all next generation JS features, we can truly, and eventually, think of creating native like applications using &lt;strong&gt;exactly&lt;/strong&gt; what we know already: no 3rd parts frameworks or application involved ( phonegap, Qt, appcelerator, etc )&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;This little website has been one of the most stupid and futuristic personal projects I have ever made. It was simply fun from the beginning till the end, the silly &lt;em&gt;represent your anger&lt;/em&gt; idea and the &lt;em&gt;everything in one place with no server needed&lt;/em&gt; implementation.&lt;br /&gt;It took a little while during my spare time and even this post has been prepared in different moments but eventually I have been able to activate my german PayPal account and the host finally worked as expected after DNS changes ( my fault here, I did it wrong ).&lt;br /&gt;I hope you can at least appreciate the idea and why, have a little laugh or contribute with some customisation.&lt;br /&gt;What's next? It could be face recognition to put anger through our camera snapshots or who knows what else ... stay tuned, and have fun ;)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-6012308990318567023?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/6012308990318567023/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=6012308990318567023' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/6012308990318567023'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/6012308990318567023'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/07/because-shit-happens.html' title='because shit happens'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-4088271786178138643</id><published>2011-07-11T21:39:00.005+02:00</published><updated>2011-07-12T09:34:52.486+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='setImmediate'/><category scheme='http://www.blogger.com/atom/ns#' term='CSS3'/><category scheme='http://www.blogger.com/atom/ns#' term='transitions'/><category scheme='http://www.blogger.com/atom/ns#' term='html5'/><category scheme='http://www.blogger.com/atom/ns#' term='setTimeout'/><title type='text'>Random Rant On CSS3 Transitions</title><content type='html'>&lt;strong&gt;Update&lt;/strong&gt;&lt;br /&gt;Thanks to &lt;a href="http://twitter.com/gregersrygg"&gt;@gregersrygg&lt;/a&gt; for his link and hints, this is a hackish way to solve the problem apparently cross browser and trustable ... still a hack!&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// this save one char, how cool is that!&lt;br /&gt;!function(document){&lt;br /&gt;    &lt;br /&gt;    // (C) WebReflection (As It Is) - Mit Style&lt;br /&gt;    &lt;br /&gt;    // we all love function declarations&lt;br /&gt;    function redraw() {&lt;br /&gt;        &lt;br /&gt;        // clientHeight returns 0 if not present in the DOM&lt;br /&gt;        // e.g. document.removeChild(document.documentElement);&lt;br /&gt;        // also some crazy guy may swap runtime the whole HTML element&lt;br /&gt;        // this is why the documentElement should be always discovered&lt;br /&gt;        // and if present, it should be a node of the document&lt;br /&gt;        // In all these cases the returned value is true&lt;br /&gt;        // otherwise what is there cannot really be considered as painted&lt;br /&gt;        &lt;br /&gt;        return !!(document.documentElement || 0).clientHeight;&lt;br /&gt;    }&lt;br /&gt;    &lt;br /&gt;    // ideally an Object.defineProperty&lt;br /&gt;    // unfortunately some engine will complain&lt;br /&gt;    // if used against DOM objects&lt;br /&gt;    document.redraw = redraw;&lt;br /&gt;    &lt;br /&gt;}(document);&lt;br /&gt;// tested with Opera, Firefox, Chrome, WebKit&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;... at the end of the day, nothing changed about this post because the summary is still that we do not have an official/standard way to do things properly and we need to use hacks to simplify our daily tasks.&lt;br /&gt;&lt;hr /&gt;&lt;br /&gt;&lt;br /&gt;so here the summary: there is no fucking way to use CSS3 transitions properly!&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Problem&lt;/h3&gt;We put everything on the DOM and we let nodes come in and out all the time or we are screwed!&lt;br /&gt;CSS3 transitions are freaking cool and freaking painful at the same time.&lt;br /&gt;The classic scenario is to pollute the whole DOM once or many times with our random appended/inserted HTMLElements.&lt;br /&gt;The goal is to keep the DOM as clean as possible still being able to let things &lt;i&gt;land on the DOM&lt;/i&gt; in our desired way.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;setImmediate bullshit&lt;/h3&gt;Rather than improve the single &lt;em&gt;setTimeout(callback, 0)&lt;/em&gt; classic case, the classic hack that supposes to make things work as expected and at the same time the classic timeout &lt;strong&gt;rarely stored as integer to clearTimeout later&lt;/strong&gt; does not scale.&lt;br /&gt;This is the reason vendors/HTML5 people/whoever decided to add another &lt;em&gt;unshimmable&lt;/em&gt; function: &lt;strong&gt;setImmediate&lt;/strong&gt;, which supposes to be used the same way "&lt;em&gt;setTimeout with zero delay&lt;/em&gt;" is commonly used.&lt;br /&gt;If vendors screw a bit up the same way FireFox did, where somebody pushed in some release a &lt;em&gt;requestAnimationFrame&lt;/em&gt; without thinking about the counterpart &lt;em&gt;clearRequestAnimationFrame&lt;/em&gt;, setImmediate becomes useless as well as setTimeout 0 is if nobody takes care of clearTimeout or &lt;em&gt;clearImmediate&lt;/em&gt; function.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Problem, Once Again&lt;/h3&gt;We &lt;em&gt;appendChild&lt;/em&gt; a node with &lt;em&gt;margin-left: -100px&lt;/em&gt;, a transition property equal to margin, and we add the className that supposes to put the &lt;em&gt;margin-left: 0&lt;/em&gt;.&lt;br /&gt;To solve this we need to appendChild the node then &lt;em&gt;abstractly wait for the browser to paint&lt;/em&gt; and after, eventually, set the new class.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var div = document.body.appendChild(&lt;br /&gt;    document.createElement("div")&lt;br /&gt;);&lt;br /&gt;div.style.marginLeft = "-1000px";&lt;br /&gt;// now we want the transition to marginLeft = 0 ... HOW?????&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;If by CSS3 above div has transition margin monitored, the only way to trigger the transition is to set a random timeout expecting that the browser renders in the meanwhile ... caus if it does not happen, we won't simply see it.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Why It Is So Hard&lt;/h3&gt;Unfortunately is most likely &lt;em&gt;Web Developers&lt;/em&gt; fault, in the meaning that browsers are doing everything possible to optimize callbacks.&lt;br /&gt;What we think is synchronous is just a matter of asynchronous, impossible to control, &lt;strong&gt;redraw&lt;/strong&gt; actions behind the scene, where of course if we change 3 times classes to the same node browsers just consider last status and that's what they draw.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;The Missing API&lt;/h3&gt;The more we have &lt;em&gt;illusion of powerful features&lt;/em&gt; the more we screw up our architectures and layouts .... there's not much to do here except a bloody &lt;strong&gt;synchronous document.redraw()&lt;/strong&gt; method, something that supposes to tell the engine: &lt;em&gt;hey, I wanna you to consider the &lt;strong&gt;current layout&lt;/strong&gt; so that after I can change it and you can consider these changes&lt;/em&gt;.&lt;br /&gt;&lt;br /&gt;Will it be too hard for the CPU/GPU? Who cares, I mean, with all uncontrolled and theoretically optimized redraws/repaint operations we have every N milliseconds, how can a developer choice hurt so much?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;mozAfterPaint&lt;/h3&gt;About Events, the cool part is that we can create them on JavaScript side and dispatch them whenever we want. Now, this paragraph notification is something &lt;strong&gt;we cannot fire&lt;/strong&gt; in a meaningful way but it supposes to tell us ... exactly what? No idea, because the problem is that I do not want to control the status of the DOM via unpredictable setTimeout behavior, I wanna be able to tell the browser that &lt;em&gt;status is OK now, would be so kind to draw the whole fucking thing for me, please?&lt;/em&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;As Summary&lt;/h3&gt;I hate lack of power under the &lt;em&gt;HTML5 is for developers&lt;/em&gt; flag, I see setImmediate as a joke that I will be forced to use at some point for who knows which reason, but I still miss the possibility to properly control all these CSS3 transitions power via JavaScript, and once again, messing up between the view, and the controller.&lt;br /&gt;&lt;br /&gt;Told'ya it was a rant!&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-4088271786178138643?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/4088271786178138643/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=4088271786178138643' title='11 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/4088271786178138643'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/4088271786178138643'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/07/random-rant-on-css3-transitions.html' title='Random Rant On CSS3 Transitions'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>11</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-8610813312130576308</id><published>2011-07-05T21:23:00.003+02:00</published><updated>2011-07-05T22:16:14.108+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='base64'/><category scheme='http://www.blogger.com/atom/ns#' term='html5'/><category scheme='http://www.blogger.com/atom/ns#' term='inline'/><title type='text'>Online Base 64 Converter</title><content type='html'>&lt;strong&gt;Update&lt;/strong&gt; apparently I am more than late since &lt;a href="http://datauri.com/"&gt;datauri.com&lt;/a&gt; does similar stuff ... oh well, better two options than nothing, right? Thanks &lt;a href="http://twitter.com/mathias"&gt;@mathias&lt;/a&gt; for the update.&lt;hr /&gt;&lt;br /&gt;&lt;br /&gt;Right, you may think this is the most useless thing ever but actually embedded content is freaking cool and this is the reason I have created a truly simple page in &lt;a href="http://www.3site.eu/base64/"&gt;3site.eu/base64&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;What The Hack Is That&lt;/h3&gt;Nothing truly special, you choose a file, you get its representation in base64 compatible with inline data url.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Best Available Option&lt;/h3&gt;... is converting data accordingly with your browser: who better than a browser can know how to understand inline data? &lt;strong&gt;Chrome&lt;/strong&gt; or any other &lt;strong&gt;HTML5 Enabled Browser&lt;/strong&gt; should work &lt;strong&gt;offline&lt;/strong&gt; without problems, but if you are masochist and stubborn, it may fallback into server side encoding. Latter case may be dropped as soon as my cheap space in my cheap website will suffer too many requests so ... did I say already use a decent browser?&lt;br /&gt;And that's all folks :)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-8610813312130576308?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/8610813312130576308/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=8610813312130576308' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/8610813312130576308'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/8610813312130576308'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/07/online-base-64-converter.html' title='Online Base 64 Converter'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-8583892557406628006</id><published>2011-06-24T17:13:00.008+02:00</published><updated>2011-06-25T07:23:44.366+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='PHP'/><category scheme='http://www.blogger.com/atom/ns#' term='JHP'/><category scheme='http://www.blogger.com/atom/ns#' term='experiment'/><title type='text'>JavaScript Hypertext Preprocessor</title><content type='html'>&lt;img src="http://www.3site.eu/images/ouch.png" style="float:left;margin:0 12px 12px 0" /&gt; well, the doctor said I can remove the tutor that was blocking my painful dislocated shoulder so here I am to test a "writing session" under pain killers from my bed!&lt;br /&gt;With such post title you may think that doctor was a shrink ... well, I let you figure it out after reading ;)&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;About Hybrid Programming Languages&lt;/h3&gt;We all know &lt;a href="http://jashkenas.github.com/coffee-script/"&gt;CoffeScript&lt;/a&gt;, right? As well as &lt;a href="http://code.google.com/p/traceur-compiler/"&gt;Traceur Compiler&lt;/a&gt; ... right? These are what I call Hybrid Programming Languages, or better, those kind of pseudo representation of the programming language we use, in this case still JavaScript, passing through a more abstract, enhanced, "improved" syntax (Coffee) or language features (Traceur) .&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;About PHP And JavaScript&lt;/h3&gt;If you follow me since years you may have noticed how many times I have tried to make PHP more &lt;i&gt;JavaScriptish&lt;/i&gt;. &lt;a href="http://webreflection.blogspot.com/2008/04/php-javascript-like-object-class.html"&gt;JavaScript like Object class&lt;/a&gt; is the first example from 2008, while &lt;a href="http://webreflection.blogspot.com/2009/03/jsphp-javascript-object-like-php-class.html"&gt;[js.php] A JavaScript Object Like PHP Class&lt;/a&gt; was surely a better attempt, thanks to new PHP 5.3 features, as well as &lt;a href="http://webreflection.blogspot.com/2008/06/from-future-php-javascript-like-number.html"&gt;PHP JavaScript like Number class&lt;/a&gt;, this time based on PECL operator overloads.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;I Am Not Alone&lt;/h3&gt;What I could not expect is that such "&lt;em&gt;wanna write PHP as if it is JavaScript&lt;/em&gt;" topic is an obsession for many other developers such &lt;a href="http://twitter.com/#!/t"&gt;Tantek Çelik&lt;/a&gt; with his &lt;a href="http://tantek.pbworks.com/w/page/19402872/CassisProject"&gt;CASSIS&lt;/a&gt; or &lt;a href="http://twitter.com/#!/stoyanstefanov"&gt;Stoyan Stefanov&lt;/a&gt; via &lt;a href="http://www.phpied.com/javascript-style-object-literals-in-php/"&gt;JavaScript-style object literals in PHP&lt;/a&gt;.&lt;br /&gt;As somebody commented already in one or more related posts, "&lt;em&gt;why on earth do not use simply node.js ?&lt;/em&gt;".&lt;br /&gt;Well, if node.js had even half of PHP hosts support, I am pretty sure many of us would have already solved this problem ... unfortunately node.js is "&lt;em&gt;not that ready yet&lt;/em&gt;" and for some reason hosters prefer whatever version of PHP rather than a faster and more fashionable &lt;a href="http://nodejs.org/"&gt;node.js&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;JHP: JavaScript Hypertext Preprocessor&lt;/h3&gt;The name JHP is not new for me. I have used the same name many months before projects like &lt;a href="http://phpjs.org/"&gt;php.js&lt;/a&gt; were announced.&lt;br /&gt;While latter project aim is to bring to JS functionalities from PHP, I have revolutionized a bit my own concept of JHP trying to bring into native PHP world all JS possibilities ... here some example:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// $Object and $Function&lt;br /&gt;$o = $Object();&lt;br /&gt;$o-&gt;name = 'JHP';&lt;br /&gt;$o-&gt;toString = $Function(function ($self) {&lt;br /&gt;    return $self-&gt;name;&lt;br /&gt;});&lt;br /&gt;echo $o; // JHP&lt;br /&gt;&lt;br /&gt;$Object-&gt;prototype-&gt;toString-&gt;call($o); // [object Object]&lt;br /&gt;&lt;br /&gt;$me = $Object();&lt;br /&gt;$me-&gt;name = 'WebReflection';&lt;br /&gt;$me-&gt;hasOwnProperty('name'); // true&lt;br /&gt;&lt;br /&gt;$o-&gt;toString-&gt;call($me); // WebReflection&lt;br /&gt;$o-&gt;toString(); // JHP&lt;br /&gt;&lt;br /&gt;$f = $o-&gt;toString;&lt;br /&gt;$f($me); // WebReflection&lt;br /&gt;&lt;br /&gt;// $String&lt;br /&gt;$str = $String('abc')-&gt;concat('d', 'ef', $String('g'));&lt;br /&gt;echo $str; // abcdefg&lt;br /&gt;&lt;br /&gt;echo $Object-&gt;prototype-&gt;toString-&gt;call($str); // [object String]&lt;br /&gt;&lt;br /&gt;// $String is an object&lt;br /&gt;// so it's possibe to define properties (this is a getter)&lt;br /&gt;$Object-&gt;defineProperty($str, 'name', (object)array(&lt;br /&gt;    // just recicle the method inherited from $String-&gt;prototype&lt;br /&gt;    'get' =&gt; $str-&gt;toString,&lt;br /&gt;    // set propeties&lt;br /&gt;    'enumerable' =&gt; false,&lt;br /&gt;    'writable' =&gt; false,&lt;br /&gt;    'configurable' =&gt; false&lt;br /&gt;));&lt;br /&gt;&lt;br /&gt;echo $o-&gt;toString-&gt;call($str); // abcdefg&lt;br /&gt;// invoking $str-&gt;name as getter&lt;br /&gt;// passing then through $str-&gt;toString callback&lt;br /&gt;&lt;br /&gt;$a = $Array();&lt;br /&gt;$a-&gt;push(1, 2, 3);&lt;br /&gt;echo $a-&gt;length; // 3&lt;br /&gt;&lt;br /&gt;$a-&gt;forEach(function ($value, $i, $arr) {&lt;br /&gt;    echo $value.PHP_EOL;&lt;br /&gt;});&lt;br /&gt;&lt;br /&gt;// uh, and require as well ...&lt;br /&gt;$require('sys')-&gt;print('Hello World');&lt;br /&gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;XMLHttpRequest Example&lt;/h3&gt;This is just what's already possible to extend some global.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// sync only ... well, it's PHP&lt;br /&gt;$XMLHttpRequest = $Function();&lt;br /&gt;$XMLHttpRequest-&gt;prototype-&gt;open = $Function(function ($self, $mode, $uri, $async = false) {&lt;br /&gt;    $self-&gt;_uri = $uri;&lt;br /&gt;    $self-&gt;_mode = $mode;&lt;br /&gt;});&lt;br /&gt;$XMLHttpRequest-&gt;prototype-&gt;send = $Function(function ($self, $data = null) {&lt;br /&gt;    // actually with curl we may emulate post, get, etc ...&lt;br /&gt;    $self-&gt;responseText = file_get_contents($self-&gt;_uri);&lt;br /&gt;});&lt;br /&gt;&lt;br /&gt;$xhr = $XMLHttpRequest();&lt;br /&gt;$xhr-&gt;open('get', 'http://webreflection.blogspot.com/', false);&lt;br /&gt;$xhr-&gt;send();&lt;br /&gt;echo $xhr-&gt;responseText; // this blog ... somehow&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;$Array, $Boolean, $Function, $Number, $Object, $String&lt;/h3&gt;This is almost all I have so far and everything is absolutely in a prototype/experimental status.&lt;br /&gt;This is why I have not created a repository yet, also because this project was abandoned but just recently I have read the post from phpied.com so I thought ... well, why not talk a bit about my good old experiments as well? Maybe there is something to learn, surely there is a lot to improve, also thanks to latest PHP SPL and ... well, I let you decide what to do with this folder well forgotten in my good old netbook. You tell me if it makes sense, if you like the idea, and accordingly with feedbacks I will eventually consider to re-think from the scratch the whole pile of code in order to make it better, faster, usable, etc etc ... ok?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;What's Missing&lt;/h3&gt;&lt;br /&gt;First of all ... to refactor everything, since at the beginning I remember I was trying to obtain a fresh new environment, or better, its globals, but I trapped myself without bringing the possibility to reuse current globals in a proper way.&lt;br /&gt;Said that, the thing that I have never even started to do, as example, is a Narcissus based parser able to transform for me all JavaScript into JHP, bringing via &lt;em&gt;use&lt;/em&gt; all nested scopes so that everything will be automatically available and we can really write JS and deploy on a PHP host ... this sound cool, uh? Well, let me tell you something, PHP is not that bad but such alien cannot surely be fast ;)&lt;br /&gt;Last, but not least, the require uses eval and I hate eval, even if it's damned handy in some case.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;How To Test / Where Is JHP&lt;/h3&gt;&lt;br /&gt;Well, it's here: &lt;a href="http://code.google.com/p/jhp/downloads/list"&gt;have fun with JHP&lt;/a&gt;!&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-8583892557406628006?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/8583892557406628006/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=8583892557406628006' title='6 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/8583892557406628006'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/8583892557406628006'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/06/javascript-hypertext-preprocessor.html' title='JavaScript Hypertext Preprocessor'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>6</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-6394390922950084507</id><published>2011-06-05T19:05:00.015+02:00</published><updated>2011-06-06T19:23:20.221+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='use strict'/><category scheme='http://www.blogger.com/atom/ns#' term='ES5'/><category scheme='http://www.blogger.com/atom/ns#' term='ES3'/><title type='text'>ES5 and use strict</title><content type='html'>&lt;strong&gt;Update&lt;/strong&gt;&lt;br /&gt;There was &lt;a href="http://javascriptweblog.wordpress.com/2011/05/03/javascript-strict-mode/"&gt;another article about it&lt;/a&gt; which has less examples but more complementary points or descriptions.&lt;br /&gt;Moreover, that page links to a &lt;a href="http://java-script.limewebs.com/strictMode/test_hosted.html"&gt;specific use strict compatibility page&lt;/a&gt;, right now green only with &lt;a href="http://www.mozilla.com/en-US/firefox/channel/"&gt;Firefox Aurora&lt;/a&gt; and &lt;a href="http://tools.google.com/dlpage/chromesxs"&gt;Google Chrome Canary&lt;/a&gt;.&lt;br /&gt;However, another page shows &lt;a href="http://kangax.github.com/es5-compat-table/strict-mode/"&gt;more use strict cases&lt;/a&gt; as well and Canary seems to miss one check while &lt;a href="http://nightly.webkit.org/"&gt;Webkit Nightly&lt;/a&gt; shows all green YES. &lt;a href="http://www.opera.com/browser/next/"&gt;Opera Next&lt;/a&gt; is not there yet while &lt;a href="http://ie.microsoft.com/testdrive/info/downloads/default.html"&gt;IE10&lt;/a&gt; surprisingly scores all of them except Function declaration in statements.&lt;br /&gt;Well done guys!&lt;hr /&gt;&lt;br /&gt;&lt;br /&gt;on page 233 of the &lt;a href="http://www.ecma-international.org/publications/files/ECMA-ST/ECMA-262.pdf"&gt;ECMAScript 5th Edition&lt;/a&gt; we can read details about &lt;em&gt;"use strict"&lt;/em&gt; activation and what it means for our code.&lt;br /&gt;Somebody believes this ES5 &lt;em&gt;feature&lt;/em&gt; can help developers to write less errors ... well, I think not everything is that good as it looks.&lt;br /&gt;This post is about all those points with concrete examples.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;No OctalIntegerLiteral or OctalEscapeSequence&lt;/h3&gt;&lt;br /&gt;Base 8 has not many use cases on daily JS tasks. As example, to obtain the number 8 in base 8 we can write something like &lt;em&gt;010&lt;/em&gt; where:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;alert(010 === 8);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The problem is that &lt;em&gt;01&lt;/em&gt; is not enough to force the engine to consider that number a base 8 and it will be interpreted as 1 indeed. Fair enough, I personally don't give a hack about base 8 so this does not hurt, it's just slightly simplified numbers parsing.&lt;br /&gt;Same story for &lt;em&gt;OctalEscapeSequence&lt;/em&gt;, no "&lt;i&gt;octal magic&lt;/i&gt;" anymore.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;No Global Variables&lt;/h3&gt;If our closure has a reference not defined in the outer scope, there is no global variable but a ReferenceError.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;(function(){"use strict";&lt;br /&gt;    for(i = 0; i &lt; 2; i++) {&lt;br /&gt;        // never executed due "i" ReferenceError&lt;br /&gt;    }&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Above example is a classic one ... or better, a classic for newcomers with PHP or Python background, as example, where local variables are implicit and global one should be explicit.&lt;br /&gt;While Python has a sort of implicit scope lookup with classes, PHP introduced &lt;a href="http://de2.php.net/manual/en/functions.anonymous.php"&gt;closures&lt;/a&gt; only recently (well, 5.3 which should be right now the default minor version in every bloody server).&lt;br /&gt;Since after 1 day of JavaScript development you should have got it (use &lt;em&gt;var&lt;/em&gt; for local scope variables) I do believe this is more a limit, rather than a feature.&lt;br /&gt;First of all, the current situation is quite naif since FireFox does not throw anything, it just stop working, while other browsers may nicely ignore this "feature".&lt;br /&gt;Moreover, the moment &lt;strong&gt;we want to define a global reference&lt;/strong&gt; we need to have in our closure a safe reference to the global context or &lt;strong&gt;we are simply screwed&lt;/strong&gt;.&lt;br /&gt;The second part of this point is that if the reference has been defined as &lt;em&gt;writable:false&lt;/em&gt;, aka read only as &lt;em&gt;undefined&lt;/em&gt; is, a &lt;em&gt;TypeError&lt;/em&gt; should be thrown.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;(function(){"use strict";&lt;br /&gt;    undefined = 123;&lt;br /&gt;    // throw TypeError&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Funny enough, if we have nested scope that relies in &lt;em&gt;undefined&lt;/em&gt; but the outer one has something like:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;(function(){"use strict";&lt;br /&gt;    var undefined = 123;&lt;br /&gt;    // other nested functions&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;nothing will happen, &lt;strong&gt;undefined is still not trustable&lt;/strong&gt;.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Safer arguments and eval&lt;/h3&gt;... but wasn't eval evil? Anyway, in the forth point of use strict specifications we have errors whenever we try to reassign arguments or eval.&lt;br /&gt;Fine for eval, but a kinda common arguments trick won't be usable anymore.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// this will not work anymore&lt;br /&gt;(function (context){"use strict";&lt;br /&gt;    arguments = [].slice.call(arguments, 1);&lt;br /&gt;    // some operation with arguments as Array&lt;br /&gt;    outerCallback.call(context, arguments);&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Goodbye arguments caller and callee&lt;/h3&gt;Once again, &lt;em&gt;arguments.callee&lt;/em&gt; is gone. Moreover, &lt;em&gt;arguments.callee.caller&lt;/em&gt; is done as well but in this case it's not about the caller property, the whole &lt;em&gt;callee&lt;/em&gt; concept is gone.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;(function anonymous(){"use strict";&lt;br /&gt;    alert(anonymous.caller); // throws TypeError&lt;br /&gt;    arguments.callee;            // throws TypeError&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;They call it "&lt;em&gt;graceful migration&lt;/em&gt;", I call it WTF. If &lt;em&gt;arguments&lt;/em&gt; is still there and it's a bloody object similar to an Array, why this object should throw an error with an undefined property?&lt;br /&gt;OK, it's about migration, but actually what &lt;em&gt;use strict&lt;/em&gt; introduced here is &lt;strong&gt;caller and callee as new reserved words&lt;/strong&gt;, at least for properties of arguments or whatever function ... well done ...&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;arguments indexes&lt;/h3&gt;Whenever you have noticed or not, if you change a named argument value the arguments object will be affected at the same time. Here a basic example:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// before&lt;br /&gt;(function (a, b){&lt;br /&gt;    var c = a;&lt;br /&gt;    a = b;&lt;br /&gt;    b = c;&lt;br /&gt;    alert([].slice.call(arguments));&lt;br /&gt;    // b, a&lt;br /&gt;}("a", "b"));&lt;br /&gt;&lt;br /&gt;// after&lt;br /&gt;(function (a, b){"use strict";&lt;br /&gt;    var c = a;&lt;br /&gt;    a = b;&lt;br /&gt;    b = c;&lt;br /&gt;    alert([].slice.call(arguments));&lt;br /&gt;    // a, b&lt;br /&gt;}("a", "b"));&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;To be honest, whenever it helps or not, I wonder who the hell ever used the first dynamic shared arguments indexed property value case on any sort of logic code ... was it an ES3 gotcha? Well, in such case I agree, it does not make fucking sense so ... thanks, I am sure somebody in this world will have problems about this new entry.&lt;br /&gt;However, somebody that does not know JavaScript and programming principles as well may have problems ( nothing personal man, you just did it wrong 'till now ).&lt;br /&gt;Sarcasm a part, it's good to have this clarification on specs.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Bindings and arguments&lt;/h3&gt;&lt;blockquote&gt;For strict mode functions, if an arguments object is created the binding of the local identifier arguments to the arguments object is immutable and hence may not be the target of an assignment expression. (10.5).&lt;/blockquote&gt;Well, if you get anything different form what I have said already about redefining the arguments reference/object, please do not hesitate to wake me up in the middle of the night while I am on vacations since seriously I cannot figure out what's this point about.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Unique Object Property Name&lt;/h3&gt;With ES3 we could have done something like:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;(function (){&lt;br /&gt;    var o = {&lt;br /&gt;        one: 1,&lt;br /&gt;        one: 2&lt;br /&gt;    };&lt;br /&gt;    alert(o.one); // 2 ???&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Now, since properties order is not granted at all even in a classic &lt;em&gt;for(var key in obj){}&lt;/em&gt; loop, this point is about being not ambiguous and do the right assignment once. As summary, with use strict above example will produce an error: &lt;em&gt;property name "one" appears more than once in object literal&lt;/em&gt;.&lt;br /&gt;Once again, if you ever tried to assign same property more than once ... well, I can just say it's good they made this less ambiguous but I do believe this won't improve anybody code quality (being a mistake every Unit Test would have spot in any case).&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;arguments and eval as reserved identifiers&lt;/h3&gt;It's just like that, an argument cannot be called eval or arguments otherwise we gonna have a SyntaxError.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;(function (){"use strict";&lt;br /&gt;    function testEval(eval){}&lt;br /&gt;    function testArguments(arguments){}&lt;br /&gt;    var o = {&lt;br /&gt;        get test(eval) {}&lt;br /&gt;        set test(eval) {}&lt;br /&gt;    };&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;All cases will throw an error so, once again, hwew ES5 is introducing &lt;em&gt;partial reserved keywords&lt;/em&gt; and this is &lt;strong&gt;wrong&lt;/strong&gt;, imho.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Strict eval&lt;/h3&gt;I am not sure I got the next point, but here some behavior:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var evil = (function anonymous(){"use strict";&lt;br /&gt;    return function (o_O) {&lt;br /&gt;        var result = eval(o_O);&lt;br /&gt;        alert(b);&lt;br /&gt;        return result;&lt;br /&gt;    };&lt;br /&gt;}());&lt;br /&gt;&lt;br /&gt;evil("function b(){}");&lt;br /&gt;// function b(){'use strict';}&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;// example 2&lt;br /&gt;var evil = (function anonymous(){"use strict";&lt;br /&gt;    var a = 123;&lt;br /&gt;    return function (o_O) {&lt;br /&gt;        var result = eval(o_O);&lt;br /&gt;        alert(b());&lt;br /&gt;        return result;&lt;br /&gt;    };&lt;br /&gt;}());&lt;br /&gt;&lt;br /&gt;evil("function b(){return a}"); // 123&lt;br /&gt;&lt;/pre&gt;Apparently &lt;em&gt;eval&lt;/em&gt; has been maden a bit safer but I can see its &lt;em&gt;evil nature&lt;/em&gt; all over the place without problems. Kinda good that function defined through eval inside a strict function are automatically strict as well so I guess this point is about strict inheritance through evaluation.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Strict this&lt;/h3&gt;There are different behaviors completely changed and it's not all about &lt;em&gt;undefined === this&lt;/em&gt;.&lt;br /&gt;Actually, it's not about &lt;em&gt;this&lt;/em&gt; as &lt;em&gt;undefined&lt;/em&gt; at all, &lt;strong&gt;it's about not changing the reference to something different&lt;/strong&gt;.&lt;br /&gt;There is a classic trick to obtain the global object in the most secure possible way:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var global = function(){return this}();&lt;br /&gt;alert(global); // [object Window]&lt;br /&gt;                     // [object global] in node.js&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Above example is the equivalent of this function:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;function Global() {&lt;br /&gt;    return this;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;window == Global.call() == Global.call(null) == Global.call(undefined);&lt;br /&gt;// true&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Untill now, the &lt;em&gt;this&lt;/em&gt; reference has always been changed into the global object if the context was null or undefined.&lt;br /&gt;Moreover, the reference has been changed into a proper object reference with primitives values such boolean, number, and string.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// ES3&lt;br /&gt;function previousHello() {&lt;br /&gt;    // primitive converted into new Primitive&lt;br /&gt;    // e.g. this reference is a new String(s)&lt;br /&gt;    alert("Hello " + this); // Hello World&lt;br /&gt;&lt;br /&gt;    // we can add properties to new String&lt;br /&gt;    this.test = 123;&lt;br /&gt;    alert(this.test);       // 123&lt;br /&gt;}&lt;br /&gt;var s = "World";&lt;br /&gt;previousHello.call("World");&lt;br /&gt;alert(s.test);              // undefined&lt;br /&gt;// since properties cannot be attached to a primitive&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;I don't remember I have ever defined properties runtime when the callback was about primitives values.&lt;br /&gt;To me is like using &lt;strong&gt;objects as trash bin&lt;/strong&gt; since nothing can be possibly reused after the function has been invoked.&lt;br /&gt;This is what is changed in ES5 and use strict, there is no magic anymore when &lt;em&gt;call&lt;/em&gt; or &lt;em&gt;apply&lt;/em&gt; are used.&lt;br /&gt;A primitive value will be primitive, an undefined one will be undefined and null will be null.&lt;br /&gt;Here the test case:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// ES5&lt;br /&gt;function sayHello() {"use strict";&lt;br /&gt;    alert("Hello " + this); // Hello World&lt;br /&gt;    this.test = 123;&lt;br /&gt;    alert(this.test);       // undefined&lt;br /&gt;}&lt;br /&gt;sayHello.call("World");&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;function nullThis() {"use strict";&lt;br /&gt;    alert(this); // null&lt;br /&gt;}&lt;br /&gt;nullThis.call(null);&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;function undefinedThis() {"use strict";&lt;br /&gt;    alert(this); // undefined&lt;br /&gt;}&lt;br /&gt;undefinedThis.call();&lt;br /&gt;// same as&lt;br /&gt;undefinedThis.call(undefined);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;It must be said that all these changes make life easier for engines behind the language since call and apply are widely used and all those checks about the context type and its eventual convertion are gone.&lt;br /&gt;At the same time I would have reserved &lt;em&gt;null&lt;/em&gt; as only exception to retrieve the global context since we have no more any safe way to do it and this is in my opinion bad.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;More greedy delete&lt;/h3&gt;While before we could have tried to delete variables, and without success:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;(function test(a){&lt;br /&gt;    var b = "b";&lt;br /&gt;    delete a;&lt;br /&gt;    delete b;&lt;br /&gt;    delete test;&lt;br /&gt;    alert([a, b, test]);&lt;br /&gt;    // a,b,function test(){...}&lt;br /&gt;}("a"));&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;We cannot do this kind of mistake anymore since a SyntaxError will occur.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;(function test(a){"use strict";&lt;br /&gt;    var b = "b";&lt;br /&gt;    delete a;&lt;br /&gt;    delete b;&lt;br /&gt;    delete test;&lt;br /&gt;    alert([a, b, test]);&lt;br /&gt;}("a"));&lt;br /&gt;// SyntaxError&lt;br /&gt;// applying the 'delete' operator to an unqualified name&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The fact this was not possible was clear in ES3 specs but ,,, hey, now we know it better.&lt;br /&gt;Only object properties with a configurable option equal to true can be deleted and nothing else.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;TypeError on delete&lt;/h3&gt;Even if a property is not writable, we can still delete it since it is considered a configuration option.&lt;pre class="code"&gt;&lt;br /&gt;(function test(a){"use strict";&lt;br /&gt;&lt;br /&gt;    var o = Object.create(null, {&lt;br /&gt;        deletable: {&lt;br /&gt;            value: 123,&lt;br /&gt;            configurable: true,&lt;br /&gt;            writable: false,&lt;br /&gt;            enumerable: true&lt;br /&gt;        }&lt;br /&gt;    });&lt;br /&gt;    alert(o.deletable); // 123&lt;br /&gt;    // o.deletable = 456; // Error: read-only&lt;br /&gt;&lt;br /&gt;    // bye bye property&lt;br /&gt;    delete o.deletable;&lt;br /&gt;    alert(o.deletable); // undefined&lt;br /&gt;&lt;br /&gt;    // free to manipulate&lt;br /&gt;    o.deletable = 456;&lt;br /&gt;    alert(o.deletable); // 456&lt;br /&gt;&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;To seal/froze the property and to avoid delete operation all we need to do is to mark it as not configurable.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;(function test(a){"use strict";&lt;br /&gt;&lt;br /&gt;    var o = Object.create(null, {&lt;br /&gt;        deletable: {&lt;br /&gt;            value: 123,&lt;br /&gt;            configurable: false,&lt;br /&gt;            writable: false,&lt;br /&gt;            enumerable: true&lt;br /&gt;        }&lt;br /&gt;    });&lt;br /&gt;&lt;br /&gt;    delete o.deletable;&lt;br /&gt;    // Error: property o.deletable is non-configurable&lt;br /&gt;    //        and can't be deleted&lt;br /&gt;&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Since to be able to set properties as non configurable we need ES5 already, I think this was a mistake in the use strict rules because I would expect the same behavior for something introduced in ES5 as well as &lt;em&gt;Object.defineProperty&lt;/em&gt; is.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Goodbye with statement&lt;/h3&gt;Whenever you like it or not, the &lt;em&gt;with statement&lt;/em&gt; is gone.&lt;br /&gt;I seriously do not want to spend &lt;a href="http://webreflection.blogspot.com/2009/12/with-worlds-most-misunderstood.html"&gt;more than I have done already&lt;/a&gt; about it so ... forget it, be happy about the choice and shut up or Mr Crockford and all minifiers will come out the dark wardrobe and punch you in the face.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Reserved arguments and eval identifiers&lt;/h3&gt;Everything else about &lt;em&gt;use strict&lt;/em&gt; is related to &lt;em&gt;arguments&lt;/em&gt; and &lt;em&gt;eval&lt;/em&gt; keywords.&lt;br /&gt;These cannot be used in function expressions, declarations, as variables, these cannot be reassigned, these must be used exclusively for what these are ... got it?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Summary&lt;/h3&gt;ES5 introduced &lt;em&gt;use strict&lt;/em&gt; to let developers be familiar with things that will disappear soon in the next version of JavaScript.&lt;br /&gt;I am not happy about many choices, specially regarding the caller property which was a must have for debugging and introspective purpose but ... hey, engines are not clever enough to activate these things when necessary but these engines are able to swap runtime a totally different behavior between a non strict function and a strict one.&lt;br /&gt;In few words we still do not have full JavaScript potential here because of this transition that is apparently revolutionary behind the scene, surely not the best present ever for all developers that got JavaScript and used few tricks when necessary to improve their application logic and, why not, security.&lt;br /&gt;Well ... deal with &lt;em&gt;"use strict"&lt;/em&gt; and put it there by default or shut up for all new version of JavaScript ... this is the way in any case.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-6394390922950084507?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/6394390922950084507/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=6394390922950084507' title='8 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/6394390922950084507'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/6394390922950084507'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/06/es5-and-use-strict.html' title='ES5 and use strict'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>8</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-7116690938741762029</id><published>2011-06-03T12:31:00.003+02:00</published><updated>2011-06-03T13:21:03.989+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='partial'/><category scheme='http://www.blogger.com/atom/ns#' term='JavaScript'/><category scheme='http://www.blogger.com/atom/ns#' term='polyfills'/><title type='text'>Partial Polyfills</title><content type='html'>This is a quick one already discussed during my recent workshop in Warsaw, a concept rarely considered or adopted from JS developers.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;What Are Polyfills&lt;/h3&gt;If we are updated enough to know ECMAScript 5th Edition, we probably know all possible shims and fallbacks for Array extras as well (e.g. &lt;a href="https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/array/foreach"&gt;Array.prototype.forEach&lt;/a&gt;).&lt;br /&gt;Polyfills are simply snippets able to bring features already available for most recent browsers into those not updated yet.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Why Polyfills&lt;/h3&gt;If we develop with present and future in mind, we can take advantage of most recent techniques and solutions in order to both speed up via native support, where available, and maintain our application just stripping out code once all target browsers support them natively ... isn't this cool ?!&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Polyfills Side Effects&lt;/h3&gt;The most common side effect of a polyfill is &lt;strong&gt;performances impact&lt;/strong&gt;. The Array::forEach is already a good example of decreased performances.&lt;br /&gt;If we think about a forEach, it's nothing different than a classic &lt;em&gt;for loop&lt;/em&gt;, except we can reuse a function and eventually inject a different context.&lt;br /&gt;As summary, while the code size will be reduced and all "&lt;em&gt;Array loops gotcha&lt;/em&gt;" resolved nicely, old browsers already slower will be even slower due &lt;em&gt;simulated native behavior implemented through JavaScript&lt;/em&gt;.&lt;br /&gt;The second most important side effect is that sometimes we cannot possibly reproduce the new native behavior via old JavaScript, which means we are compromising logic and potentials of our application in order to support "&lt;em&gt;not there yet&lt;/em&gt;" browsers.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Partial Polyfills&lt;/h3&gt;Once we have defined a "&lt;em&gt;full specs simulated&lt;/em&gt;" polyfill we can forget problems and use it whenever we want. Unfortunately, we have to agree with all other external libraries as well, libraries that would like to be &lt;strong&gt;dependencies free&lt;/strong&gt; and that most likely will re-implement or re-check over and over if that polyfill is present or not.&lt;br /&gt;On the other hand, there are many situations were we do not need the full implementation of a missed feature and in these cases the advantage of a &lt;strong&gt;partial polyfill&lt;/strong&gt; will result in &lt;strong&gt;reduced and safer code&lt;/strong&gt;.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;What Is A Partial Polyfill&lt;/h3&gt;Let's take the classic &lt;a href="https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Array/indexOf"&gt;Array.prototype.indexOf&lt;/a&gt; as example and check the size and the "complexity" of the full spec proposal in MDC ... done?&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// our main library closure&lt;br /&gt;(function () {&lt;br /&gt;&lt;br /&gt;// all we may need to indexOf&lt;br /&gt;var indexOf = [].indexOf || function (value) {&lt;br /&gt;    for (var i = this.length; i-- &amp;&amp; this[i] !== value;);&lt;br /&gt;    return i;&lt;br /&gt;};&lt;br /&gt;&lt;br /&gt;// wherever we need ...&lt;br /&gt;var index = indexOf.call(arrayLikeObject, value);&lt;br /&gt;&lt;br /&gt;// end of our main closure&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;If we deal with properly defined arrays, arguments, or DOM collections, and if we use indexOf simply to &lt;strong&gt;avoid duplicated entries&lt;/strong&gt; in a generic stack, ask yourself if it makes sense to implement the full specs there rather than those two lines of JS showed above.&lt;br /&gt;As somebody noticed, that snippet is more similar to &lt;a href="https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Array/lastIndexOf"&gt;Array.prototype.lastIndexOf&lt;/a&gt;, due reversed loop, but why bother if our indexOf use case is specific?&lt;br /&gt;Why pollute the global Array.prototype causing potential problems for other libraries?&lt;br /&gt;Why make the "&lt;em&gt;search into array&lt;/em&gt;" routine more expensive for already slower browsers?&lt;br /&gt;In few words we can reuse few extra bytes in every closure we want to obtain a simplified indexOf behavior compatible with every browser, isn't it ?!&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Why Safer&lt;/h3&gt;Unless we are not sure 100% that the Array.prototype.indexOf has been replaced with a full specs version and since we may lazy load extra code that may be greedy or change again that prototype, we can address that callback and use &lt;strong&gt;call&lt;/strong&gt; as much as we want being sure that &lt;strong&gt;no library will ever change our expected performances and/or behavior&lt;/strong&gt;.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Why Smaller&lt;/h3&gt;Not only we can copy and paste those two lines of code in many places without impacting code size, we can also take advantage of most popular minifiers, able to make each call smaller.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;// minified indexOf through prototype&lt;br /&gt;a.indexOf(b);&lt;br /&gt;&lt;br /&gt;// minified addressed indexOf&lt;br /&gt;x.call(a,b);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Last, but not least, using &lt;em&gt;call&lt;/em&gt; we can automatically use by default the indexOf with objects and every other ArrayLike variable.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Conclusion&lt;/h3&gt;There are many cases where we may need one or more ES5 feature but not all of them will be used 100% of their potentials. A partial polyfill can ensure better performances and easier access in the private scope.&lt;br /&gt;Surely we may avoid this technique if by default we normalize all behaviors but once again, we all know we don't like much core functionalities dependencies that may be broken or extremely slow for what we need in our specific cases.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/34454975-7116690938741762029?l=webreflection.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://webreflection.blogspot.com/feeds/7116690938741762029/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=34454975&amp;postID=7116690938741762029' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7116690938741762029'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/34454975/posts/default/7116690938741762029'/><link rel='alternate' type='text/html' href='http://webreflection.blogspot.com/2011/06/partial-polyfills.html' title='Partial Polyfills'/><author><name>Andrea Giammarchi</name><uri>http://www.blogger.com/profile/16277820774810688474</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='32' height='32' src='http://www.3site.eu/graphic/blogspot_profile.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-34454975.post-3881793266334480741</id><published>2011-05-28T00:04:00.017+02:00</published><updated>2011-05-28T10:40:26.886+02:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='JSLint'/><title type='text'>My Last Comments On JSLint</title><content type='html'>&lt;h3&gt;Preface&lt;/h3&gt;I have been working with many teams and I have used JSLint on daily basis. This post is not about the tool itself, neither against Douglas work, &lt;strong&gt;this post is about developers often too religious about this tool&lt;/strong&gt;.&lt;br /&gt;Finally, if you follow this blog you have already read tons of &lt;a href="http://webreflection.blogspot.com/2010/02/jslint-bad-part.html"&gt;other reasons&lt;/a&gt; to &lt;strong&gt;think&lt;/strong&gt; rather than "&lt;em&gt;suffer silently this tool&lt;/em&gt;".&lt;br /&gt;It's my last post about it and I hope "&lt;em&gt;it will not hurt your feelings&lt;/em&gt;".&lt;hr /&gt;&lt;br /&gt;&lt;br /&gt;Seriously guys, it's not that I think JSLint is all bad, but I cannot stop thinking it's simply an &lt;a href="http://en.wikipedia.org/wiki/Cause_and_effect"&gt;effect&lt;/a&gt;.&lt;br /&gt;The more I hear or read about developers being so religious about this tool, the more I feel to &lt;a href="http://twitter.com/#!/WebReflection/status/74226773411368961"&gt;blame it&lt;/a&gt;.&lt;br /&gt;I am pretty sure Douglas will hate me for this post but I really hope he will read it 'till the end.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Douglas Talk At Falsy Values&lt;/h3&gt;Both me and big Doug &lt;a href="http://falsyvalues.com/"&gt;were there&lt;/a&gt;, me for a workshop and Mr D. for his speech.&lt;br /&gt;"&lt;i&gt;Surprisingly&lt;/i&gt;" Mr Crockford talked about JSLint (again?!) and why it's so good.&lt;br /&gt;While many hints for newcomers are &lt;strong&gt;absolutely a must know&lt;/strong&gt;, many others are &lt;strong&gt;absolutely inconsistent&lt;/strong&gt; for senior JavaScript developers.&lt;br /&gt;There is a particular slide and a particular sentence Douglas said there:&lt;br /&gt;&lt;blockquote&gt;... write code the way it's meant for the language ...&lt;/blockquote&gt;&lt;br /&gt;Above sentence was related to &lt;em&gt;variables declaration&lt;/em&gt;, showing behind something similar to this classic example:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;(function () {&lt;br /&gt;    // never executed&lt;br /&gt;    if (false) {&lt;br /&gt;        var something = 123;&lt;br /&gt;    }&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;As all of us know, and if not we should, the reason JSLint would like to have all variables defined on top of the function is that no matter which condition, for or while loop, we have at some point, the parser will pre-consider all &lt;em&gt;var&lt;/em&gt; in the same scope as local scope variables available since the very beginning.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;(function () {&lt;br /&gt;    // there is no "var" in this scope&lt;br /&gt;    alert(something);&lt;br /&gt;    // throws "Can't find variable: something"&lt;br /&gt;    if (false) {&lt;br /&gt;        // eventually global in ES3 and ES5 with no strict&lt;br /&gt;        something = 123;&lt;br /&gt;    }&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;The moment we define a variable local, even if we never reach that line, that variable is available for the whole scope, got it?&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;(function () {&lt;br /&gt;    alert(something);&lt;br /&gt;    // undefined and no errors&lt;br /&gt;    if (false) {&lt;br /&gt;        var something = 123;&lt;br /&gt;    }&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Good, now ...&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;JSLint Inconsistencies&lt;/h3&gt;Since the previous point is clear to everybody, I wonder if it's clear that &lt;strong&gt;function declaration has even more precedence than variables&lt;/strong&gt;.&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;(function () {&lt;br /&gt;    alert(something);&lt;br /&gt;    // the function declared later on&lt;br /&gt;&lt;br /&gt;    function something() {&lt;br /&gt;        return 123;&lt;br /&gt;    }&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;This is not true for function expressions, where the result will still be the same obtained with variables:&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;(function () {&lt;br /&gt;    alert(something);&lt;br /&gt;    // undefined and no errors&lt;br /&gt;&lt;br /&gt;    var something = function() {&lt;br /&gt;        return 123;&lt;br /&gt;    };&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Accordingly, &lt;strong&gt;function declaration is referenced on top of everything, variables included&lt;/strong&gt;!&lt;br /&gt;So why on bloody earth this piece of code does not pass JSLint?&lt;br /&gt;&lt;pre class="code"&gt;&lt;br /&gt;var something = (function () {&lt;br /&gt;&lt;br /&gt;    // top reference available ever&lt;br /&gt;    // function declaration&lt;br /&gt;    function something() {&lt;br /&gt;        return oneTwoThree;&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    // second references available in this scope&lt;br /&gt;    // local scope variable&lt;br /&gt;    var oneTwoThree = 123;&lt;br /&gt;&lt;br /&gt;    // return the local function call&lt;br /&gt;    return something();&lt;br /&gt;&lt;br /&gt;}());&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;a href="http://www.jslint.com/"&gt;Try by yourself&lt;/a&gt; the result:&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;Error:&lt;br /&gt;Implied global: oneTwoThree 5&lt;br /&gt;&lt;br /&gt;Unused variable: oneTwoThree 1 'something'&lt;br /&gt;&lt;br /&gt;---------------------------------&lt;br /&gt;&lt;br /&gt;Global something&lt;br /&gt;&lt;br /&gt;1 'something'()&lt;br /&gt;Unused oneTwoThree&lt;br /&gt;Complexity 1&lt;br /&gt;&lt;br /&gt;4 something()&lt;br /&gt;Global oneTwoThree&lt;br /&gt;Complexity 1&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;I can bet the amount of bullshit I can read in latter result is a shame for Douglas Crockford in first person, isn't it?&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Not Only Inconsistencies&lt;/h3&gt;Another part covered by Doug speech was the &lt;a href="http://webreflection.blogspot.com/2009/12/with-worlds-most-misunderstood.html"&gt;with&lt;/a&gt; &lt;a href="http://webreflection.blogspot.com/2009/12/with-some-good-example.html"&gt;statement&lt;/a&gt; ... here summarize:&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;... somebody &lt;i&gt;(n.d. I guess me)&lt;/i&gt; may argue that the with statement may be useful in certain situations, but since it is always ambiguous and there is nothing that could not be done without it, the with statement should disappear from JavaScript ....&lt;br /&gt;&lt;/blockquote&gt; ... and this is what happened.&lt;br /&gt;If we try &lt;em&gt;"use strict";&lt;/em&gt; activation in most recent browsers we can spot that the &lt;em&gt;with statement&lt;/em&gt; is not allowed anymore, "&lt;i&gt;thanks&lt;/i&gt;"!&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;A Tool To Rule Them All&lt;/h3&gt;It was actually a colleague of mine asking Douglas this question (or what I got about it) :&lt;blockquote&gt;&lt;br /&gt;... so, you are saying that JS developers have no discipline, but don't you think that "&lt;em&gt;dictating discipline&lt;/em&gt;" is not such easy task as well? ...&lt;br /&gt;&lt;/blockquote&gt;I honestly do not remember the answer but I am sure Douglas provided a proper one ... anyway ... what I do believe is that &lt;strong&gt;every developer has is own style, as long as syntax and readability are not too much compromised&lt;/strong&gt;.&lt;br /&gt;If we use this tool thinking our code will improve any how we are first of all acting like machines plus we are not considering a "&lt;em&gt;little detail&lt;/em&gt;" ...&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Your Team Does Not Know JavaScript&lt;/h3&gt;Precisely! I know this is hard to face, but in 11 years of JavaScript programming I have never found a reason to have such tool that &lt;strong&gt;changes allowed programming language syntax defined by specifications&lt;/strong&gt; ... fucking &lt;a href="http://www.ecmascript.org/"&gt;read them&lt;/a&gt; and stop winging! (and pardon my french)&lt;br /&gt;In few words, I have never had a single problem to understand any other piece of JavaScript code written by any possible developer out there but when I had a problem, and at the beginning of whatever programming language we all have, I have investigated, studied, and finally understood, what was going on in that piece of code and what was &lt;strong&gt;missing from my JS knowledge&lt;/strong&gt; about it.&lt;br /&gt;&lt;strong&gt;Surely I did not blame the other developer&lt;/strong&gt;, since if we would like to be monkeys on daily basis, of course we should use as many tools as possible that throw warnings even if the piece of code we wrote is absolutely correct, and we still have my precedent example few paragraph before as proof ...&lt;br /&gt;On the other hand, if we would like to &lt;strong&gt;master our JavaScript knowledge&lt;/strong&gt; there is no way &lt;strong&gt;a piece of code that perfectly works could be screwed up because of JSLint&lt;/strong&gt;.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;Early JavaScript Days&lt;/h3&gt;When Douglas Crockford was still promoting JavaScript all over the world, nobody had any idea what he was talking about ... well, &lt;strong&gt;now we all have&lt;/strong&gt;.&lt;br /&gt;This bloody language is absolutely everywhere and those "&lt;em&gt;feeling cool&lt;/em&gt;" Java developers that still think JS is a toy are regretting 50% of their studies because they just don't get it ... that's why projects like &lt;a href="http://code.google.com/webtoolkit/overview.html"&gt;GWT&lt;/a&gt; exists: developers that think JavaScript is a toy, write Java that is gonna be translated into Javascript ... and this is &lt;strong&gt;how powerful and flexible JavaScript is&lt;/strong&gt;.&lt;br /&gt;In these days, and surely before, we truly need discipline and a lot of hints since as lazy developers we could not spend half a day reading ECMAScript 3rd Edition specs ... isn't it?&lt;br /&gt;In these days, and for these developers, of course JSLint &lt;strong&gt;has to be there&lt;/strong&gt;, they don't know what they are doing but hey, at least they are willing to learn something more from this tool (and most likely behind a syntax translator such GWT is, created to do not throw JSLint warnings ...) .&lt;br /&gt;As demonstrated before, &lt;strong&gt;this is not enough&lt;/strong&gt;.&lt;br /&gt;Java skills into JavaScript language are similar to me pretendng to have &lt;a href="http://en.wikipedia.org/wiki/Alex_Martelli"&gt;Alex Martelli&lt;/a&gt; knowledge using Visual Basic 6 on daily basis ... I hope you know what I mean ...&lt;br /&gt;As summary, if you think you can move knowledge from another programming language without deeply understanding the new one pretending you come from "&lt;em&gt;something better&lt;/em&gt;" you are half way trough your own failure.&lt;br /&gt;At the end of the day it may not matters, as long as the next point is clear for everybody.&lt;br /&gt;&lt;br /&gt;&lt;h3&gt;TDD And Unit Tests Are The Only "Safer Way"&lt;/h3&gt;Yeah you read it right ... there is no way our JavaScript code is gonna be any safer because of JSLint or whatever JS validation tool: &lt;strong&gt;no&lt;/strong&gt; fucking &lt;strong&gt;way&lt;/strong&gt;!&lt;br /&gt;If we think that &lt;em&gt;===&lt;/em&gt; rather than &lt;em&gt;==&lt;/em&gt; is all we need to be safe, without understanding why we may be safer or why we may do &lt;a href="http://webreflection.blogspot.com/2010/10/javascript-coercion-demystified.html"&gt;something simply redundant&lt;/a&gt; without considering &lt;strong&gt;cases where we want to &lt;em&gt;==&lt;/em&gt;&lt;/strong&gt;, we have never been so wrong.&lt;br /&gt;Unit Tests, and more Unit Tests on top of Unit Tests are &lt;strong&gt;the only answer to our code quality&lt;/strong&gt;!&lt;br /&gt;It does not matter how we write routines as long as &lt;strong&gt;real Senior Developers can understand it&lt;/strong&gt;, simply asking more if they really don't, and as long as &lt;strong&gt;all our possible implementation cases have been considered&lt;/strong&gt;.&lt;
