The Dark Side of Javascript Fatigue

Javascript fatigue is a real experience for many developers who don’t spend their day to day in Node.js bashing out javascript. For many developers javascript is an occasional concern. The thing I can’t figure out about the javascript development world is the incredible churn. Churn is often disaster for a programming community. It frustrates anyone trying to build a solid application that will have a shelf life of a decade or more. Newcomers are treated to overwhelming choices without enough knowledge to choose. Then they find what they’ve learned is no longer the new and shiny tool only a few months later. And anyone on the outside feels validated in not jumping in.

Many in the javascript community attempt to couch all the churn as a benefit. It’s the incredible pace of innovation. I see sentiments like this:

The truth is, if you don’t like to constantly be learning new things, web development is probably not for you. You might have chosen the wrong career!
Josh Burgess

Even if we accept that it all the ‘innovation’ is moving things forward more quickly, there is rarely the reflection on the consequences. I’ve worked on an approximately 9 year old Rails app for about 5 years now and I’m still shocked by the number different frameworks and styles of javascript that litter the app:

  • Hand rolled pre JQuery javascript
  • Javascript cut and paste style
  • RJS (an attempt to avoid writing javascript altogether in early rails)
  • YUI
  • Prototype
  • Google Closure
  • JQuery
  • Angular

Eight different frameworks in about as many years. And though we adopted Angular about 2 years ago we’re already dealing with non-backwards compatibility, Angular 2.0. This is a large burden on maintenance and it costs us very real time to spin up on each one when we have to enhance the app or fix a bug.

This is a monolithic app that’s been built over quite a few years, but the big difference is the Rails app was opinionated and stuck to a lot of default conventions. The framework churn of Rails has been much more gradual and generally backwards compatible. The largest pain we experience was going from Rails 2 to 3, when Rails was merged with Merb. The knowledge someone built up in their first few years working in Ruby and Rails still applies. The churn is certainly exists, but at a measure pace.

In phone screens when I describe our main app, I list off the myriad javascript frameworks we use as a negative they should know about. And almost none of the candidates have heard of Google Closure, even though a critical piece of the app was written in it. They often assume I must be talking about the JVM Clojure.

Javascript has never been popular because of elegance or syntax. Rants like the following are not hard to find:

You see the Node.js philosophy is to take the worst fucking language ever designed and put it on the server.
Drew Hamlett

Large majorities of developers would rather avoid it completely to focus on any modern language and hopefully use a transpiler if they have to touch Javascript. In this environment it might do the javascript community some good to settle down some and focus on some stability.

Javascript Goes Back to Class

Not long ago at a user group I saw a strange piece of sample code like this on an overhead projector:

1
2
3
4
5
6
7
8
9
10
11
12
class Person {

  constructor(firstName, lastName) {
    this.firstName = firstName;
    this.lastName = lastName;
  }

  fullName() {
    return this.firstName + ' ' + this.lastName;
  }

}

I chuckle a little bit inside. I’ve heard plenty of arguments over the years that Javascript’s prototypical inheritance was the right way to do things and trying to force traditional OO on Javascript was doing it all wrong:

If you’re creating constructor functions and inheriting from them, you haven’t learned JavaScript. It doesn’t matter if you’ve been doing it since 1995. You’re failing to take advantage of JavaScript’s most powerful capabilities. — Eric Elliot

It turns out ECMAScript 6 has officially added class style OO to the language. So the needs of many occasional Javascript developers to have a more familiar looking construct that would be at home in Java, C#, or Ruby eventually won.

Converging on Javascript is a Bad Idea

For many developers despite some of the node.js hype, Javascript is a language we’ve been stuck with by an unfortunate decision by Netscape to bundle a language tossed together in 10 days. It wasn’t even called Javascript at the time, it emerged originally as LiveScript. They even tried to market a server side version bundled with Netscape Enterprise Server in the days when you could sell web servers for real money.

Dave Winer’s recent blog post on Why aren’t the BigCo’s Converging on Javascript? argues that Javascript has arrived and is dominating even while the big Companies like Apple and Google try to push newer languages. I agree that these companies have some of their own agendas in building out new languages, but if Javascript were truly so great and dominant why does everyone build a transpiler from ClojureScript to Opal to avoid having to write in plain old Javascript. My answer is because Javascript is a terrible language if you have a choice.

Look at any newer modern language and you’re going to find a nicer language with many fewer warts than Javascript take your pick of many:

  • Ruby
  • Scala
  • Clojure
  • C#
  • Go
  • Rust
  • Elixir
  • Python
  • Swift

Javascript would have died off very quickly without its’ continued support as the only way to script browser clients. Even now many are turning to transpiling to take the pain out of supporting large javascript code bases. It may eventually turn out that Javascript becomes just a readable intermediate language that your favorite language compiles down to much like byte code on the JVM. Or maybe the browser vendors start supporting a new VM on the browser and languages can target that.

One Year with Jasmine

It’s been about one year since we introduced Jasmine as our default for Javascript testing. Looking back it’s easy to declare it a success:

  • We test all our new javascript instead of just deciding it isn’t worth the effort.
  • Javascript is broken out into files instead of having the temptation of just leaving it inline in a view template.
  • Functions are broken down and refactored to be small and testable.
  • We’ve even been able to test some complex Closure javascript using Jasmine instead of JSUnit.
  • Running the full Jasmine suite is a part of every CI build.

If we’d only achieved a few of these things I’d consider it a big success. For a long time my default approach was to handle Javascript testing through functional Selenium based tests. While these are valuable tests, they certainly don’t help doing TDD with Javascript. Jasmine has finally allowed me to stay in a BDD/TDD workflow when switching between Ruby and Javascript.