
90% Good parts of jQuery - at only 13% of the size - mythz
https://github.com/mythz/jquip
======
pamelafox
After measuring the loading performance of my PhoneGap app and seeing that
jQuery took 800ms to load (even when cached), I spent the last few days
porting from jQuery to Zepto, which boasts a similar API but loads in only
300ms. You can see the load times here:
[https://docs.google.com/spreadsheet/ccc?key=0Aq_a4WNAMuCEdDd...](https://docs.google.com/spreadsheet/ccc?key=0Aq_a4WNAMuCEdDdjSlhyWXJaTkQ0TVJFc1k1RzlTTlE)
(You can see how I did the measurements in this post:
[http://www.everyday.im/learning/phonegap-loading-
performance...](http://www.everyday.im/learning/phonegap-loading-
performance.html))

While porting 6 jQuery plugins over, I encountered various differences in the
APIs and it was a bit of a headache to sort through them (especially the very
subtle differences), but it was worth it.I'm writing a blog post currently on
my porting experience, as I imagine others might take on the task and
encounter similar issues.

For people comparing Zepto to this offering, keep in mind that Zepto also
offers mobile-specific events, so if your reason for porting is mobile
latency, Zepto's a good bet.

~~~
nicknyc
Users stay on a website for more than 800ms.

Wouldn't it be more cost effective (rather than convert/port a whole site to a
new js lib) to rewrite your page init JavaScript so it does not require a js
lib at all (0ms)? Jquery would be async loaded by the time the user executes
actions/buttons; if it had not loaded yet you wait, or show a loading icon,
etc.

This porting/optimization adds no value to your users 6 months from now who
are running a quad core nexus-razr-droid's browser that loads jquery in 300ms.

~~~
bad_user
Moore's law is applied differently to mobile phones, as processing power is
less important than battery life. And even if phones will get a lot more
powerful, that's secondary to poor bandwidth, a problem that I bet we'll still
have 4 years from now.

I use jQuery because it makes Javascript usage sane. Without it I would hate
my job.

~~~
dingle_thunk
Have a play with CofffeeScript - perhaps it'll give you enough syntactic sugar
that client-side frameworks become unnecessary.

~~~
bad_user
CoffeeScript only takes care of syntax problems. It doesn't handle DOM
traversing or other API related issues.

------
nikcub
the jQuery project has started doing this[1].

It was at risk of ending up like PHP (in more ways than one). the core team
recognizes that the API needs a trim. I also no longer use jQuery and haven't
in a while because of the bloat.

but I think the way they are approaching it is wrong. They want to trim the
API by 10% for the next -1.8- (edit: 1.7) release. This would break semantic
versioning[2].

I think they should fork the code now with a new 'jQuery 2' branch and not
break any backwards compatibility in the 1.x branch. The 2.x branch should be
a complete re-org with browser support as modules (for eg. if you want to
support IE 6.0 you enable a module, etc.)

For now, the jQuery light branch should be optional in 1.x. There are
analogies in this approach with what PHP did between 4 and 5, and what Python
did between 2 and 3. jQuery shouldn't be stripping out API functions in point
releases, but it definitely, definitely needs a trim (and I would rather this
work is done on the mainline jQuery project rather than in forks. I think a
lot of devs at the moment have forks of Zepto/jQuery they run (i do)).

this project may be the perfect starting point for a jQuery2 branch. i'd
definitely be interested in working on that project, and bringing in features
from all the various forks and cleaning it up.

[1] <http://blog.jquery.com/2011/11/08/building-a-slimmer-jquery/>

[2] <http://semver.org/>

Edit: the deprecated API functions are planned for v1.7, not v1.8 - which
means soon. I think it will cause a mess for people who auto-upgrade.

~~~
johnbender
The most important deprecations are of live/die, though they won't be removed
until 1.9. Use delegate as the replacement

    
    
        $("#foo").live("click", function(){ });
    

is equivalent to

    
    
        $(document).delegate( "#foo", "click", function() { });

~~~
masklinn
> Use delegate as the replacement

Actually, use the new `#on` as replacement: it can handle the job of `#bind`
and `#delegate` (and `#live` of course), so I'd fully expect it to be the only
one remaining in the fullness of time.

Warning: the first two arguments are reversed compared to `#delegate`:

    
    
        $(document).delegate("#foo", "click", function() { });
    

becomes

    
    
        $(document).on("click", "#foo", function() { });

~~~
funksta
There's a nice article about transitioning to .on() and .off(), including the
changes and benefits, at:

<http://www.andismith.com/blog/2011/11/on-and-off/>

------
lunaru
The README for this desperately needs the blacklist, not the whitelist. I care
a lot more about the 10% that's missing.

Unfortunately, the "limitations" sections reads fairly cryptically. I'm
probably just a little slow today. Can anyone explain what's actually not
included? For example are "Valid Examples" examples of what's allowed or not
allowed?

~~~
kellishaver
From the readme, I see two major show-stoppers for me; no .delegate() - or
even .live(), and no support for the 'change' event... and I can't tell if
selectors support filters like :first, :last, :checked, etc.

~~~
southpolesteve
Really no .live()? That would be a deal breaker for most of my projects

~~~
est
As of jQuery 1.7, the .live() method is deprecated.

<http://api.jquery.com/live/>

------
kemayo
"Events passed to your event handers are the 'real' browser DOM events."

This is a real deal-breaker for me. One of the absolute best things about
jQuery is how it normalizes events, so you don't have to _care_ that, e.g.,
the source element is event.target in some browsers and event.srcElement in
others.

~~~
mythz
Note: jquery is also removing copying unifid props from the events, instead
needing to access it in future via $.originalEvent.srcElement, etc

<http://blog.jquery.com/2011/11/08/building-a-slimmer-jquery/>

~~~
shadowfiend
I don't think that means it's removing unified properties. I think that means
that srcElement won't be copied in, but target will still refer to the right
thing (i.e., to srcElement if that's what the current browser is providing).
It's just not also providing a copy of srcElement for the user.

------
mambodog
Perhaps this could be jQuery's Merb, encouraging the jQuery developers to
reexamine the current monolithic package. I'd appreciate a modular version
that can still be built as full-size jQuery for situations in which it is
convenient.

------
numlocked
Don't most apps reference jQuery from a CDN source (like Google)? In those
cases jQuery is probably served from the browser cache. And if "those cases"
are "most cases", is having a smaller version of a similar library
particularly valuable?

~~~
pamelafox
The parse time is significant for jQuery, atleast on some mobile devices. For
example, in my tests on an Android N1 today, jQuery took 800ms to parse (even
when cached) whilst Zepto took 300ms -- saving 500ms.

~~~
DiabloD3
Google in their Page Speed ranking consider 100kb == 100ms.

See: [https://code.google.com/speed/page-
speed/docs/mobile.html#De...](https://code.google.com/speed/page-
speed/docs/mobile.html#DeferParsingJS)

BTW, their Page Speed thing is now available online:
<https://developers.google.com/pagespeed/>

~~~
dextorious
Parent talks about _parsing_ speed.

~~~
DiabloD3
So does Google.

------
ryan-allen
The 'competitive advantage' JQuery has over the competition is the fact it's
been so thoroughly tested in so many browsers for its plethora of features.

I hope this library gains some traction, as I'd love to see a JQuery clone
that could be modified to pass in targets as named parameters instead of the
over-reliance of 'this'.

Every tech seems to have an annoying something. PHP it's the order of
arguments in stdlib functions, in Rails it's indirect code ruining your day,
in JQuery it's 'what does this refer to again in this context?', and 'var that
= this', ugh!

~~~
ayu
If you're talking about variables in closures, a coworker of mine has a pretty
clever way to do it: "var _this = this". It's just a generally useful part of
javascript.

~~~
ludwigvan
I usually do var $that = $(this);, the $ prefix is a Hungarian notation trick
that shows variables that have been jQuery'fied.

------
mmaunder
jQuery 1.7.0 is 94K.

jQuery 1.7.0 gzipped is 33K.

I'm performance obsessed since if our biz serves an additional 2K on our
widgets it's an extra 1.86TB of transfer/month.

However for most on-site content, 33K is the size of a large image. Most delay
loading a web page is caused by latency. Latency in the three way handshake to
establish TCP connections and latency for each additional HTTP request even
with keepalive enabled. Payload is not as big an issue because it needs fast
throughput, not fast round-trip times which are impossible to achieve if
you're far away from the server.

Smaller and faster are always good and always worth striving for (in coding).
So I don't want to take away from this, especially since it means more eyes on
jQuery. I think it's great work. But keep in mind that the speed increase is
not going to be enormous and the cost is running a non-standard jQuery that
lacks .css(), .ajax() and $(function()).

~~~
mythz
It's not just code-base size that affects performance. There's the latency of
the extra network hit, parse js time, etc.

$(function()) isn't included because it's generally bad practice over having
javascript run immediately at the bottom before the </body> tag.

If you're site doesn't use $.ajax() why include it? many sites don't use ajax.

$.css() isn't included by default because it's implementation is huge. I
prefer to addClass/removeClass (which only causes 1 reflow) or set element
styles directly.

~~~
nicpottier
> $(function()) isn't included because it's generally bad practice over having
> javascript run immediately at the bottom before the </body> tag.

Really? I'm not a Javascript expert but I play one on TV and I always thought
$(function()) was the standard way of bootstrapping everything safely.

Is the new standard really just Javascript blocks at the bottom? Would love to
read more on the pros and cons, got any links?

~~~
mythz
Yes, Unfortunately this is a common misconception, and is why the Google
closure library intentionally leaves this feature out (so people don't use
it):

>>The short story is that we don't want to wait for DOMContentReady (or worse
the load event) since it leads to bad user experience. The UI is not
responsive until all the DOM has been loaded from the network. So the
preferred way is to use inline scripts as soon as possible.

>>By intentionally leaving out DOMContentReady wrappers we have been able to
prevent Google Apps to use on this anti pattern. \--
[https://groups.google.com/forum/#!topic/closure-library-
disc...](https://groups.google.com/forum/#!topic/closure-library-
discuss/G-7Ltdavy0E)

Also see:

[http://encosia.com/dont-let-jquerys-document-ready-slow-
you-...](http://encosia.com/dont-let-jquerys-document-ready-slow-you-down/)

[http://stackoverflow.com/questions/6026645/document-
readyfun...](http://stackoverflow.com/questions/6026645/document-
readyfunction-vs-script-at-the-bottom-of-page)

~~~
MRSA
Just for clarification,

I was looking through Mozilla Developer network. There is no documented
DOMContentReady event. There is a DOMContentLoaded [1] event which is target
at the document object. There is also a load [2] event fired at the window
object. This is fired when the document is completely loaded.

jQuery.ready will use DOMContentLoaded and load as a backup. [3]

It is common for jQuery developers to shove their whole code base into the
ready callback, which I imagine would slow a page down.

[1] <https://developer.mozilla.org/en/Gecko-Specific_DOM_Events>

[2] <https://developer.mozilla.org/en/DOM/window.onload>

[3] <https://github.com/jquery/jquery/blob/master/src/core.js>

------
fooyc
I would love to be able to require() jQuery features:

    
    
        require(['jQuery.ajax', 'jQuery.events'], function() {
            // code using ajax and events here
        });
    

Much easier than to manage script tags.

(hint: CommonJS / AMD)

~~~
xal
The problem with that is that plain script tags can be started to load once
the first TCP package of the HTML source code has been received. Your
javascript tag would only be executed after all that has been loaded and the
JS parser has been initialized. That can be up to 300ms to 500ms on slow and
mobile devices.

~~~
busticated
RequireJS has an optimizer which concats and minifies - problem solved!

------
pacomerh
Does anyone know of an app/tool to detect only the used parts of jQuery and
trim the unused?.

~~~
rkalla
Google closure compiler <http://code.google.com/closure/compiler/>

------
orthecreedence
I like that mootools lets you do this on your own. The builder lets you choose
exactly that you want. IMO the _only_ detriment to using Mootools over jQuery
is that less people use Moo, therefor less libraries are available.

------
moonboots
The google closure tools provides this modularity automatically. The compiler
removes unused functions in the google closure library.

~~~
akrymski
yes that should be the way to go, not providing a library in lots of parts
(i've yet to try it - how well does it work in practice?). compilers should
handle this for you (linking in only the required functions) instead of
distributing a library in chunks.

i would also like to see jQuery versions for different browsers (kinda like
Zepto for Webkit but with 100% of the APIs) - so I could compile using closure
against different libraries and serve just the right stuff to different user
agents.

it shouldn't be hard to add user-agent specific comments to jQuery so the
library could be used to produce user-agent specific versions. i think the
relative popularity of zepto shows that there's a need for that.

------
pistoriusp
ender.js is trying to solve this problem: <http://ender.no.de/>

~~~
aliem
I am a big fan of ender, you can build a framework out of smaller specialized
libraries, the Jeesh is very close to jQuery API, add reqwest and morpheus to
the stack and you have the missing ajax functionality (with a cleaner
interface) and a very nice and fast css tweener based upon MooTools.Tween.

------
dextorious
What he has done is nice, but hardly what he says he achieved.

90% good parts of jQuery? I don't think so. The omissions, like .css,
abstracted events, etc make this unfit for the majority of jQuery using
projects out there.

So it's more like "90% of what the author wants, YMMV" that "90% period".

