Au Courant

Blog Index

TypeScript: The Future of Javascript?

Posted on 1st Sep 2015

Learning Typescript

I'll get to the why and what of TypeScript, but first a toot on my own horn - I served as a technical reviewer/advisor on the recently published Learning TypeScript from Packt Publishing.

Essentially, think of TypeScript as Javascript on steroids. Javascript was conceived in the very early days of the web browser to add a little interactive spice to staid static HTML. But where the need arose for serious interactivity or animation, developers turned (primarily) to Flash. Flash, in turn, evolved to support the increasingly heavy demands being made on it. The first version of ActionScript (Flash's programming language) actually strongly resembles Javascript; but the release of ActionScript 3 in 2006 (yes, ten years ago), Adobe decisively remade ActionScript as a modern programming language with packages, strong typing, class inheritance etc., which not only made it into a much more robust language (very similar to Java) but enabled performance gains by a factor or 10.

In the meantime Javascript has (relative to ActionScript) has remained stuck with the version 1 paradigm; numerous additions to the API may have been added but it structurally it remains virtually unchanged. That this might be a problem has not gone unrecognized, and several different approaches have been taken to move Javascript forward, such as CoffeeScript, DART, and now TypeScript.

TypeScript is being developed by Microsoft. It received a particular vote of confidence from Google, who decided to abandon their own in-house effort to upgrade JS (AtScript) in favour of incorporating TypeScript. This alone is reason enough to call TypeScript the “future of JavaScript” (though using TS is not required to develop with Angular 2.

So what exactly is TypeScript? If you’re familiar with SASS, SCSS or .less, the concept is similar. TypeScript is built around a transpiler (some prefer the term compiler) which takes code written with TS syntax and translates it into standard JavaScript, just as the SCSS transpiler takes style code written using the SCSS syntax and translates into standard CSS. And just like SCSS, TS accepts plain vanilla JavaScript code, so in principle you could write JavaScript exactly as you have always done and it will transpile into, well, JavaScript. Obviously there is no point in this except for the very important reason that any JS frameworks or libraries can be used “as is”, no modification, so you can continue to use them as before, while leveraging the power of TS in your core code.

So what is that power? In essence, it consists of “syntactic sugar” — extensions to standard JS syntax — which allows the programmer to more fully express their intentions in the actual code they write. So, for example, instead of writing a lot of comments to remind (or inform other programmers) what parameters a function is expecting, through strong typing that information is built right into the TS source code, which a TS-aware IDE can use to a) help the programmer with hints and auto-completion and b) flag errors where there are type mismatches.

JS was designed originally to be simple and forgiving. You could create a variable to hold a string, then assign an array to it, followed by an object, then a number etc. etc. and JS would never complain. At the byte level, what actually passes through the CPU, the variable is only reference to a memory location with no guarantee that whatever is at that location will “make sense”. So the forgiving nature of JS becomes entrapment; the error will only become apparent at run time. Maybe. Certainly the page will not work as expected, but the reason why can be difficult to track down.

With strong typing, to take a simple example, once you create a variable and assign it a number, TS will recognize it as having the “number” type; if the programmer then tries to assign a different type, TS will flag the error when transpiling the code to JS — and a TS-aware IDE will flag it right in the code. Now, since this “error” is still valid JS code, your TS code will transpile anyhow. It’s up to the developer to decide, oops, I didn't mean that, and fix it or let it go. Which would not be “best practice” — but that’s the developer’s decision. (A better practice, in cases where you really do need to store different value types in a given variable, is to explicitly type it as “any” when first declaring it.)

This is of course just the tip of the typing iceberg, and strong typing is only the beginning of TS’s syntactic sugar.

Look into any book or course on object-oriented programming (OOP) and you will find discussions of such principles as inheritance, encapsulation, polymorphism etc. etc. JavaScript is essentially a procedural language with limited support for modern OOP principles; it does not support the class syntax (“new”, “extends” etc.), which is how true OOP languages like Java, C#, Swift, and, yes, ActionScript 3, implement inheritance and so forth. JS does have prototype inheritance but this is cumbersome, especially when trying to extend an object.

TS brings true class syntax with support for class inheritance/extension/subclassing (call it what you will). The transpiler converts this code into prototype inheritance, which advanced JS programmers will recognize easily, with a bit of helper code at the top to support subclassing.

TypeScript in the real world

As an advanced ActionScript developer I find TS a very natural fit, allowing me to apply the OOP principles that I am familar with to JavaScript development. More specifically, in several cases I’ve been called upon to redevelop some Flash apps I’ve done in HTML5 (need I explain why?). Being able to rewrite the code in TypeScript, recreating the same classes and subclasses etc., turned what could have been a festival of pain into a straightforward, even pleasurable process. It didn’t hurt that the GreenSock tweening/animation engine, which I rely heavily on for AS development, has been ported to JavaScript, employing to the extent possible the same syntax as the AS version.

TS vs AS: a performance advantage?

I mentioned that JavaScript is comparable to ActionScript 1. You may ask if TS brings JavaScript up to the level of ActionScript 3. The answer is simple: No.

Why? The adding of syntactical sugar such as classes and strong typing — that was done in AS2. But AS2 compiles down to the same byte code, and runs is the same virtual machine, as ActionScript 1 (AVM1). And, as I’ve also mentioned, TS always compiles to standard (ES5) JavaScript, and thus does nothing to change the characteristics or limitations of the JavaScript run-time engine. AS3, on the other hand, goes hand in hand with a new byte code format running in a new virtual machine (AVM2, incorporated in the Flash plugin starting with version 9, as well as Adobe AIR). Is is this virtual machine/byte code (and compiler) combination that radically improved ActionScript performance by a factor of 10 or more. To cite one example, AS3 supports integers. CPUs like integers, they inherently translate directly into bit patterns. Remember when Floating Point Units were expensive additions to computers? Before long they were incorporated into CPU chips but the performance hit is much the same. Loops — iterating over an array of values to, say, move bullets towards a target in a shoot-em-up game, checking for collisions all the while — is intensive computationally — and doing integer math for the counters etc. is a big advantage.

Another advantage of the AS3 format is that class objects are by default sealed, I.E., unlike JS objects (and classes) which are always dynamic, your code cannot add or change properties or methods at run-time. Again, CPUs like this; once instantiated, it can expect the properties and method calls of an object/class to be in the same place in memory, while with dynamic objects it has to go through a process of looking up the locations in hash tables, a hit on performance).

Interestingly, there is some movement in favour of incorporating byte code in the browser (see this Ars Technical article), because of the inherent performances, which is ironic given that so much effort and pressure has gone into removing byte code implementation in the browser via plugins (and not just Flash; Java is feeling the same heat).

And so…?

The browser will evolve. JavaScript is evolving, slowly (ES6 is on the horizon). TS may become widely adopted (Angular is wildly popular, but not everyone is enthusiastic about Angular 2); but if not many of its features will likely be rolled into future iterations of JavaScript. But why wait?