A while ago I wrote a pretty simple ASP.NET control to show the last song you listened to (via Last.fm) on your own website. You can see mine at the top of this page, just underneath the header.
Some of you will have noticed a performance hit on the page load time by looking at the code. I accessed the Last.fm AudioScrobbler XML service with a single line of code:
XDocument recentTracksXml =
XDocument.Load(
"http://ws.audioscrobbler.com/1.0/user/televisionfoot/recenttracks.xml");
The problem with this is that I don't know how long it will take to go and fetch this XML file (it's not a service I have control of). Showing the last song I listened to is hardly critical to my website, and I don't want to increase the page load time if the service is slow. The problem, of course, is that I'm not calling this service asynchronously.
The ideal scenario would be to render the page first (as quickly as possible), and then go and fetch the XML asynchronously from the client side while the reader is looking at my website. There is a very easy way to do this: enter AJAX with jQuery.
Firstly, I wrote a web service that will fetch me the last track I listened to via Last.fm's AudioScrobbler service. I made the web service return a chunk of HTML, nice and easy to insert directly into the DOM. The web service method looks something like this:
[WebMethod]
public string GetMostRecentTrack()
{
XDocument mostRecentTracksXml =
XDocument.Load(
"http://ws.audioscrobbler.com/1.0/user/televisionfoot/recenttracks.xml");
XElement mostRecentTrackXml = mostRecentTracksXml.Root.Elements("track").First();
return string.Format("<p>Last listened to {0} by {1}</p>",
(string) mostRecentTrackXml.Element("name"),
(string) mostRecentTrackXml.Element("artist"));
}
The key thing is that I call this service using jQuery's $(document).ready event - which of course fires after the page has finished loading. This way, the user gets the page as quick as possible, and I fetch the additional data (the latest track I listened to) asynchronously and display it when it's ready. This speeds up the page loading time, and improves the overall user experience. The jQuery looks similar to the following:
<script type="text/javascript">
$(document).ready(function() {
$.ajax({
type: "POST",
url: 'LastFmService.asmx/GetMostRecentTrack',
data: "{}",
contentType: "application/json; charset=utf-8",
dataType: "json",
success: function(msg) {
$("div.MostRecentTrackContainer").append(msg.d);
},
error: function(msg) {
$("div.MostRecentTrackContainer").append('Error - try again later.');
}
});
});
</script>
To really add the finishing touches to this bit of code, I actually do a few other things that I don't show here in this blog post:
- I cache the most recent track data for 10 minutes once it has been fetched. I only bother to do the client side AJAX call if I don't already have cached data available on the server.
- If I do perform the AJAX client-side call, initially I show an AJAX style animated gif, and then switch to the most recent track text once it is available.
- When I switch from the animated loading gif to the recent track text, I use jQuery's fadeOut() and fadeIn() animation effects, to really add the finishing touches!
This is what it looks like if a user hits my page and nothing is cached:

The end resuult of all of this is giving the user a bit of up-to-date information about the author of this site with no performance hit on page loading times and to top it off some pretty awesome client side animation effects.