We are pleased to announce the arrival of YUI 3.10pr1 today. It is available via Yahoo! CDN, an archived download, or on npm. Our YUI Library staging website has also been updated to reflect the changes in this release. Please take note of the testing advisory below.
What's New in This Release?
We have been hard at work for a while now on some deep changes to YUI that dramatically improve performance. This preview release includes the results of this performance work. Also included in this release is the new
grunt-based build system that Dav Glass has been working on. Ryan Grove has included some improvements to
Y.Tree as well.
Attribute and Base Performance Improvements
On Chrome 25, compared to 3.8.1, we're seeing the following improvements (numbers in ops/sec):
|new MyBaseCore() [extends BaseCore]||51,980||140,016||3|
|MyBaseCore with 10 simple value attributes||20,535||45,541||2|
|MyBaseCore with 20 varied attributes (using perf. best practices)||11,699||19,153||2|
|MyBaseCore with 10 simple value attributes - set()||799,081||2,239,983||3|
|MyBaseCore with 10 simple value attributes - get()||2,527,214||10,424,878||4|
When combined with the work in CustomEvent and EventTarget (see below) , we're seeing:
BaseCore have seen dramatic performance improvements. These in turn improve
Base which many components depend upon, including custom components. One of the key performance changes introduced this PR is the caching of the static
ATTRS aggregation which occurs when you instantiate a
Base-based object. Before this change, YUI would re-aggregate
ATTRS for every instance created, resulting in about 1/3 of the time required for
Base instantiation. Now for the second instance onwards, YUI re-uses the cached aggregation improving performance substantially. Note however, as a result of this change, if you touch the
ATTRS collection on a 'class' directly there's the potential for breakage (this is a rare case). The cache won't know about your modifications if they come in after the first instance of the class is created. If you have such code in your custom components, it will need to use the new
modifyAttrs() static method. For more details see
CustomEvent and EventTarget Performance Improvements
On Chrome 25, compared to 3.8.1, we're seeing the following improvements:
|Low-level Publish (over regular publish)||-||1,404,890||5|
|Fire With Payload - 10 listeners||146,386||275,239||2|
|Fire - 10 listeners||176,905||347,636||2|
|Fire With Payload - 2 listeners||160,905||351,084||2|
|Fire - 2 listeners||209,820||671,328||3|
|Fire With Payload - 0 listeners||835,323||4,791,071||6|
|Fire - 0 listeners||839,048||5,139,582||6|
|EventTarget Construction + Publish(foo) + Fire(foo) - no listeners||104,124||306,288||3|
Another set of optimizations focus on
EventTarget, primarily for the 'no listeners' code path but also for custom events in general. The goal for these changes was to improve
new Base() times.
Base publishes and fires 2 events (
initalizedChange) during construction, which for the 80% case do not have listeners. The theme for this set of changes was to do the following:
- Try to fast-path common usage.
- Try to avoid the cost of the 20% features on the 80% path.
For more details, take a look at the HISTORY.md for
Algorithmic development and testing was done on Chrome for both sets of performance improvements above, but micro-optimizations for each specific browser were tested with jsperf across all browsers. The "x Change" that is presented in the data above was also tested across browsers and shown to exist beyond Chrome. YUI Developer Derek Gathright (@derek) posted some performance numbers using his new YUI Benchmark tool.
Ryan Grove (@yaypie) has added an extension to
Tree.Sortable which can be mixed into any Tree class to provide customizable sorting logic for nodes. He has also added
traverse() methods to assist with building extensions for
Y.Tree. For more details, check out the HISTORY.md entry.
Using grunt for Release Builds
Dav Glass (@davglass) has converted the build system over to using
grunt. Both dev and release builds are now done using this task runner, which has been a frequently requested feature for some time now.
grunt also integrates with
yogi to allow you to run both tests and builds. Dav solicited feedback from the community via our 'yui-contrib' mailing list and received responses that helped him make the best decision. This is a great example of a YUI developer making use of our Contributor Mailing List and Contributor Model in making changes for the better. If you want more details on how to use
grunt, please take a look at the new BUILD.md file included in this release. Also, if you want to develop for YUI we encourage you to join the mailing list to keep up with the latest. Check out the Contributor Model to learn how additions and improvements are integrated into the project.
You can find the complete list of changes for this release on GitHub. We had a total of 214 commits by 11 authors since YUI 3.9.1. Also note that Luke Smith (@ls_n) recently updated the user guide for Y.Promise so check that out as well.
Given that these performance improvements have a broad impact across many YUI components, we recommend that you take this preview release and try it out in a staging environment with your own applications. It is vital that we hear about any issues you may run into so that we can fix them in a timely manner before the full 3.10 release. Please take note of the potential change you may need to make to your custom code if you modify your
ATTRS class directly after the first instantiation. If you do run into an issue, please file a ticket.