In The Beginning, Node Created os.cpus().length Workers

Schnorr_von_Carolsfeld_Bibel_in_Bildern_1860_006

As reported in the previous two posts, we are boldly going where many have already gone before – into the brave new world of Node.js development. Node has this wonderful aura that makes you feel unique even though the fact that you can find answers to your Node.js questions in the first two pages of Google search results should tell you something. This reminds me of Stuff White People Like, where the question ‘Why do white people love Apple products so much” is answered thusly:

Apple products tell the world you are creative and unique. They are an exclusive product line only used by every white college student, designer, writer, English teacher, and hipster on the planet.

And so it is with Node.js, where I fear that if I hesitate too much, somebody else will write an app in Node.js and totally deploy it to production, beating me to it.

Jesting aside, Node.js definitely has the ‘new shoes’ feel compared to stuff that was around much longer. Now that we graduated from ‘Hello, World’ and want to do some serious work in it, there is a list of best practices we need to quickly absorb. The topic of this post is fitting the square peg of Node.js single-threaded nature into the multi-core hole.

For many skeptics, the fact that Node.js is single-threaded is a non-starter. Any crusty Java server can seamlessly spread to all the cores on the machine, making Node look primitive in comparison. In reality, this is not so clear-cut – it all depends on how I/O intensive your code is. If it is mostly I/O bound, those extra cores will not help you that much, while non-blocking nature of Node.js will be a great advantage. However, if your code needs to do a little bit of sequential work (and even a mostly I/O bound code has a bit of blocking work here and there), you will definitely benefit from doubling up. There is also that pesky problem of uncaught exceptions –  they can terminate your server process. How do you address these problems? As always, it depends.

A simple use case (and one that multi-threading server proponents like to use as a Node.js anti-pattern) is a Node app installed on a multi-core machine (i.e. all machines these days). In a naive implementation, the app will use only one core for all the incoming requests, under-utilizing the hardware. In theory, a Java or a RoR server app will scale better by spreading over all the CPUs.

Of course, this being year 5 of Node.js existence, using all the cores is entirely possible using the core ‘cluster’ module (pun not intended). Starting from the example from two posts ago, all we need to do is bring in the ‘cluster’ module and fork the workers:

var cluster = require('cluster');

if (cluster.isMaster) {
   var numCPUs = require('os').cpus().length;
   //Fork the workers, one per CPU
   for (var i=0; i< numCPUs; i++) {
      cluster.fork();
   }
   cluster.on('exit', function(deadWorker, code, signal) {
      // The worker is dead. He's a stiff, bereft of life,
      // he rests in peace.
      // He's pushing up the daisies. He expired and went
      // to meet his maker.
      // He's bleedin' demised. This worker is no more.
      // He's an ex-worker.

      // Oh, look, a shiny new one.
      // Norwegian Blue - beautiful plumage.
      var worker = cluster.fork();

      var newPID = worker.process.pid;
      var oldPID = deadWorker.process.pid;

      console.log('worker '+oldPID+' died.');
      console.log('worker '+newPID+' born.');
   });
}
else {
   //The normal part of our app.

The code above does two things – it forks the workers (one per CPU core), and it replaces a dead worker with a spiffy new one. This illustrates an ethos of disposability as described in 12factors. An app that can quickly be started and stopped, can also be replaced if it crashes without a hitch. Of course, you can analyze logs and try to figure out why a worker crashed, but you can do it on our own time, while the app continues to handle requests.

It can help to modify the server creation loop by printing out the process ID (‘process’ is a global variable implicitly defined – no need to require a module for it):

http.createServer(app).listen(app.get('port'), function() {
   console.log('Express server '+process.pid+
                ' listening on port ' + app.get('port'));
});

The sweet thing is that even though we are using multiple processes, they are all bound to the same port (3000 in this case). This is done by the virtue of the master process being the only one actually bound to that port, and a bit of white Node magic.

We can now modify our controller to pass in the PID to simple page and render it using Dust:

exports.simple = function(req, res) {
  res.render('simple', { title: 'Simple',
                         active: 'simple',
                         pid: process.pid });
};

This line in simple.dust file will render the process ID on the page:


This page is served by server pid={pid}.

When I try this code on my quad-core ThinkPad laptop running Windows 7, I get 8 workers:

Express server 7668 listening on port 3000
Express server 8428 listening on port 3000
Express server 8580 listening on port 3000
Express server 9764 listening on port 3000
Express server 7284 listening on port 3000
Express server 5412 listening on port 3000
Express server 6304 listening on port 3000
Express server 8316 listening on port 3000

If you reload the browser fast enough when rendering the page, you can see different process IDs reported on the page.

This sounds easy enough, as most things in Node.js do. But as usual, real life is a tad messier. After testing the clustering on various machines and platforms, the Node.js team noticed that some machines tend to favor only a couple of workers from the entire pool. It is a sad fact of life that for college assignments, couple of nerds end up doing all the work while the slackers party. But few of us want to tolerate such behavior when it comes to responding to our Web traffic.

As a result, starting from the upcoming Node version 0.12, workers will be assigned in a ’round-robin’ fashion. This policy will be the default on most machines (although you can defeat it by adding this line before creating workers):

    // Set this before calling other cluster functions.
    cluster.schedulingPolicy = cluster.SCHED_NONE;

You can read more about it in this StrongLoop blog post.

An interesting twist to clustering is when you deploy this app to the Cloud, using IaaS such as SoftLayer, Amazon EC2 or anything based on VMware. Since you can provision VMs with a desired number of virtual cores, you have two dimensions to scale your Node application:

  1. You can ramp up the number of virtual cores allocated for your app. Your code as described above will stretch to create more workers and take advantage of this increase, but all the child processes will still be using shared RAM and virtual file system. If a rogue worker fills up the file system writing logs like mad, it will spoil the party for all. This approach is good if you have some CPU bottlenecks in your app.
  2. You can add more VMs, fully isolating your app instances. This approach will give you more RAM and disk space. For JVM-based apps, this would definitely matter because JVMs are RAM-intensive. However, Node apps are much more frugal when it comes to resources, so you may not need as many full VMs for Node.

Between the two approaches, ramping up cores is definitely the cheaper option, and should be attempted first – it may be all you need. Of course, if you deploy your app to a PaaS like CloudFoundry or Heroku, all bets are off. It is possible that the code I have listed above is not even needed if you intend to host your app on a PaaS, because the platform will provide this behaviour out of the box. However, in some configurations this code will still be useful.

Example: Heroku gives you a single CPU dyno (virtualized unit of server power) with 512MB RAM for free. If you stay on one instance but pick a 2-core dyno with 1GB RAM (I know, still peanuts), that will cost you $34.50 at the time of writing (don’t quote me on the numbers, check them directly at the Heroku pricing page). Using two single core dynos will cost you the same. Between the two, JVM would probably benefit from the 2x dyno (with more RAM), while a single threaded Node app would benefit from two single core instances. However, our code gives you the freedom to use one 2X dyno and still use both cores. I don’t know if availability is the responsibility of the PaaS or yourself – drop me a line if you know the details.

It goes without saying that workers are separate processes, sharing nothing (SN). In reality, the workers will probably share storage via the attached resource, and storage itself can be clustered (or sharded) for horizontal scaling. It is debatable if sharing storage (even as attached resources) disqualifies this architecture from being called ‘SN’, but ignoring storage for now, your worker should be written to not cache anything in memory that cannot be easily recreated from a data source outside the worker itself. This includes auth or session data – you should rely on authentication schemes where the client sends you some kind of a token you can exchange for the user data with an external authentication authority. This makes your worker not unlike Dory from Pixar’s ‘Finding Nemo’, suffering from short term memory loss and introducing itself for each request. The flip side is that a new worker spawned after a worker death can be ready for duty, missing nothing from the previous interactions with the client.

In a sense, using clustering from the start builds character – you can never leave clustering as an afterthought, as something you will add later when your site becomes wildly popular and you need to scale. You may discover that you are caching too much in memory and need to devise schemes to share that information between nodes. It is better to get used to SN mindset before you start writing clever code that will bite you later.

Of course, this being Node, there is always more than one way to skin any particular cat. There is a history of clustering with Node, and also keeping Node alive (an uncaught exception can terminate your process, which is a bummer if only one process is serving all your traffic). In the olden days (i.e. couple of years ago), people had good experience with forever. It is simple and comes with a friendly license (MIT). Note though that forever only keeps your app alive, it is not clustering it. More recently, PM2 emerged as a more sophisticated solution, adding clustering and monitoring to the mix. Unfortunately, PM2 comes with an AGPL license, which makes it much harder to ship it with your commercial product (which means little if you are just having fun, but actually matters if you are a company of any size with actual paying customers installing your product on premise). Of course, if your whole business is hosted and you are not shipping anything to customers, you should be fine.

What I like about ‘cluster’ module is that it is part of the Node.js core library. We will likely add our own monitoring or look for ‘add-on’ monitoring that plays nicely with this module, rather than use a complete replacement like PM2. Regardless of what we do about monitoring, the clustering boilerplate will be a normal part of all our Node.js apps from now on.

© Dejan Glozic, 2014

Book Review: RESS Essentials

6944OT_RESS Essentials

I have decided to start reviewing books as part of my blog activity with mixed emotions. Our industry is so fast moving, so ephemeral that books seem to fight a losing battle on being relevant the day they are published, never mind 6 months or a year down the road. Books on actual concrete products are very often little more than the missing manuals (so much so that O’Reilly actually has a ‘Missing Manuals‘ series, with a ‘The book that should have been in the box’ tagline – burn!). Just check the new titles – ‘Windows 8.1’, ‘HTML5’, ‘iPad’!!

Somewhat better fate is reserved for books that attempt to describe an approach or technique rather than any particular platform, language or library. Sound principles tend to outlive the actual building blocks used to implement them. The book I am covering in this review falls into that category, since it attempts to address a fairly new approach to wrestling with the explosion of Web clients.

The book’s title is ‘RESS Essentials’ by Joanna Krenz-Kurowska and Jerzy Kurowski and is brought to us by Packt Publishing. I already wrote about RESS in RESS to the Rescue. In a nutshell, responsive Web design (or RWD) is used to make a Web application adapt to the various aspects of the client, and reformat the experience to best fit each client in question (be it desktop, tablet or phone). RESS (or REsponsive design Server Side) goes further by involving the server. The rationale is that CSS can hide or reformat content depending on the client, but everything is still sent by the server, whether it will be needed or not. RESS attempts to address the performance side of the responsive design by choosing what to send before any formatting decisions are made on the client.

Even in Internet years, RESS is a young technique, and a very good illustration of that is that the authors felt the need to devote most of chapter 1 to controversies surrounding RESS. To put it simply, not everybody is convinced that RESS is a good idea. Nevertheless, enough people are (including the godfather of RESS Luke Wroblewski, incidentally another Pole – in a bit of Polish trivia, my photographer told me that his last name means ‘sparrow-like’). As such, the rest of the book assumes you have been sufficiently convinced RESS is a good and useful thing and you want to get on with it.

Chapter 1 also brought one of the unexpected insights into RESS and responsive design, where it can actually go to the other side of the client spectrum. When it comes to RWD, most of the focus is on how your site reacts to non-desktop clients. However, for eons the desktop design assumed certain maximum width and happily ignored the side bands, making browser window maximization futile. On high quality, large monitors these side bands seems like a waste of real estate (compared to how desktop applications or games use it). RESS and responsive Web design can unlock full potential of your high end monitor – no reason why we cannot add rules to keep adding more content if you maximize your browser on a 27” or 30” monitor.

In chapter 2, authors pay homage to the client side, by diving into the real world example using Gridpak for the responsive grid and Twitter’s Bootstrap for everything else.

Real action starts in chapter 3, where focus is moved to the server – the key value add of the RESS technique. In order to determine what to send to the client, server-side device detection is used. Two most popular solutions discussed in the chapter are WURFL and DeviceAtlas. There is a problem – these services are not available for free, or if they are, the free (or even cheap Cloud-based) version is not a viable option for anything but a test site. For completeness, authors cover some Open Source alternatives such as YABFDL (also known as Dave Olsen’s Detector) – more modest in its database but still usable and free with permissive license (with coverage that keeps up with new devices through the use of the modernizr.js library).

Chapter 4 puts server side detection into action. Different markups for different clients (to optimize for ability, support for modern features and JavaScript), different media sizes based on screen width, and manual selection of page versions. This chapter mostly deals with the first of the three goals, with plenty of code snippets using both WURFL and Dave Olsen’s Detector.

Chapter 5 moves on to dealing with image resolution on the server. Images comprise a large portion of the overall site payload and sending images that are too large or of unnecessarily high resolution is costly both performance-wise, but also by eating into the monthly bandwidth allowance for mobile users. The RESS solution for handling image sizes and resolution is in line with the overall approach and has some interesting properties compared to the known alternatives.

As said, all this effort around sending the right-sized images to the client is at least partially driven by performance considerations. In chapter 6, authors note that client screen size is not the only parameter to take into account – connection bandwidth is as important. Unfortunately, as of today there are no media queries for connection quality and bandwidth that could be used to tailor image size and compression to use. In their absence, authors offer a number of techniques to optimize images or reduce the need to use them in the first place.

One thing I really liked in this chapter was a graph showing that with the reduction of screen size (and with RESS solution for images enabled), the size of CSS and JavaScript files started to overtake images, to the point where images were only 1/3 of the CSS/JavaScript files for iPhone portrait resolutions (320px). This was a good reminder that RESS needs to be combined with other good practices if performance was a concern. I particularly liked a tidbit that the average webpage reached 1585 KB on September 15, 2013. That’s a lot of KBs to send to any client, particularly mobile phones, and underlines the need for techniques such as RESS to improve Web performance.

Changing gears, chapter 7 switched back to the client and focused on using and extending jQuery and Bootstrap to make your site responsive when dealing with elements such as tables and carousels. jQuery has essentially become the equivalent of gravity for JavaScript libraries (i.e. you cannot avoid it and must play nice with it), and Bootstrap is insanely popular in its third incarnation. While not necessarily limited to RESS (the code in this chapter could be easily used in a client-only RWD solution), we should not forget that RESS is a combination of server and client side techniques for responsive design, and the examples in this chapter are definitely useful for Web developers that seek responsive design solutions.

I am a bit puzzled with chapter 8, which introduces REST and combines it with RWD. It is not strictly RESS in that it simply uses Ajax to call REST services. There is nothing wrong with what is proposed in this chapter, but REST is another kind of ‘gravity’ for many teams including mine, and tossing it here on the pile with RESS and RWD seems odd, particularly because it involves PHP in code examples. Since this was the last chapter in the book, I was left wanting for a chapter that is more fit for wrapping it all up and reinforcing the key messages of the book (an epilogue, as it were).

In the end, where does it left me, the reader and the reviewer? I would say that RESS Essentials is part of the new breed of ‘mini-books’, considering its size (120 pages including index). It is definitely not the first of its kind – Responsive Web Design by Ethan Marcotte is 143 pages, and Mobile First by Luke Wroblewski is 123 pages. This class of books covers areas and topics that are too complex to be covered in one blog post or article but perhaps not as complex to require a book that can double as a weapon and will consume years of author’s life. The format definitely allows hot topics to be covered in a time frame that at least gives them a fighting chance of having some decent use before the inevitable progress renders them obsolete.

I think that the authors did a good job covering the ground on the topic of RESS and I definitely learned a lot by reading it. The book is part of the ‘Community Experience Distilled’ series, and it definitely fits the description, since the authors provided a number of examples and code snippets that look like something they arrived at through personal experience while working on real world projects. Whether RESS itself has a staying power is left to be seen. I am concerned about the limited choices when it comes to server side agent detection (at least in the Open Source world), so Dave Olsen’s Detector effort should be commended.

When it comes to code snippets, I was more interested in general concepts than the server side code examples because they were universally in PHP. There is nothing wrong with PHP but I would prefer examples in Java, or even better, in JavaScript using Node.js. Using Java or Node.js would work better with the final chapter about combining REST with RESS.

As far as the format and language is concerned, I have two minor nits to pick. While the book is generally well written, Joanna’s and Jerzy’s Polish background occasionally creeps into their sentence structure. Not being a native speaker myself, I cannot quite put my finger on why I was able to notice, I just felt that way as I was reading. Another mild nit is that the PDF version of the eBook results in too small a font, and when I tap to zoom in, the text is single-spaced, making it less than perfect for reading on iPads. On the flip side, single spacing made for faster vertical scrolling. YMMV if you use a different reader or format.

That’s it for my first review – next on the docket is Smashing Magazine Book #4 – now that’s a book you can use for self defense if need be!

© Dejan Glozic, 2014

Beam My Model Up, Scotty!

star-trek-transporter

I know, I know. Scotty is from the original series, and the picture above is from TNG. Unlike Leonard from The Big Bang Theory, I prefer TNG over the original, and also Picard over Kirk. Please refrain from hate mail.

Much of both real and virtual ink has been spilled over Star Trek transporter technology and quirks. Who can forget the episode when Scotty has preserved himself as a transporter pattern in an endless loop only to be found and freed 70 years later by the TNG crew (see, there’s your Scotty-TNG link). But this article is about honouring all the hours I spent on various Star Trek instalments by applying the transporter principles to Web development.

As the Web development collective mind matures, a consensus is forming that spaghetti are great on your dining table but bad for your code. MVC design pattern on the server is just accepted as gravity, and several JavaScript frameworks are claiming it is necessary on the client as well. But is it always?

Here is case in point. Our team recently rebuilt a dashboard – a relatively complex peace of interactive technology. This is our third attempt at it (third time’s the charm, right)? Armed with all the experience of the previous two versions, plus our general desire to pull back from the extreme Ajax, we were confident this would be it. Why build a dashboard? Yes, I know, everybody and his uncle has one, and there are perfectly good all singing, all dancing commercial ones to be had. Here is a counter-question: why do you have a kitchen in your house when you can eat at perfectly good restaurants? Everybody has a dashboard because it is much more convenient to have your own (Google Analytics has one, WordPress I am writing this on has one). They can be simple because they don’t need to cater to all the possible scenarios, and much more tightly integrated. And not to mention cheaper (like eating at home vs. eating out). But I digress.

In the previous version, we sent a lot of JavaScript to the client, and after transporting and parsing it, JavaScript turned around and used XHR to fetch the model from the server as JSON. Then we wired up the model and the view and every time users made a change, we would update the model to keep it in sync. Backbone.js or Angular.js would have come in handy for this, only they didn’t exist when we wrote that code. Plus we hate frameworks.

In this version we wanted the dashboard page to arrive mostly assembled from the server. That part was clear. But we wanted to avoid the MV* complexity and performance consequences if possible. Plus it is really hard to even apply the usual data binding with dashboards because you cannot just wire the template with the model and let the framework do its magic. In a dashboard, the template itself is editable – users can drag and drop widgets around, delete them and add new ones. Essentially both the template and the data are built up from the model. This is not your grandmother’s MVC, that’s for sure.

Then we remembered Star Trek transporters and figured – why don’t we disperse the model and embed the model shards into the DOM as we are building the initial HTML on the server? We were waiting to hit a brick wall at some point, but it didn’t happen – this is an actually viable option. Here is why this approach (I will call it M/V) works for us like a charm:

  1. Obviously it is easy to do on the server – when we are building the initial response, embedding model shards into the HTML is trivial using HTML5 custom data properties (those attributes that start with ‘data-‘).
  2. The model arrives ready to use on the client – no need for an extra request to fetch the model after the fact. OK, Backbone.js has a way of bootstrapping models so that they arrive as payload with the initial response. However, that approach qualifies as CrazyHacks™ at best, and you save nothing payload-wise – the sum of the shards equals one whole model.
  3. When the part of the DOM needs to change due to the user interaction, it is easy to keep the associated ‘data-*’ properties in sync.
  4. When moving entire DOM branches (say, when dragging widgets between columns or changing layouts), model shards stay with their DOM elements – this is a real winner in our use case.
  5. We use DOM custom event bubbling to notify about the change – one listener at the top of the DOM branch is all that is needed to keep track of the sharded model’s dirty state. This helps us to stay lean because there is no need for JavaScript pub/sub implementations that increase size. It is laughably trivial to fire and listen to these events using jQuery, and they are fast, being implemented natively by the browser. Bootstrap uses the same approach.
  6. When the time comes to save, we traverse the DOM, collect the shards and assemble them again into a transient JavaScript object, then send it as JSON to the server via XHR. We use PUT/POST when we have the entire model, but more often the not, the view only renders a fraction of it (lazy loading), so we use PATCH instead.

This approach bought us some unreal savings in performance and size. Right now, we brought down total JavaScript from ~245kB to ~70KB minified gzipped (this includes jQuery, Require.js and Bootstrap). The best part is that this JavaScript loads asynchronously, after the initial content has already been displayed. The page is not only objectively fast, it is subjectively even faster because the initial content (what Twitter team calls ‘time to first tweet’) is sent in the first response.

As it is often the case in life, this approach may not work for everybody. A pattern where true MVC really shines is when you have multiple views listening to the same model. Changing the model updates all the views simultaneously, without the need for the pub/sub hell. But if you have exactly one view and one model, using M/V becomes a real option.

I can hear the collective gasp of architects in the audience. There are many things you can say about M/V, but architecturally pure it is not. But here is the problem. Speed and page size should be a valid architectural concern too. In fact, if you want your Web app to be usable on mobile devices, it is practically the only concern that matters. Nobody is going to wait your architecturally pure pig of a page to load while waiting for coffee – life is too short for 1MB+ web pages, pure or not.

Say No to layer cake, embrace small, live long and prosper!

© Dejan Glozic, 2013

Swimming Against The Tide

True story: I visited Ember.js web site and saw three required hipster artifacts: ironic mustaches, cute animals and Ray-Ban Wayfarer glasses (on a cute animal). A tweet was in order and within minutes, it was favored by a competing client side framework by Google (Angular). Who would have guessed client side frameworks are so catty? I can almost picture Angular News guy clicking the ‘Favorite’ button and yelling ‘Oh, Burn!!’ And it wasn’t even a burn, I actually like Ember web site – it is so …. cute.

The reason I visited Ember (and Angular, and Backbone, and Knockout) was to figure out what was going on. There is this scene in a 2002 movie Gangs Of New York where Leonardo DiCaprio leads his gang of Dead Rabbits to fight the competing gang (the Natives), and he has to wade through a river of people running in the opposite direction to avoid cannons fired by the Navy from the harbor. Leonardo and his opponent, a pre-Lincoln Daniel Day-Lewis were so enthralled in their epic fight that they missed the wider context of the New York Draft Riots happening around them. Am I like Leo (minus the looks, fame and fortune), completely missing the wider historic context around me?

Not long ago, I posted a repentant manifesto of a recovered AJAX addict. I swore off the hard stuff and pledged to only consume client-side script in moderation. The good people from Twitter and 37Signals all went through the same trials and tribulations and adopted similar approach (or I adopted theirs). Most recently, Thomas Fuchs, the author of Zepto.js expressed a similar change of heart based on his experiences in getting the fledgling product Charm off the ground. Against that backdrop, the noise of client-side MVC frameworks mentioned above is reaching deafening levels, with all the people apparently not caring about the problems that burned us so much. So what gives?

There are currently two major camps in the Web development right now, and they mostly differ in the role they allocate for the server side. The server side guys (e.g. Twitter, Basecamp, Thomas, yours truly) have been burned by heavy JavaScript clients and want to render initial page on the server, subsequently using PJAX and modest amounts of JavaScript for delicious interactivity and crowd pleasers. Meanwhile, a large population of developers still want to develop one page Web apps that require the script to take over from the browser for the long periods of time, relegating the server to the role of a REST service provider. I don’t want to repeat myself here (kindly read my previous article) but the issues of JavaScript size, parsing time, performance, memory leaks, browser history, SEO didn’t go away – they still exist. Nevertheless, judging by the interest in Angular, Backbone, Ember and other client side JavaScript frameworks, a lot of people think the tradeoffs are worth it.

To be correct, there is a third camp populated mostly by LinkedIn engineering team. They are in a category for themselves because they are definitely not a one page app, yet they do use Dust.js for client side rendering. But they also use a whole mess of in-house libraries for binding pages to services, assembling them, delaying rendering when below the fold, etc. You can read it on their blog – suffice to say that similar to Facebook’s Big Pipe, the chances you can repeat their architecture in your project are fairly slim, so I don’t think their camp is of practical value to this discussion.

Mind you, nobody is arguing the return to the dark ages of Web 1.0. There is no discussion whether JavaScript is needed, only whether all the action is on the client or there is a more balanced division of labor with the server.

I thought long and hard (that is, couple of days tops) about the rise of JavaScript MVC frameworks. So far, this is what I came up with:

  1. Over the last few years, many people have written a lot of crappy, unmaintainable, messy jumble of JavaScript. They now realize the value of architecture, structure and good engineering (client or server).
  2. A lot of people realize that some really smart people writing modern JavaScript frameworks will probably do a better job providing this structure then themselves.
  3. Many projects are simply not large enough to hit the general client side scripting turning point. This puts them in a sweet spot for client side MVC – large enough to be a mess and benefit from structure, not large enough to be a real pig that makes desktop browsers sweat and mobile browsers kill your script execution due to consuming too much RAM.
  4. These projects are also not easily partitioned into smaller contexts that can be loaded as separate Web pages. As a result, they rely on MVC JavaScript frameworks to perform data binding, partitioning, routing and other management.
  5. Modern templating engines such as Mustache or Handlebars can run both on the client and on the server, opening up the option of rendering the initial page server side.
  6. JavaScript community is following the same path that Web 1.0 server side MVC went through: the raise of opinionated and prescriptive MVC frameworks that try to box you into good practices and increase your productivity at the price of control and freedom.
  7. The people using these frameworks don’t really have performance as their first priority.
  8. The people using these frameworks plan to write a separate or native mobile client.

There could be truth in this, or I could be way off base. Either way, my team has no intention of changing course. To begin with, we are allergic to loss of control these frameworks demand – we subscribe to the camp that frameworks are bad. More importantly, we like how snappy our pages are now and want to keep them that way. We intend to keep an eye on the client MVC frameworks and maybe one day we will hit a use case where client side data binding and templates will prove useful (say, if we attempt something like Gmail or Google Docs or Google Calendar). If that happens, we will limit it to that particular use case, instead of going all in.

Meanwhile, @scottjehl perfectly describes my current state of mind thusly:

output-HTML

© Dejan Glozic, 2013

RESS to the Rescue

It seems that every couple of years we feel a collective urge to give a technique a catchy acronym in order to speed up conversation about UI design. Last couple of years, we grew accustomed to throwing around the term Responsive Design casually, probably because it rolls off the tongue easier then “we need to make the UI, like, re-jiggle itself on each thingy”. Although I like saying ‘re-jiggle’. Re-swizzle is my close second.

As we were working on the tech preview of the Jazz Platform Home app, we naturally wanted it to behave on phones and tablets. And it did. The header in particular is a breathing, living thing, going through a number of metamorphoses until a desktop caterpillar turns into a mobile butterfly:

res-all

It all works very well, but a (butter)fly in the ointment is that we need to send the markup for both the caterpillar and the butterfly on each request. We do CSS media query transformations to make them do what we want, but we are clearly suboptimal here. I am sure that with some CSS shenanigans we could pull it off with one set of HTML tags, but at some point it just becomes too hard and error-prone. Clearly it is one thing to make the desktop/tablet header drop elements and adjust with screen size, and another to switch to a completely new element (off-screen navigation) while keeping the former rotting in the display:none hell.

This is not the only example where we had to use this technique. The next example has the section switcher in the Project Details page go from vertical set of tabs to a horizontal icon bar:

proj-res

Again, both markups are sent to the client, and switched in and out by CSS as needed. This may seem minor but in a more complex page you may end up sending too much stuff on all clients. We need to involve the server into this using some kind of a hybrid technique.

As JJG before, Luke Wroblewski has not actually invented this technique but simply put a name on it. RESS stands for REsponsive design + Server Side and first appeared in Luke’s article in 2011. The technique calls for involving the server in responsive design so that only what is needed is sent to the client. It also goes by the name ‘adaptive design’. The server is not meant to replace but rather complement responsive design. You can view the server as a more coarse-grained player in this duo, sending ‘mobile’ or ‘desktop’ stuff to the client, while the responsive design takes care of adapting to the device in more steps or decision points. It needs to because what does it mean ‘mobile’ today anyway? There is a continuum of screen sizes now, from phones to phablets to mini-tablets to regular tables to small laptop screens to desktops – what is ‘mobile’ in that context?

It seems like RESS would help us in our two examples above by allowing us to not send the desktop header to the phone and off-screen navigation to the desktop. However, the server has limited means to perform device detection. At the very bottom, there is HTTP header ‘user-agent’. Agent sniffing is a never-ending task because of new devices that keep coming online. There is a lot of virtual ink spilled on the algorithms that will correctly detect what you are running. This is error-prone activity relying on pattern matching against lists that normally go stale if not updated constantly. There were attempts to subcontract this job, but many are either stack-specific or fee-based (such as WURFL or detectmobilebrowsers.mobi), or a combination of all these approaches. I don’t see how any of these solutions make sense to most of the web sites that want to go the RESS route. Simply judging by the number of available solutions, you can see that this is not a solved problem, analogous to the number of hair loss treatments.

Another approach we can use (or combine with user agent detection) is to send the viewport size to the server in a cookie. This arms the server with the additional means to make correct decision because while, say, iPad is reported as ‘mobile’, it has enough resolution to be sent a full desktop version of the page, and viewport size would reveal that. The problem with this technique is that your site needs to be visited at least once to give JavaScript a chance to set the cookie, which means that the optimization only kicks in on repeat visits.

Considering the imprecise nature of device detection, you should consider RESS a one-two approach – server tries its best to detect the device and send the appropriate content, then responsive design on the client kicks in. A prudent approach would be to err on the safe side on the server and give up on device detection at the first sign of trouble, letting the client do its thing (when, say, user-agent has never been seen before or cookies are disabled preventing viewport size transmission). With this approach, we should ensure that client-side responsive design works well on its own, and consider server-side an optimization, a bonus feature that kicks in for the most straightforward cases (i.e. most well known phones, tablets) and/or on repeat visits.

By using the vision analogy, the most you would expect your server to do in a RESS-enabled site is to tell you that the vehicle on the road is a car and not a truck, and that it is black(ish). As long as you don’t expect it to tell you that it is a 2012 BMW i3 with leather seats and technology package, you will be OK.

© Dejan Glozic, 2013

Feed Your Web UI Without Choking It

Today’s topic is penguins, how they feed their young and how to apply that to Web development. Now watch my improbable feat of connecting these two topics. Come for the penguins, stay for the Web UI!

I am a father and as all parents know, part of the job description when your kids reach certain age includes suffering through many an animated movie (I am looking at you, Hoodwinked!). On one occasion though, I actually enjoyed the movie, and it happened to be Happy Feet. Those of you who watched it know that young Mumble is fed by his father Memphis eating a big fish, then regurgitating the half-digested food into Mumble’s beak, like so:

Antarctic adelie penguins (js) 21

This is not from the movie but I don’t want to wrestle with Warner Bros over the copyright for the images.

As I watched the scene, I started thinking about what I like to call ‘naive Ajax’. I already gave Ajax its own blog post so no need to repeat myself here. Suffice to say is that when Ajax was young, making an XHR call to fetch some data was fairly straightforward and powerful. At that time, there were readily available services of the monster variety (Big Bad Services or BBS©). These services often returned horrible XML, and in the ‘all you can eat’ amounts. Developers didn’t want to bother with writing the services themselves, preferring to stay on the client writing JavaScript. They just called the Big Bad Service, suffered through the XML, threw most of it away and built their DOM nodes out of the useful parts.

I think you are starting to see the improbable analogy here: the unprocessed, big data service is like feeding the little Mumbo raw fish – too much for its little beak. Let me count the ways why that is suboptimal:

  1. Big services normally serve verbose XML with tons of namespace information. If you are lucky and the service supports gzip, it may not be a big problem (XML is insanely compressible), but if it does not, a lot of the bytes are sent down the wire unnecessarily.
  2. XML is not the optimal format to process on the client. You can let the browser parse it into a DOM tree, and traverse the DOM. However, that means that your JavaScript code needs to be larger because it contains nontrivial amount of logic just to traverse the data and sift it out.
  3. The data may not be fully digestible (see what I did here) – you may need to derive some of it from what you have received, or make more than one XHR request and sort out the joins in-browser.
  4. Very often you get way more than you need, which is wasteful because you waited and wasted the bandwidth and traversed a big DOM only to throw it away.

It would be foolish to assume that this is the thing of the past and that modern JSON services are much better and do not suffer from this problem. You may as easily choke your Web UI with a ton of JSON data – the only difference is that you will get huge JavaScript objects instead of an XML DOM tree. The accent is on ‘impedance mismatch’, not on the exchange format.

What is the ‘right way’ then? Use what I call ‘Happy Feet Services’. Write your own service on the presentation server (the one serving the rest of the Web app resources) in a service language of your choice. Make that service call the Big Bad Services, process the response, correlate the data, toss the unused parts away – it will do a much better job on the server. Once you finally bring the data set down to a super tasty little nugget, send it to the browser as gzipped JSON. It will arrive quickly because it is small, it will be turned into a JavaScript object by the browser, and your client JavaScript does not need to be very large because the data set is readily usable – no processing required.

If you feel lucky (punk!), you can go one step further and make your Happy Feet Service even more useful: make it dual-purpose using content negotiation. If you ask for “application/json”, return JSON as described. If you ask for “text/html”, send out the same data already rendered and ready to go as HTML markup – all you need to do is pipe it into a DIV using innerHTML property. You will have dynamic Ajax app with very little JavaScript.

For this realization alone, I would say I got my money’s worth. The only thing I learned from Hoodwinked! is not to give coffee to a squirrel. I knew that already.

© Dejan Glozic, 2013

Pulling Back from Extreme AJAX

I always thought that Jesse-James Garret had an awesome name. It is up there with Megan Foxx and that episode of The Simpsons when Homer briefly changed his name to Max Power. How many of us have a name that prompted John Lee Hooker to compare his level of badness to us? Granted, the Jesse in question (Jesse Woodson James) was too busy robbing banks and leading gangs to be a Chief Creative Officer of anything, but the power of the name is undeniable.

JJG, of course, is the guy who coined the phrase ‘Asynchronous JavaScript and XML’ (AJAX). It put a name on the technique that turned JavaScript from a quirky scripting language for coding web site menus to a powerhouse, delivering amazingly interactive Web applications to your browser. If we wanted to be sticklers, the majority of people now use JSON, not the original XML for the X part of the technique, but would we like JJG as much if he called the technique AJAJ? I don’t think so.

AJAX works roughly like this: in the dark ages of Web 1.0, whenever you wanted to react to user input in a significant way, you had to pass the data to the server and get a new rendition of the page. A lot of effort went into hiding this fact – session state was kept, parameters were passed, resources were cached to speed up page redraw, but it was still flashy and awkward – nothing like the creamy smoothness of desktop application UX. Then Microsoft needed some hooks, first in Outlook, then in IE, to make asynchronous requests to the server without the need to reload the page. The feature remained relatively obscure until Google made a splash with Gmail and Google Maps in a way that was browser-agnostic. Then JJG called the whole thing AJAX. You can read it all on Wikipedia.

Fascination with AJAX was long lasting. I guess we were so used to the limitations of Web 1.0 and what browsers were supposed and not supposed to do that for the longest time we had to pinch ourselves when looking at so much interactivity without page reload. I remember watching Google Wave demo at Google IO conference in 2009 and the presenter kept saying “and remember, there are no plug-ins here, this is all done with JavaScript in a regular browser”. Four years after the phrase was born!

There is a self-deprecating American joke that claims that “it is not done until it is overdone”. I live in Canada but when it comes to AJAX we are equally culpable. In our implementation of AJAX in the Rational Jazz Project, we served AJAX for every meal. We had AJAX hors d’oeuvres followed by AJAX soup, AJAX BBQ and then triple-fudge AJAX for desert. No wonder we now suffer from AJAX heartburn. Will somebody pass the Zantac?

See, the problem is that it is easy to overdo AJAX by forgetting that we are not writing desktop applications. We still need to have the healthy respect for the Web and remember that it is a fundamentally different environment than your desktop. Forgetting this fundamental tenet usually leads to a three-stage illness:

  1. Obesity. As in real-world diet, AJAX calories add up, and before you know it, your web page is ready for the Fat Farm. I have seen a page that needed to load more than 1MB of JavaScript (gzipped) before anything useful was shown.
  2. Separation Anxiety. Since it takes so much effort to load a page and make it useful, fat AJAX apps fear browser separation and do everything in their power to avoid a refresh. It can degenerate all the way to ‘one page apps’ that stay around like a bad penny, all the while faking ‘pages’ with DIVs that are hidden and shown via CSS.
  3. The God Complex. The final stage of this malady is that since we are not leaving the browser, and since any nontrivial app needs to manage a number of objects and resources, we come up with elaborate schemes for switching between them, lying to the browser about our navigation history, and finally fully re-implementing a good number of features that browsers already do, only much better. Pop-up menus, history management, tab management – we essentially ask the browser to load our app (painfully) and then go take a nap for a couple of hours – we will take over.

Should we lay this at the doorstep of Microsoft, Google and JJG? It would be easy but it would not help us. Nobody asked us to lose control of ourselves and amass such JavaScript love handles and triple chins. No AJAX Hello World snippet has 1MB of JavaScript. AJAX is wonderful when used in moderation. Large, slow to load AJAX pages are a problem even on the desktop, and are a complete non-starters in the increasingly important mobile world. Even if you ignore the problem of moving huge JavaScript payload over mobile networks, JavaScript engines in smartphone browsers have much smaller room to play and can cripple or downright terminate your app. By the way, this kind of defeats the purpose of so called ‘hybrid apps’ where you install a web app as native using PhoneGap/Cordova shim. That only eliminates the transport part but all the issues with running JavaScript on the phone remain. I am not saying that hybrid apps don’t have their place, only that they are not exempt from JavaScript weight watching.

How does a page wake up one morning and realize nothing in the wardrobe closet fits any more? Writing 1MB worth of JavaScript takes a lot of effort – it does not happen overnight. One of the reasons are desktop and server side developers writing client code but still somehow wanting to think they are in their comfort zone. A lot of Java developers think JavaScript is Java’s silly little brother. They devise reality-distortion force fields that allow them to pretend they are still writing in strongly typed languages (I am looking at you, GWT). Entire Java libraries are converted to JavaScript without a lot of scrutiny. I am strongly against it. As I always say, si fueris Romanae, Romano vivito more. If your code will end up running in a browser as JavaScript, why don’t you write in JavaScript and take advantage of all unique language features, instead of losing things in translation and generating suboptimal code?

But it is not (just) suboptimal code generation that causes the code bloat. It is the whole mindset. Proper strongly typed OO languages encourage creating elaborate class hierarchies and overbuilding your code by using every pattern from the Gang Of Four book at least once. That way the porky code lies. Coding for the web requires acute awareness that every line of code counts and rewards brevity and leanness. As it turns out, you pay for each additional line of JavaScript three times:

  1. More code takes longer to send to the browser over the moody and unpredictable networks
  2. More code takes longer for the browser to parse it before being able to use it
  3. More code will take more time to run in the browser (I know that JavaScript VMs have gotten better lately, but in the real life I still need to perform an occasional act of scriptocide – JavaScript performance problem didn’t entirely go away)

And what would an article by a middle-aged architect be without an obligatory “kids these days” lament? Many of the newly minted developers start out on the client side. They become very good at coaxing the browser into doing wonderful things, and this affinity naturally degenerates into doing ALL your work on the client. The server essentially becomes a resource delivery layer, sending JSON to JavaScript frameworks that are doing all of the interesting work in-browser. This is wrong. The proper way of looking at your application is that it consists of the following parts:

  1. Storage (Model)
  2. Server side logic (Controller)
  3. Server side rendering engine (View)
  4. Network transport layer
  5. Browser that renders HTML using CSS and reacting to user interactions via JavaScript

Notice how JavaScript is one of 7 aspects you need to care about. If you look at some implementations these days, you would think all the other aspects only exist to deliver or otherwise support JavaScript. It is the equivalent of a body builder that focused all his training on his right arm biceps. A balanced approach would yield much better results.

OK, Dejan, quit pontificating. What do we do to avoid dangers of irresponsible AJAXing in the future?

Well, armed with all this hard won experience, we have decided to take the opportunity of the new Jazz Platform project to wipe the slate clean and do things right. We are not alone in this – there is evidence that the pendulum has swung back from Extreme AJAX towards a healthier diet where all the Web App food groups are represented. For example, a lot of people read a blog post about Twitter performance-driven redesign, driven by exactly the same concerns I listed above. More recently, I stumbled upon an article by Mathias Schäfer arguing for a similarly mature and sane approach that embraces both the tried and true Web architectures and the interactivity that only JavaScript can provide.

You will get much better results by using the proper tool for the job. Want to access stored data fast? Pay attention to which storage solution to pick, and how to structure your data to take advantage of the particular properties of your choice. Need to show some HTML? Just serve a static document. Need to serve a dynamic document that will not change for the session? Use server side MVC to render it (I am talking a concept here, not frameworks – many server-side frameworks suffer from similar bloat but it is less detrimental on the server). Use the power of HTML and CSS to do as much rendering, animation, transition effects as you can (you will be surprised what is possible today with HTML5 and CSS3 alone). Then, and only then, use JavaScript to render widgets and deliver interactivity that wowed us so much in the recent past. But even then, don’t load JavaScript widgets cold – take advantage of the server-side MVC to prime them with markup and data so that no trip back to the server is necessary to render the initial page. You can use asynchronous requests later to incrementally update parts of the page as users go about using it (instead of aborting it half way because “this thing takes forever to load, I don’t have that kind of time”.

Eight years since AJAX has entered our vocabulary, the technique has matured and the early excesses are being gradually weeded out. We now know where overindulgence in JavaScript can lead us and must be constantly vigilant as we are writing new web applications for an increasingly diverse browser and mobile clients. We understand that AJAX is a tool in our toolbox, and as long as we don’t view it as a hammer and all our problems as nails, we will be OK. We can be bad like Jesse-James, guilt-free.

© Dejan Glozic, 2013