Going Simple with JavaScript

I was making a change to a page that needed to pull from a remote API and make changes to various parts of the page. Sounds like the time to pull out jQuery and Ajax, doesn't it? Instead, I just used old fashioned JavaScript. Actually, I used new fashioned JavaScript.

Browsers haven't stood still in the advent of libraries and frameworks. As a result, we can take advantage of those features when we need to bake in a little extra.

Some JSONP

The first step was to get the JSONP call executing. This is generally straightforward: embed a script tag into the page. The script will run a function that you've defined on your page.

var scr = document.createElement('script'); scr.src = 'http://openexchangerates.org/latest.json?callback=formatCurrency'; document.body.appendChild(scr);

When the script runs, it'll pass the data into the formatCurrency function. Excellent.

Once the data is in the function, I needed to grab all the elements of a particular type and make changes based on those.

querySelectorAll

The querySelectorAll method will grab all elements that match a particular selector—similar to jQuery. It's limited to selectors that the browser understands, which is definitely less than what jQuery can do. Sometimes a chisel will do in place of a sledgehammer.

The querySelectorAll method works in IE8 and up and all of the other popular browsers, too. I also wrapped my entire block of code to check if the browser supports this method before doing anything.

if (document.querySelectorAll) { function formatCurrency (data) { var els = document.querySelectorAll('.price'); /* do stuff with the elements */ } var scr = document.createElement('script'); scr.src = 'http://openexchangerates.org/latest.json?callback=formatCurrency'; document.body.appendChild(scr); }

As you can see in the example, all I'm looking for is every element that has a class of price. I could've used getElementsByClassName but that's not supported in IE8, whereas querySelectorAll is. So far, so good.

After that, it was just a matter of getting an attribute, making some changes and then re-inserting it into the DOM using innerHTML. Easy peasy.

Progressive Enhancement

But what of users who don't support this new fandangled functionality? It'll be the same as those who don't support JavaScript. In my case, it meant that users will see just Canadian pricing instead of converting it into their local currency.

Here's the final script in its entirety.

if (document.querySelectorAll) { var currencyLookup = { EUR:'€', USD:'US$', CAD:'CDN$' } function formatCurrency (data) { // format germany price var els = document.querySelectorAll('.price'); for (var i=0; i<els.length; i++) { var price = parseInt(els[i].innerHTML.replace(/[^0-9]*/,'')); var curr = els[i].getAttribute('data-currency'); var newPrice = price / data.rates.CAD * data.rates[curr]; els[i].innerHTML = '<small>' + currencyLookup[curr] + '</small>' + Math.round(newPrice); } } var scr = document.createElement('script'); scr.src = 'http://openexchangerates.org/latest.json?callback=formatCurrency'; document.body.appendChild(scr); }

That's a total of 628 bytes. No JavaScript libraries or frameworks required. That could be minified to 469 bytes. A far cry from the 91,000 bytes needed just to get jQuery on the page.

Take it easy

"Just use jQuery" might be the go-to phrase but, thankfully, you don't always need that much code to solve a simple problem. Pages are getting bigger and bigger. It's nice to know that we don't always have to use large resources to accomplish a small goal.