<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0">
   <channel>
      <title>kylescholz.com :: blog</title>
      <link>http://www.kylescholz.com/blog/</link>
      <description></description>
      <language>en</language>
      <copyright>Copyright 2012</copyright>
      <lastBuildDate>Mon, 20 Dec 2010 13:20:52 -0500</lastBuildDate>
      <generator>http://www.sixapart.com/movabletype/?v=5.01</generator>
      <docs>http://blogs.law.harvard.edu/tech/rss</docs> 

      
      <item>
         <title>Performance Calendar</title>
         <description><![CDATA[<p>Each day this month, a web performance expert is posting an article on <a href="http://calendar.perfplanet.com/">Performance Calendar</a>. There is some really fantastic content here.</p>

<p>My contribution is <a href="http://calendar.perfplanet.com/2010/fast-ads-with-html5/">Faster Ads with HTML5</a>.</p>]]></description>
         <link>http://www.kylescholz.com/blog/2010/12/performance_calendar.html</link>
         <guid>http://www.kylescholz.com/blog/2010/12/performance_calendar.html</guid>
         <category>performance</category>
         <pubDate>Mon, 20 Dec 2010 13:20:52 -0500</pubDate>
      </item>
      
      <item>
         <title>HTML5 History is the Future</title>
         <description><![CDATA[<div style="margin-bottom:4px">
HTML5 exposes <a href="http://www.whatwg.org/specs/web-apps/current-work/multipage/history.html#history-0">a new API for web application developers to work with the history stack</a>:
</div>
<div style="background-color:#e0e8f0;border:1px solid #69c;padding:2px;">
<pre>interface History {
  ...
  void <b>pushState</b>(in any <b>data</b>, in DOMString <b>title</b>, in optional DOMString <b>url</b>);
  void <b>replaceState</b>(in any <b>data</b>, in DOMString <b>title</b>, in optional DOMString <b>url</b>);
};</pre>

<pre>interface HTMLBodyElement : HTMLElement {
  ...
  attribute Function </b>onpopstate</b>;
};</pre>
</div>

<p>
The new interface provides push/pop semantics that, until now, we've emulated using JavaScript libraries like <a href="http://code.google.com/p/reallysimplehistory/">Really Simple History</a>.
</p>

<p>
<b>Web Apps and History</b>
</p>

<p>
Web applications need to interact with the browser history to support bookmarkable and "back-buttonable" states. This is a pretty common feature of Ajaxy applications. For example, visit <a href="http://www.viewru.com/#Bonobo">http://www.viewru.com/#Bonobo</a> and browse or search for your favorite musician. The application uses an Ajaxy, single-window-context model to keep the music playing while you browse, but supports bookmarks and the back-button because users expect these features to work in their browser.
</p>

<p>
Prior to the HTML5 History additions, a solution to this problem involved these two parts:

<div style="background-color:#e0e8f0;border:1px solid #69c;padding:2px;">
<pre>// Store a representation of the state in the location hash
function setState(state) {
  window.location.hash = state;
}</pre>
<pre>// Detect a change to location.hash
var lastState;
window.setTimeout(function() {
  var state = window.location.hash;
  if (lastState != state) {
    lastState = state;
    handleState(state);
  }
}, 100);</pre>
</div>

<p>
The solution is less than ideal for several reasons:
</p>
<b>Sluggishness</b>
<ul style="margin-left: 16px;">
  <li>Executing a timeout function every 100ms won't make your app any faster.
  <li>100ms delay in responding to back button actions.
</ul>
<br>
<b>Browser compatibility</b>
<ul style="margin-left: 16px;">
  <li>The solution above doesn't work, for example, in IE 6-7, which won't add a history event on a hash change. Really Simple History gets around this by adding an iframe and issuing a call to your server for every state change. Webkit browsers present different challenges.
</ul>
<br>
<b>Not a stack</b>
<ul style="margin-left: 16px;">
  <li>Suppose your application transitions from A->B->C. Can it transition directly back to A?
</ul>
</p>

<p>
The HTML5 version looks like this:
<div style="background-color:#e0e8f0;border:1px solid #69c;padding:2px;">
<pre>// Push the state onto the history stack
function setState(state) {
  window.history.pushState(state, '');
}</pre>
<pre>// Respond to a popstate event.
window.onpopstate = function(e) {
  handleState(e.state);
};</pre>
</div>
<p>
Here, <b>state</b> may be a string representation of the current application state, but it can also be an object. Note that it will be deep-copied on each pushState() operation.
</p>

<p>
<b>Storing application state in the hash is a hack</b>
</p>

<p>
You may point out that the new hashchange event in HTML5 addresses concerns about sluggishness, but why use location.hash at all? Storing application state in the location hash presents some real problems and limitations. Here's a short list:

<ul style="margin-left: 16px;">
<li>Content isn't crawlable: Most crawlers do not execute JavaScript or traverse dynamic fragment ids. If you want users to find your site and content via Search Engines, this just won't do.
<li>Audible "click" in IE: For some reason, IE makes a sound every time you update the location. Imagine if your application updated the location on every mousemove event!
<li>HTTP-Referer is inaccurate or missing data: The fragment ID isn't exposed in the referrer.
<li>Handling bookmarks requires extra round trip: 
<ul style="margin-left: 16px;">
  <li>Fetch myApp.html
  <li>Parse myApp.html#myState (server can't see myState)
  <li>Fetch myState
</ul>
<li>Legacy (and non-JS) browsers effectively have different URI schemes and can't share bookmarks and links.
</ul>

<p>
<b>HTML5 History and URLs</b>
</p>
<p>
Perhaps the most interesting feature of the new pushState() and replaceState() interfaces is the optional <b>url</b> argument. For the first time, web developers are able to change the effective URL to represent a change in application state without navigating away from a window context. It's very powerful. The location bar, bookmark service, and HTTP-Referer all reflect the new URL. This feature addresses many of the issues I mentioned above:
<br>
<ul style="margin-left: 16px;">
<li>Content is crawlable: A developer may express all crawlable states of their application as valid URLs.
<li>HTTP-Referer is meaningful: The referrer can reflect the latest state of the application and show or hide any information to/from 3rd parties, at the developer's discretion.
<li>Bookmarks can be handled in a single fetch: Since application state can be expressed in a URL, it's possible to service a request for the application and state in one request/response.
<li>Can use a single URI scheme to cover new and old browsers: Since information is encoded in URLs instead of the location hash, modern and legacy users can share bookmarks and links.
<li>Audible "click" in IE? Okay, I don't know about this one, but it makes sense that programmatic operations on window.history would not have an audible side effect, right?
</ul>
</p>

<p>
<b>Availability and further reading</b>
</p>
<p>
You can take these new features for a spin in Firefox nightlies. For more info, see:
<ul style="margin-left: 16px;">
<li><a href="https://developer.mozilla.org/en/DOM/Manipulating_the_browser_history">Manipulating the Browser History @ Mozilla Developer Center</a>
<li><a href="http://www.whatwg.org/specs/web-apps/current-work/multipage/history.html">Session History and Navigation @ The HTML5 Spec
</ul>
</p>]]></description>
         <link>http://www.kylescholz.com/blog/2010/04/html5_history_is_the_future.html</link>
         <guid>http://www.kylescholz.com/blog/2010/04/html5_history_is_the_future.html</guid>
         <category>html5</category>
         <pubDate>Sun, 11 Apr 2010 13:59:10 -0500</pubDate>
      </item>
      
      <item>
         <title>It&apos;s pronounced &quot;vyoo-roo&quot;</title>
         <description><![CDATA[I added support for Firefox, Safari and Internet Explorer to <a href="http://www.viewru.com"><b>viewru</b></a>. It also now works on Chrome 3 in addition to Chrome 4. On non-Chrome browsers, the user experience has been simplified so that it's reasonably performant. So browse and listen away with your browser of choice.
<br><br>
Also, nearly everyone that's asked me about <a href="http://www.viewru.com"><b>viewru</b></a> doesn't know how to pronounce it. I pronounce it "vyoo-roo" (like "guru" with a "view").]]></description>
         <link>http://www.kylescholz.com/blog/2010/02/its_pronounced_viewroo_and_1.html</link>
         <guid>http://www.kylescholz.com/blog/2010/02/its_pronounced_viewroo_and_1.html</guid>
         <category>viewru</category>
         <pubDate>Thu, 04 Feb 2010 21:55:38 -0500</pubDate>
      </item>
      
      <item>
         <title>Progressive XMLHttpRequest</title>
         <description><![CDATA[Perhaps it's subtle, but the <a href="http://www.w3.org/TR/XMLHttpRequest">draft spec for XMLHttpRequest</a> calls for <a href="http://www.w3.org/TR/XMLHttpRequest/#the-responsetext-attribute">support for progressive response handling</a>:
<br><br>
<div style="background-color:#e0e8f0;border:1px solid #69c;padding:2px">
<b>4.7.6 The responseText attribute</b>
<br><br>
The responseText attribute must return the result of running these steps:
<br><br>
1. If the state is not LOADING or DONE return the empty string and terminate these steps.
<br><br>
2. Return the text response entity body.
</div>
<br>
To rephrase for my purposes, responseText should return the intermediate contents of the response when an XMLHttpRequest is interrogated during the LOADING state. It'll take a little work to handle these partial responses as valid script, but let's first address browser support. Firefox and Webkit browsers already support this behavior if you set the Content-Type header of your response correctly. IE8 throws an exception when responseText is accessed before readyState reaches COMPLETE.
<br><br>
I ran a modified version of the streaming response tests I used in my last post to verify progressive XHR handling. The server returns several chunks in 100ms intervals that include script that indicates how much of the response was received before it is first handled by the browser.

    <style>
      .result {
        min-width: 40px;
        text-align: right;
      }
    </style>
<br><br>
    <table border=1>
      <tr>
        <td>&nbsp;</td>
        <td colspan=3><b>Bytes Buffered</b></td>
      </tr>
      <tr>
        <td><b>Configuration</b></td>
        <td><b>Firefox 3.5</b></td>
        <td><b>Chrome 3.0</b></td>
        <td><b>IE 8</b></td>
      </tr>
      <tr>
        <td>
          <a href="/projects/progressive/testxhr.html?chunk=1">
          Tranfer-Encoding: chunked
          </a>
        </td>
        <td class="result">111</td>
        <td class="result">536</td>
        <td class="result">N/A</td>
      </tr>
      <tr>
        <td>
          <a href="/projects/progressive/testframe.html?chunk=1&contentType=htmlBasic">
          Content-Type: text/html<br>
          Tranfer-Encoding: chunked
          </a>
        </td>
        <td class="result">111</td>
        <td class="result">N/A</td>
        <td class="result">N/A</td>
      </tr>
      <tr>
        <td>
          <a href="/projects/progressive/testframe.html?chunk=1&contentType=plain">
          Content-Type: text/plain<br>
          Tranfer-Encoding: chunked<br>
          </a>
        </td>
        <td class="result">111</td>
        <td class="result">85</td>
        <td class="result">N/A</td>
      </tr>
      <tr>
        <td>
          <a href="/projects/progressive/testframe.html?chunk=1&contentType=jsBasic">
          Content-Type: application/x-javascript<br>
          Tranfer-Encoding: chunked
          </a>
        </td>
        <td class="result">111</td>
        <td class="result">111</td>
        <td class="result">N/A</td>
      </tr>
    </table>

<br>
For Webkit browsers, it's critical to specify a Content-Type of "text/plain" or "application/x-javascript" when returning script content to an XHR for progressive handling. Seems reasonable, but it's easy to neglect. In my testing, I didn't see any change in behavior in the presence of a "charset" param.
<br><br>
Note that <a href="http://msdn.microsoft.com/en-us/library/ms535874(VS.85).aspx">Microsoft's documentation for XMLHttpRequest</a> now refers the to draft specification. I'm hopeful that we'll be seeing support for progressive responses soon.
<br><br>
Now, since we'll be interpreting partial response content as executable script, we'll need to do something to ensure that each chunk we evaluate terminates on a complete expression. For this test, I added delimiters between valid blocks of source:
<br><br>
<div style="background-color:#e0e8f0;border:1px solid #69c;padding:2px;">
<pre style="margin:0;padding:0">window.aFunction();
// -- //
window.bFunction();
// -- //</pre>
</div>
<br>
Where //--// is the delimiter. When outputting using chunked transfer encoding, you might organize code so that a delimiter is present at the end of each chunk boundary. On each readyState change, if the state is LOADING or DONE, I call a function to read the new content, identify a safe place to trim it, and append it to a buffer.
<br><br>
<div style="background-color:#e0e8f0;border:1px solid #69c;padding:2px;">
<pre style="margin:0;padding:0">var index = 0;
var buffer = '';
var DELIMITER = '//--//';

function handlePartialResponse(request) {
  var i = request.responseText.lastIndexOf(DELIMITER);
  if (i > index) {
    i += DELIMITER.length;
    var newChunk = request.responseText.substr(index, (i - index));
    buffer += newChunk;
    index = i;
    flushBuffer();
  }
}</code>
</div>
<br>
Finally, we evaluate the contents of the buffer. It's not necessary to remove the delimiter, since it's a valid JavaScript comment.
<br><br>
<div style="background-color:#e0e8f0;border:1px solid #69c;padding:2px;">
<pre style="margin:0;padding:0">function flushBuffer() {
  window.eval(buffer);
  buffer = '';
}</pre>
</div>
<br>
What would you use this for? Consider this technique for the response channel in your next Comet app or any time you're able to deliver part of a script response while doing expensive server side work to produce the rest.]]></description>
         <link>http://www.kylescholz.com/blog/2010/01/progressive_xmlhttprequest_1.html</link>
         <guid>http://www.kylescholz.com/blog/2010/01/progressive_xmlhttprequest_1.html</guid>
         <category>performance</category>
         <pubDate>Tue, 05 Jan 2010 23:07:08 -0500</pubDate>
      </item>
      
      <item>
         <title>Performance Implications of &quot;charset&quot;.</title>
         <description><![CDATA[A while back, I wrote <a href="http://www.kylescholz.com/blog/2009/01/progressive_script_execution.html">a post documenting the progressive response handling behavior of different browsers</a>. I was specifically interested in how many bytes must be received or how much time must pass before a browser begins to parse content. My friend and colleague, Bryan McQuade (a co-author of <a href="http://code.google.com/speed/page-speed/">Google PageSpeed</a>), recently pointed out that character encoding detection is the source of buffering delay in response handling. Specifically, in the absence of a "charset" param in the Content-Type header, a browser may buffer a large quantity of content while looking for a &lt;meta&gt; tag declaring the content encoding.
<br><br>
I set up a new round of tests to identify the impact that content encoding declarations have on progressive response handling in different browsers. As in previous tests, the server returns several chunks, in 100ms intervals, each containing script that indicates how much of the response has been received.

    <style>
      .result {
        min-width: 40px;
        text-align: right;
      }
    </style>
<br><br>
    <table border=1>
      <tr>
        <td>&nbsp;</td>
        <td colspan=3><b>Bytes Buffered</b></td>
      </tr>
      <tr>
        <td><b>Configuration</b></td>
        <td><b>Firefox 3.5</b></td>
        <td><b>Chrome 3.0</b></td>
        <td><b>IE 8</b></td>
      </tr>
      <tr>
        <td>
          <a href="/projects/progressive/testframe.html?chunk=1">
          Tranfer-Encoding: chunked
          </a>
        </td>
        <td class="result">1134</td>
        <td class="result">1056</td>
        <td class="result">300</td>
      </tr>
      <tr>
        <td>
          <a href="/projects/progressive/testframe.html?chunk=1&contentType=htmlBasic">
          Content-Type: text/html<br>
          Tranfer-Encoding: chunked
          </a>
        </td>
        <td class="result">204</td>
        <td class="result">1056</td>
        <td class="result">341</td>
      </tr>
      <tr>
        <td>
          <a href="/projects/progressive/testframe.html?chunk=1&contentType=htmlBasic&metaCharset=1">
          Content-Type: text/html<br>
          Tranfer-Encoding: chunked<br>
          ...<br>
          &lt;meta http-equiv="Content-Type" content="text/html; charset=utf-8"&gt;
          </a>
        </td>
        <td class="result">166</td>
        <td class="result">204</td>
        <td class="result">218</td>
      </tr>
      <tr>
        <td>
          <a href="/projects/progressive/testframe.html?chunk=1&contentType=htmlCharset">
          Content-Type: text/html; charset=utf-8<br>
          Tranfer-Encoding: chunked
          </a>
        </td>
        <td class="result">204</td>
        <td class="result">280</td>
        <td class="result">300</td>
      </tr>
    </table>

<br>
Note that the test doesn't account for content in the document &lt;head&gt;, so the numbers for the &lt;meta&gt; configuration are artificially short by ~70b.
<br><br>
It's clear that for Chrome and Firefox, indicating the charset has a measurable impact on performance. Now, is it more desirable to declare the charset in the Content-Type header or a &lt;meta&gt; tag? Darin Fisher suggests that placing it in the response header is more performant: The charset impacts how the response is parsed, so when the browser encounters the &lt;meta&gt; tag, it must reprocess everything it's handled so far. If you're forced to use the &lt;meta&gt;, place it as near as possible to the top of the document to reduce the amount of throwaway work done by the browser.]]></description>
         <link>http://www.kylescholz.com/blog/2010/01/performance_implications_of_charset.html</link>
         <guid>http://www.kylescholz.com/blog/2010/01/performance_implications_of_charset.html</guid>
         <category>performance</category>
         <pubDate>Sun, 03 Jan 2010 23:03:45 -0500</pubDate>
      </item>
      
      <item>
         <title>ViewRu: An Interactive Music Browser and Player</title>
         <description><![CDATA[For a long time, I've been excited about the idea of creating browsable interfaces that convey information about the similarity of items using their relative proximity (who wouldn't be excited about that?). In 2006, I created <a href="http://www.jsviz.org">JSViz</a> and a whole bunch of demos to explore the space. A major point of frustration was JavaScript and DOM performance, especially while scaling the number of items or edges in a graph. JavaScript->DOM interaction has greatly improved in the latest generation of browsers, so a few weeks ago I set out to turn an old demo into a useful application:
<br><br>
<img src="http://www.kylescholz.com/img/screenshots/viewru.png">
<br>
<a href="http://www.viewru.com/">ViewRu</a> is an interactive music browser and player. It uses artist relationships from open APIs and music streams from YouTube to provide a single interface for exploring and listening to music. Presently, it takes advantage of browser features and performance only available in <a href="http://dev.chromium.org/getting-involved/dev-channel">Google Chrome 4</a>.
<br><br>
Check it out at <a href="http://www.viewru.com/">www.viewru.com</a> and let me know what you think.]]></description>
         <link>http://www.kylescholz.com/blog/2010/01/viewru_an_interactive_music_br.html</link>
         <guid>http://www.kylescholz.com/blog/2010/01/viewru_an_interactive_music_br.html</guid>
         <category>viewru</category>
         <pubDate>Sun, 03 Jan 2010 21:46:41 -0500</pubDate>
      </item>
      
      <item>
         <title>Firefox Paint Events Update</title>
         <description><![CDATA[<p>I <a href=http://www.kylescholz.com/blog/2008/11/digging_into_paint_events_in_f_1.html>recently posted</a> about a Firefox / Firebug extension for digging into Firefox's new MozAfterPaint events. I just posted my <a href=https://addons.mozilla.org/en-US/firefox/addon/9620>second update to the Firefox Addons site</a>. In addition to highlighting the clip area of paint events, this update adds screenshots so it's possible to see the page state at the time of an event:</p>

<img src="http://www.kylescholz.com/images/firebugpaintevents.0.1.4.png">

<p>Note that capturing the screen for each paint event adds significant overhead, so it's wise to leave this feature disabled when not actively using it. Other handy features include the ability to view event details on the Firebug DOM tab:</p>

<img src="http://www.kylescholz.com/images/fbpaint.domview.png">

<p>And dig into the complete events details:</p>

<img src="http://www.kylescholz.com/images/fbpaint.domview2.png">

<p>The "image" attribute above is a data URL of the screen capture. I imagine this will have some other practical uses. Some other event types are logged for reference, and clicking on any event will reset the base time to the time of that event, to make it easier to see how actions relate to paints:</p>

<img src="http://www.kylescholz.com/images/fbpaint.clicks.png">

<p>To use this extension, you will need <a href="http://ftp.mozilla.org/pub/mozilla.org/firefox/nightly/latest-trunk/">a 3.1+ Firefox pre-release</a> and <a href="http://getfirebug.com/">Firebug 1.3</a>. You can pick up the latest version of <a href="https://addons.mozilla.org/en-US/firefox/addon/9620">Firebug Paint Events here</a>.</p>]]></description>
         <link>http://www.kylescholz.com/blog/2009/01/firefox_paint_events_update.html</link>
         <guid>http://www.kylescholz.com/blog/2009/01/firefox_paint_events_update.html</guid>
         <category>performance</category>
         <pubDate>Sun, 18 Jan 2009 17:16:55 -0500</pubDate>
      </item>
      
      <item>
         <title>Progressive Script Execution</title>
         <description><![CDATA[<p>
Recently I've been speaking to colleagues about progressive script execution, and it seems like a little-explored topic, so I'm sharing what I know. By progressive execution, I mean that scripts begin executing in the browser before the containing resource has been wholly received.
</p>

<b>Dealing with Dynamic Response Sizes</b>

<p>
One of the first hurdles people encounter with progressive response handling is that most HTTP responses have a Content-Length in the response header. This means that the size of the response must be known before any data is sent over the network. For static resources, this isn't such a problem because the entire response is available at once, but for dynamic resources, this means that the entire response must be determined before any part of it can be written to the network.
</p>

<p>
Imagine your web application performs an expensive operation that takes up to half a second to complete. If it takes another 500ms on average to transfer all of your HTML and CSS to users, it will take a full second to load your page. If you could transfer the bulk of that data while waiting for the operation to complete, then tack on the final bits, you might cut your response time in half.
</p>

<p>
This can be accomplished with effective use of <a href="http://tools.ietf.org/html/rfc2616#section-3.6.1">HTTP Chunking ("Transfer-Encoding: chunked")</a>. Chunked responses don't require a Content-Length header, so it's possible to do work after bytes have been sent to the network. While each chunk in the response will contain a header, indicating the size of the chunk, any number of chunks can be appended until a terminating delimiter is provided.
</p>

<b>Executing Scripts Progressively</b>

<p>
In the hypothetical example above, we were dealing with HTML and CSS, but suppose instead that we have a large amount of script to deliver with each response. Take note, external &lt;script>s and XHRs are not progressively interpreted*. Other methods, such as inline &lt;script>s and iframes are required. Also note, individual script blocks are not evaluated until the full contents have been received and parsed by the client. So it's advisable to split scripts into small sections, each wrapped in it's own block:
</p>

<pre>&lt;script>
...
&lt;/script>
&lt;script>
...
&lt;/script>
&lt;script>
...
&lt;/script>
</pre>

<p>
The ideal size of these script blocks will vary by application and the connection characteristics of your users. You might consider typical packet size (about 1460b) and the behavior of <a href=http://en.wikipedia.org/wiki/Slow-start>TCP Slow Start</a> as a guide.
</p>

<b>Browser Support and Caveats</b>

<p>
To explore progressive execution,  I implemented a simple HTTP server in Perl (<a href="http://www.kylescholz.com/projects/progressive/threshhold.txt">View Source for Example #1</a>), that writes several small chunks (real HTTP chunks) that look like:
</p>

<pre>&lt;script>document.write('10: 737b: ' + n() + 'ms&lt;br>')&lt;/script></pre>

<p>
The fields indicate the chunk number, number of bytes written to the buffer, and a function call that outputs the milliseconds since the last script execution. I was surprised by two findings:
<br>1) Webkit browsers don't support progressive execution at all. Ouch!
<br>2) Other browsers don't begin parsing and executing until a byte threshhold has been reached, and this threshhold varies from browser-to-browser. In IE7, my output looks like:
</p>

<pre>0: 127b: 0ms
1: 188b: 0ms
2: 249b: 0ms
3: 310b: 969ms
4: 371b: 1015ms
...</pre>

<p>And in Firefox 3:</p>

<pre>0: 127b: 2ms
1: 188b: 0ms
2: 249b: 1ms
3: 310b: 1ms
4: 371b: 1ms
5: 432b: 1ms
6: 493b: 0ms
7: 554b: 1ms
8: 615b: 1ms
9: 676b: 1ms
10: 737b: 1ms
11: 799b: 0ms
12: 861b: 1ms
13: 923b: 1ms
14: 985b: 1ms
15: 1047b: 876ms
16: 1110b: 1021ms
...</pre>

<p>
This shows that the threshhold in IE7 is about 200-300b, and in Firefox3, about 1kb. While scripts won't execute until the threshhold is reached, it may still be advantageous to deliver content smaller than the threshhold early to take advantage of idle network time. Though you might consider padding your response if it enables you to provide early feedback to users.
</p>

<p>
It's not necessary to create a new chunk for each script block to achieve progressive execution, but you must be able to determine the size of each chunk before it can be written. It's also important to flush the network buffer at logical intervals (at the close of each script block, for example).
</p>

<p>
A modified version of the demo HTTP server (<a href="http://www.kylescholz.com/projects/progressive/progressive_chunks.txt">View Source for Example #2</a>) demonstrates that progressive execution can be achieved within chunks. For this example, each chunk contains 5 script blocks. I precomputed the total size of each chunk, and appended the output in 1 second intervals. Output for a run in IE follows:
</p>

<pre>0: 127b: 0ms
1: 188b: 0ms
2: 249b: 0ms
3: 310b: 1016ms
4: 371b: 922ms
...</pre>

<p>And for Firefox 3:</p>

<pre>0: 127b: 1ms
1: 188b: 1ms
2: 249b: 1ms
3: 310b: 1ms
4: 371b: 1ms
5: 432b: 1ms
6: 493b: 1ms
7: 554b: 1ms
8: 615b: 2ms
9: 676b: 1ms
10: 737b: 1ms
11: 799b: 1ms
12: 861b: 1ms
13: 923b: 1ms
14: 985b: 1ms
15: 1047b: 1136ms
16: 1110b: 817ms
...</pre>

<p>
That concludes my overview. I'm interested in questions and ideas for further exploration.
</p>

<p>
* XHR implementations that notify when bytes are received could theoretically be evaluated progressively, but to evaluate JavaScript safely in such a context would require a fair amount of infrastructure. Also, I haven't seen this done yet, but I'd love a pointer if anyone has.
</p>]]></description>
         <link>http://www.kylescholz.com/blog/2009/01/progressive_script_execution.html</link>
         <guid>http://www.kylescholz.com/blog/2009/01/progressive_script_execution.html</guid>
         <category>performance</category>
         <pubDate>Tue, 06 Jan 2009 01:59:39 -0500</pubDate>
      </item>
      
      <item>
         <title>Digging into Paint Events in Firebug</title>
         <description><![CDATA[<p>
I'm always on the prowl for new tools and signals for analyzing and improving frontend performance. When <a href="https://developer.mozilla.org/web-tech/2008/10/13/mozafterpaint/">Mozilla announced the new MozAfterPaint event</a> in <a href="http://ftp.mozilla.org/pub/mozilla.org/firefox/nightly/latest-trunk/">Firefox nightlies</a>, I got excited and got to work.
</p>

<p>
<a href="http://ejohn.org/blog/browser-paint-events/">John Resig posted a bookmarklet</a> for viewing MozAfterPaint events, but I'm primarily interested in paint events that fire before onload(), so a bookmarklet isn't ideal. I stayed up late last night and created a simple Firebug extension for capturing and viewing these events. To use:
</p>

<p>
<ul style="margin-left:16px">
<li> <a href="http://ftp.mozilla.org/pub/mozilla.org/firefox/nightly/latest-trunk/">Get a recent nightly build of Firefox</a>
<li> <a href="http://getfirebug.com/releases/index.html#beta">Ensure you're using Firebug 1.3</a>
<li> <a href="https://addons.mozilla.org/en-US/firefox/addon/9620">Install the extension</a>
</ul>
</p>
<br>
<center><img src="http://www.kylescholz.com/img/screenshots/firebugpaintevents.png"></center>

<p>
After restarting, you'll have a "Paints" tab in Firebug. Mouse over the events to see the clip areas highlighted. 
</p>

<p>
Thanks to Mozilla for making MozAfterPaint available! I've only started digging in and I'll try to follow up with some observations. In the meantime, post away, I'm interested in yours.
</p>]]></description>
         <link>http://www.kylescholz.com/blog/2008/11/digging_into_paint_events_in_f_1.html</link>
         <guid>http://www.kylescholz.com/blog/2008/11/digging_into_paint_events_in_f_1.html</guid>
         <category>performance</category>
         <pubDate>Sun, 16 Nov 2008 17:18:15 -0500</pubDate>
      </item>
      
      <item>
         <title>A Quick svg2vml Example: Gradients</title>
         <description><![CDATA[<p>A couple weeks ago I mentioned the first release of svg2vml, a lightweight library that enables cross platform, JavaScript-driven vector graphics. Here's a quick example where I use svg2vml to create Digg style gradient buttons:</p>

<p><i>If you're reading from a feed reader that doesn't embed iframes, you'll need to <a href="http://www.kylescholz.com/blog/2007/03/svg2vml_example_digg_b.html">click through</a> to see the example.</i></p>

<iframe src="/projects/svg2vml/0.1.1/digg-button.html" style="width:480px;height:230px;"></iframe>

<p>Check out the frame source for full details. Notice that the button itself is an HTML DIV and that we use CSS and HTML elements to define and position our text. So it's possible to mix HTML and vector graphics as you see fit.</p>

<p>We're just scratching the surface. svg2vml can do all kinds of cool stuff. Have fun!</p>]]></description>
         <link>http://www.kylescholz.com/blog/2007/03/svg2vml_example_digg_b.html</link>
         <guid>http://www.kylescholz.com/blog/2007/03/svg2vml_example_digg_b.html</guid>
         <category>svg2vml</category>
         <pubDate>Mon, 26 Mar 2007 15:37:29 -0500</pubDate>
      </item>
      
      <item>
         <title>svg2vml Project Announced</title>
         <description><![CDATA[<p>Today on the <a href="http://www.jsviz.org/blog">JSViz Blog</a>, Lorien announced svg2vml, a thin translation layer that enables VML capable browsers (Internet Explorer) to display a subset of SVG without any new code. </p>

<p>Checkout the <a href="http://www.jsviz.org/blog/2007/03/svg2vml.html">full post</a> for details.</p>]]></description>
         <link>http://www.kylescholz.com/blog/2007/03/svg2vml_project_announced.html</link>
         <guid>http://www.kylescholz.com/blog/2007/03/svg2vml_project_announced.html</guid>
         <category>svg2vml</category>
         <pubDate>Sat, 10 Mar 2007 23:44:21 -0500</pubDate>
      </item>
      
      <item>
         <title>Gone Googlin&apos;</title>
         <description><![CDATA[<p>Hey friends, sorry I haven't been posting or responding to any of your e-mails lately! I assure you I've got an excuse. I'm moving from my place in Rochester, New York to California next week to start a new job with Google. I'll let you know more when I can, but please hang tight in the meantime.</p>

<p>I've got plenty of JSViz news to share and I'll be posting as time and wifi permit over the next week.</p>]]></description>
         <link>http://www.kylescholz.com/blog/2007/02/gone_googlin.html</link>
         <guid>http://www.kylescholz.com/blog/2007/02/gone_googlin.html</guid>
         <category>google</category>
         <pubDate>Fri, 09 Feb 2007 16:15:53 -0500</pubDate>
      </item>
      
      <item>
         <title>Tutorial: Building a Snowflake Graph from XML</title>
         <description><![CDATA[<p><i>I just posted this new tutorial on <a href="http://www.jsviz.org/blog/2007/01/tutorial_building_a_snowflake.html">jsviz.org... </a></i></p>

<p>
JSViz 0.3.3 includes a few examples to help you get started. In this tutorial, I'm going to go over one of them. We'll create a Snowflake Graph from the contents of an XML file. You can find the example source, with comments based on this tutorial in the <a href="http://www.jsviz.org/wiki/index.php/Download">0.3.3 Distribution</a>.
</p>

<a href="http://jsviz.org/files/jsviz/0.3.3/examples/XMLLoader_Snowflake.html">Here's the final product</a>

<p>
<b>1) Start with a new HTML file</b>
</p>

<p>Add appropriate JSViz imports and an empty "init()" function body:
</p>

<p>
<a href="http://www.jsviz.org/blog/2007/01/tutorial_building_a_snowflake.html">Continue reading this post at jsviz.org...</a></p>]]></description>
         <link>http://www.kylescholz.com/blog/2007/01/tutorial_building_a_snowflake.html</link>
         <guid>http://www.kylescholz.com/blog/2007/01/tutorial_building_a_snowflake.html</guid>
         <category>jsviz</category>
         <pubDate>Mon, 22 Jan 2007 20:27:27 -0500</pubDate>
      </item>
      
      <item>
         <title>JSViz 0.3.3 Released</title>
         <description><![CDATA[<p>The <a href="http://www.jsviz.org/blog/">jsviz.org</a> website is now available but I'll be cross-posting big news here to keep subscribers and search traffic informed:</p>

<p><b>JSViz 0.3.3 is now available</b>. This release includes two major features:</p>

<p><b>Snowflake Model</b> is an updated implementation of the "Tree Model" offered in JSViz 0.2. This is a geometric model, offering superior speed to Force Directed layouts, but only capable of representing hierarchical data (sorry, no circuits).</p>

<p><a href="http://jsviz.org/files/jsviz/0.3.3/examples/XMLLoader_Snowflake.html">An Example Snowflake Graph</a></p>

<p><b>Layouts</b> offer a simplified interface to the core JSViz libraries. New projects can now be created with minimal code and simple configuration. Additional examples, using Layouts:</p>

<p><a href="http://jsviz.org/files/jsviz/0.3.3/examples/XMLLoader_ForceDirected.html">An Example Force Directed Graph with Data Loader</a><br />
<a href="http://jsviz.org/files/jsviz/0.3.3/examples/RandomCircuit_ForceDirected.html">An Example Force Directed Graph with Randomly Generated Data</a></p>

<p>You can download the full source as a single ZIP archive or browse individual files on the <a href="http://jsviz.org/wiki/index.php/Download">Download page</a></p>

<p>I'll follow up with tutorials shortly.</p>]]></description>
         <link>http://www.kylescholz.com/blog/2007/01/jsviz_033_released.html</link>
         <guid>http://www.kylescholz.com/blog/2007/01/jsviz_033_released.html</guid>
         <category>jsviz</category>
         <pubDate>Sun, 21 Jan 2007 23:31:38 -0500</pubDate>
      </item>
      
      <item>
         <title>More Music Mashing</title>
         <description><![CDATA[<p>I've received a lots of great comments and e-mails about the music recommendations demo I posted a week or so ago. But a number of you mentioned that the recommendations were a little funny. Questions and observations so far:</p>

<ul style="margin-left:14px">
<li>Theivery Corporation is the center of the universe! Every album ever released is 3 or fewer hops away from a Theivery Corporation album.</li>
<li>Why is every album I search for related to Beck? or Moby? or <b>Neil Young</b>? Though I'll point out, the man has been in almost every band that's ever released an album. Seriously, that album by the <b>Back Street Boys and Young</b> is one of my favorites!</li>
<li>How is this tool useful if the only related albums to my search are by the same artist?</li>
</ul>

<p>Right. So ... There's a lesson here:<p>

<p style="margin-left:20px"><i>There's always a little bit of <b>"magic"</b> in a mashup.</i></p>

<p>The music recommendations demo gets album relationships from Amazon.com's E-commerce API. Similarity is based on buying patterns, which apparently lead to some unexpected or disappointing results. So I decided to try out an alternative.</p>

<p>I worked up a quick mashup using the <a href="http://www.audioscrobbler.net/data/webservices/">Audioscrobbler (Last.fm) API</a> for Artist-to-Artist recommendations. Audioscrobbler uses the listening patterns of it's users to determine relationships. Unfortunately, the images served up with this API aren't especially useful in identifying artists, <a href="http://static.last.fm/proposedimages/thumbnail/6/2003/13061.jpg">especially when scaled down</a>. So this demo is currently text-only. If you're interested, the demo could be extended to grab an album image from Amazon.com. I tried this and bailed out quickly because it added a lot of latency to the addition of new nodes, but you may be able to cut this down using an image cache.</p>

<center>
<p><a href="http://www.kylescholz.com/projects/speaking/tae2006/music.fm/#Kim%20Hiorthoy"><img src="/img/screenshots/music.fm.png" border="0"></a></p>
</center>

<p><a href="http://www.kylescholz.com/projects/speaking/tae2006/music.fm/#Kim%20Hiorthoy">So give it a try.</a></p>

<p>Oh, one more thing! These demos don't work so well in ie7. This isn't an issue with the JSViz 0.3.1 API. I'll fix the demos when I have some spare time. Thanks for all the feedback. It's useful in driving this project.</p>]]></description>
         <link>http://www.kylescholz.com/blog/2006/11/more_music_mashing.html</link>
         <guid>http://www.kylescholz.com/blog/2006/11/more_music_mashing.html</guid>
         <category>visualization</category>
         <pubDate>Sun, 05 Nov 2006 23:11:35 -0500</pubDate>
      </item>
      
   </channel>
</rss>
