An Escape From Front End Development

Thursday, January 8, 2015 by K. Scott Allen
9 comments

The year 2015 starts and I’m working on a code generator, which is one of the more enjoyable tasks in software for me. Code generators and meta programming requires considerably more mental focus than banging out business code, the kind of focus where any interruption is tantamount to dumping the Atlantic Ocean on a continental scale forest fire. It also means the interrupter is subject to an assortment of growls, stares, and verbal assaults, and for these I apologize.

The are a couple specific challenges  this project, but the general challenge in building code generation software is in building a model that can serve two masters. On one hand, the model has to make the actual generation phase easier. On the other hand, the model has to be easy to build from some source of data, be it a visual designer or, in my case, XML. Not just any XML, but XML of debilitating complexity as one critic puts it, and I agree. There are times when I suspect someone has willfully obfuscated the XML, but then I remember Hanlon’s razor (with a twist):

Never attribute to malice that which is adequately explained by stupidity, or is the output of a standards committee. 

Regardless of the data source, I’ve been to the codegen rodeo before, and the code usually falls into place like the following:

codegen

Adapters have to surround the model to make it usable from both ends. In this scenario there are parsers to transform XML into meaningful data structures, and adapters to facilitate the code generation. Ironically, this has been done before as open source, but the output is JavaScript. JavaScript and it’s various server-side runtimes have some strengths, but algorithmic number crunching and set sorting at scale is not one of the those.

I’m replacing JavaScript code then, with something I hope is better. The irony is how I spent 2014 writing more JavaScript code than I have in the previous 15 years, on the server but mostly on the client, and I needed a break. A problem with real teeth. It’s not that front end development doesn’t have any challenges, but I’ve been frustrated by the irresponsible amounts of accidental complexity in front end development.

Ah, you must be talking about the complex framework by the name of Angular.

Well, no, but let’s use Angular as an example. It is, truthfully, a simple framework when you discard all the permutations offered and stick to simple, disciplined, and calculated practices. Projects go haywire for any number of reasons, here are three examples I’ve seen in just the last week.

1) Projects that treat Angular modules as CommonJS or AMD modules, in the sense that every little component needs a dedicated module. With Angular this practice only creates more work and bookkeeping for little gain.

2) The confusion between module.factory and module.service. I always try to tell people to think of factory and service as registration APIs only. To the consumer, it doesn’t matter which one you choose, they both create a service component. When people tell me they are passing a factory to their controller, I get confused. The factory API registers a factory function, but the function is not what the injector will pass to a controller, the injector will pass the output of the method, which is the service.

Taking a step back, both of these problems stem from one of the “two hard things”:

There are only two hard things in Computer Science: cache invalidation and naming things.

-- Phil Karlton

And that’s something I won’t escape from. Naming things is hard on the frontend, but also here on the backend, too.

PageObjects and Protractor

Tuesday, January 6, 2015 by K. Scott Allen
11 comments

I’m a fan of the PageObject pattern when writing Protractor tests, because PageObjects make the test code more expressive and readable. When I sit down to write some Protractor tests, I usually write the test code I want to see first, and then try to make it happen.

For example, when writing some tests for a “login and redirect” scenario, I started off with some test specs like the following.

describe("The security application", function () { 

    var secret = new SecretPage();
    var login = new LoginPage(); 

    it("should redirect to login page if trying to view a secret as anonymous user", function () {
        secret.go();
        expect(browser.getCurrentUrl()).toBe(LoginPage.url);
    }); 

    it("should go back to the secret after a login", function () {
        login.login("sallen", "sallen");
        expect(browser.getCurrentUrl()).toBe(SecretPage.url);
    }); 

});

These tests require two page objects, the SecretRecipePage and the LoginPage. SInce Protractor tests run in Node, each page can live in a distinct module. First, the SecretRecipePage.

var config = require("./config"); 

var SecretPage = function () { 

    this.go = function() {
        browser.get(SecretPage.url);
    }; 

}; 

SecretPage.url = config.baseUrl + "security/shell.html#/secret"; 

module.exports = SecretPage;

And the LoginPage.

var config = require("./config"); 

var LoginPage = function () { 

    this.go = function() {
        browser.get(LoginPage.url);
    }; 

    this.login = function(username, password) {
        $(".container [name=username]").sendKeys(username);
        $(".container [name=password]").sendKeys(password);
        $(".container [name=loginForm]").submit();
    }; 
}; 

LoginPage.url = config.baseUrl + "security/shell.html#/login"; 

module.exports = LoginPage;

Both of these modules depend on a config module to remove hard coded URLs and magic strings. A simple config might look like the following.

var config = {
    baseUrl: http://localhost:9000/Apps/
}; 

module.exports = config;

Now all the spec file needs to do is require the two page modules …...

var SecretPage = require("../pages/SecretPage");
var LoginPage = require("../pages/LoginPage.js"); 

describe("The security application", function () { 

    // …... 

});

And presto! Readable Protractor tests are passing.

image

More With Arrow Functions in ES6

Monday, January 5, 2015 by K. Scott Allen
4 comments

In a previous post we took a first look at arrow functions in ES6. This post will demonstrate another feature of arrow functions, as well as some additional scenarios where you might find arrow functions to be useful.

Every JavaScript programmer knows that the this pointer is a bit slippery. Consider the code in the following class, particularly the code inside of doWork.

class Person {
    constructor(name) {
        this.name = name;
    }

    doWork(callback) {
        setTimeout(function() {
            callback(this.name);
        }, 15); 
    }
}

The anonymous function the doWork method passes into setTimeout will execute in a different context than doWork itself, which means the this reference will change. When the anonymous function passes this.name to a callback, this won’t point to a person object and the following test will fail.

var person = new Person("Scott");
person.doWork(function(result) {
    expect(result).toBe("Scott"); // fail!
    done();
});

Since developers can never rely on JavaScript’s this reference when asynchronous code and callbacks are in the mix, a common practice is to capture the value of this in a local variable and use the local variable in place of this. It’s common to see the local variable with the name self, or me, or that.

doWork(callback) {
    var self = this;
    setTimeout(function() {
        callback(self.name);
    }, 15); 
}

The above code will pass, thanks to self capturing the this reference.

If we use an arrow function in doWork, we no longer need to capture the this reference!

doWork(callback) {
    setTimeout(() => callback(this.name), 15); 
}

The previous test will pass with the above code in place because an arrow function will automatically capture the value of this from its outer, parent function. In other words, the value of this inside an arrow function will always be the same as the value of this in the arrow’s enclosing function. There is no more need to use self or that, and you can nest arrow functions arbitrarily deep to preserve this through a series of asynchronous operations.

Using Arrow Functions Everyday

If you embrace the arrow function syntax, you might find yourself using the syntax with every few lines of code you write. JavaScript’s affinity for asynchronous operations has created an enormous number of APIs requiring callback functions. However, as JavaScript is a solid functional programming language, more and more synchronous APIs have also appeared with function arguments.

For example, ES5 introduced forEach and map methods on array objects.

let result = [1,2,3,4].map(n => n * 2);
expect(result).toEqual([2,4,6,8]);

let sum = 0;
[1,2,3,4].forEach(n => sum += n);
expect(sum).toBe(10);

There are also many libraries like underscore and lodash that use higher order functions to implement filtering, sorting, and grouping of data. With ES5 the code looks like the following.

let characters = [
    { name: "barney", age: 36, blocked: false },
    { name: "fred", age: 40, blocked: true },
    { name: "pebbles", age: 1, blocked: false }
];

let result = _.find(characters, function(character) {
    return character.age < 40;
});

With arrow functions, the result calculation becomes more expressive.

let result = _.find(characters, character => character.age < 40);
expect(result.name).toBe("barney");

You can even write a Jasmine test using an arrow function.

it("can work with Jasmine", () => {
    var numbers = [1,3,4];
    expect(numbers.length).toBe(3);
});

Many of the examples shown in this section, like the examples using forEach, map, and _, all work with the concept of collections. Other feature of ES6, like iterators, will make working with collections noticeably more flexible and reliable. We’ll turn out attention to iterators next.

Arrow Function In ES6

Tuesday, December 9, 2014 by K. Scott Allen
6 comments

JavaScript has always been a functional programming language. You can pass functions as arguments to other functions, and invoke a function that returns a function back to you. The ES6 standard improves JavaScript’s functional programming capabilities by offering a new, succinct syntax for creating functions. In addition, ES6 defines new syntax to offer features closely associated with functional programming, features like iterators and lazy evaluation. Let’s start looking at the new capabilities by looking at the arrow function, which will look familiar to anyone who has worked with CoffeeScript or C# code.

An arrow function doesn’t require the function keyword, or curly braces, or a return statement. However, arrow functions do require a new operator, the =>, which looks like an arrow pointing to the right and which gives these expressions their name. To build an arrow function for adding two numbers, one simply has to write the following.

let add = (x,y) => x + y; 

On the left-hand side of the arrow is the parameter list for the function. In this example there are two parameters, x and y. To the right of the arrow is the executable code. In this case, the code returns the sum of x and y. You could think of the arrow as pointing the parameters to the code that uses them.

Invoking an arrow function looks no different than invoking a traditional function.

let result = add(3, 5); 

expect(result).toBe(8);

Arrow functions that use exactly one function parameter do not need to surround the parameter with parenthesis.

let square = x => x * x; 

If an arrow function requires zero parameters, or more than one parameter, then the parenthesis are required.

let add = (x,y) => x + y;             // required parens 
let square = x => x * x;              // optional parens 
let compute = () => square(add(5,3)); // required parens 
let result = compute(); 

expect(result).toBe(64); 

So far, the examples use a single expression to the right of the arrow operator. When using a single expression, curly braces and return statements are not required. The return value of the function will be the value of the expression.

However, an arrow function may contain a more complex block of statements, but this approach does require braces and an explicit return (if the function wants to return a value).

let add = (x,y) => {
    var result = x + y;
    return result;
};

In the next post of this series, we’ll look at a special quality of arrow functions, and also see how we can use them in some common scenarios.

Class Inheritance in ECMAScript 6

Tuesday, November 25, 2014 by K. Scott Allen
5 comments

Continuing from a previous post

Over the years, there have been various approaches to building class hierarchies in JavaScript. All these approaches worked by stitching together constructor functions and prototype objects and each approach was slightly different from the others.

The ES6 standard allows for a declarative, consistent approach to inheritance using the class and extends keywords. As an example, let’s start with a simple class to represent a person with a name.

class Person {
    
    get name() {
        return this._name;
    } 

    set name(newName){
        if(newName){
            this._name = newName;
        }
    } 

}

var p1 = new Person();
p1.name = "Scott";
expect(p1.name).toBe("Scott");

Now we also need a class to represent an employee who has both a name and a title. Using the extends keyword, we can have an Employee class inherit from the Person class, meaning every object instantiated as an Employee will also have all the methods and properties available for a Person.

class Employee extends Person {

    get title() {
        return this._title;
    }

    set title(newTitle) {
        this._title = newTitle;
    }
}

var e1 = new Employee();
e1.name = "Scott"; // inherited from Person
e1.title = "Developer";

expect(e1.name).toBe("Scott");
expect(e1.title).toBe("Developer");
expect(e1 instanceof Employee).toBe(true);
expect(e1 instanceof Person).toBe(true);

When describing the relationship between Employee and Person we often say Person is a super class of Employee, while Employee is a sub class of Person. We can also say that every employee is a person, and as you can see in the above code, the instanceof check in JavaScript confirms that an object created using the Employee class is also an instance of Person.

While every Employee object will inherit all the state and behavior of a Person, the Employee class also has the ability to override the methods and properties defined by Person. For this example, let’s add a doWork method to every Person.

class Person {

    get name() {
        return this._name;
    }

    set name(newName){
        if(newName){
            this._name = newName;
        } 
    }

    doWork() {
        return this.name + " works for free";
    } 

}

var p1 = new Person();
p1.name = "Scott";
expect(p1.doWork()).toBe("Scott works for free");

By default, an Employee will behave the same as a Person.

var e1 = new Employee();
e1.name = "Scott";
e1.title = "Developer";
expect(e1.doWork()).toBe("Scott works for free");

However, in the Employee class we can override the behavior of doWork by providing a new implementation.

class Employee extends Person {

    // ...

    doWork() {
        return this.name + " works for a salary";
    }
}

var p1 = new Person();
p1.name = "Scott";
expect(p1.doWork()).toBe("Scott works for free");

var e1 = new Employee();
e1.name = "Scott";
e1.title = "Developer";
expect(e1.doWork()).toBe("Scott works for a salary");

Now, as the tests prove, objects instantiated from the Employee class will behave slightly differently in the doWork method than objects instantiated from the Person class. In object-oriented programming, we call this behavior polymorphism.

Using Super

There are times when a class will want to invoke behavior in its super class directly, which can be done with the super keyword. For example, the Employee class could implement the doWork method as follows.

doWork() {
    return super() + "!";
}

Invoking super will execute the super class method of the same name, so with the above code a passing test would now look like the following.

var e1 = new Employee();
e1.name = "Alex";
e1.title = "Developer";

expect(e1.doWork()).toBe("Alex works for free!");

A class can also refer explicitly to any method in the super class.

doWork() {
    return super.doWork() + "!";
}

Super Constructors

One common scenario for using super is when inheriting from a class that requires constructor parameters. The following Person class now accepts a name parameter during initialization.

class Person {

    constructor(name) {
        this._name = name;
    }

    get name() {
        return this._name;
    }

}

Now an employee will need both a title and a name during initialization.

class Employee extends Person {

    constructor(name, title) {
        super(name);
        this._title = title;
    }

    get title() {
        return this._title;
    }

}

Notice how the Employee constructor method uses super to pass along the name parameter to the Person constructor and reuse the logic inside the super class. What’s interesting about JavaScript compared to other object oriented languages, is how you can choose if and when to call the super class constructor. If I were to pick a style to remain consistent, I’d always make a call to super in a sub class before executing any other logic inside the constructor. This style would keep JavaScript classes consistent with the behavior of other object-oriented languages.

The Caveat

Now that we know what inheritance looks like in ES6, it’s time for a word of caution. Inheritance is a fragile technique to achieve re-use that only works well in a limited number of scenarios. Do a search for “composition over inheritance” to see more details.

Adventures in Angular Podcast and an AngularJS Oslo Meetup

Tuesday, November 18, 2014 by K. Scott Allen
0 comments

Last month I did an interview with the Adventures in Angular podcast crew, you can listen here.

I also did a talk at the AngularJS Meetup in Oslo. You can watch the recoding here.

Both the podcast and the Meetup talks were loosely centered around using the next version of JavaScript with the current version of Angular.

In addition to all the syntax sugar in ES6, which makes JavaScript code more expressive, the new class keyword works well for building services and controllers in Angular. As an example, imagine you are building a Pong game, and need a service to control the left paddle and a second service for the right paddle. One paddle is controlled by the keyboard, the other by AI. This is a scenario where you might, if you are brave, consider inheritance, as long as the relationship stays simple.

(function(app) {

    class Paddle {
        constructor() {
            this.x = 0;
            this.y = 0;
        }

        startMoveDown() {
            this.y += 2;
        }

        stopMoveDown() {
            this.y -= 1;
        }

        startMoveUp() {
            this.y -= 2;
        }

        stopMoveUp() {
            this.y += 1;
        }
    }

    class LeftPaddle extends Paddle {
        constructor(keyboardHandler) {
            Paddle.call(this);
            this.x = 25;
            this.y = 100;
            keyboardHandler.onArrowUp(38, () => this.startMoveUp(), this.stopMoveUp());
            keyboardHandler.onArrowDown(40, () => this.startMoveDown(), this.stopMoveDown());
        }
    }

    class RightPaddle extends Paddle {
        constructor() {
            Paddle.call(this);
            this.x = 975;
            this.y = 300;
        }
    }

    app.service("leftPaddle", LeftPaddle);
    app.service("rightPaddle", RightPaddle);

}(angular.module("pong")));

The class constructor for controllers and services will be injectable, but you’ll want to use module.service to register service classes, and not module.factory, because only .service instantiates the service using new.

Thoughts on Angular 2.0

Thursday, November 13, 2014 by K. Scott Allen
9 comments

The Great Wave off KanagawaNeil Young once sang how “every wave is new until it breaks”. The line was a poke at trendiness in the music industry, but I find the lyrical snippet is applicable to software development, too, in a number of subtle ways.

There has been a lot of turmoil surrounding the future direction of Angular, which is fair. The preview and announcements made for Angular 2.0 during ng-europe were dramatic and conveyed no empathy for the customers and development teams who have taken a dependency on the framework. Those people are left wondering when the ng-wave will break.

The Blessings and Curses of Backwards Compatibility

Web developers have always faced incompatibilities, but have also been fortunate enough to build software on top of a set of technologies and standards that have diligently preserved backward compatibility. This diligence allows the nearly 20 year old web page for the animated movie Space Jam to live on. We’ve been accustomed to building software using web standards that keep working into the future. Stability is good for business.

But backward compatibility has a price. I believe the web moves at a snails pace, which is contrary to popular opinion. However, compare the evolution of the JavaScript language to some of its peers like C# or even Java. Next year’s ECMASCript 6 release is the first big move forward for the language in nearly 20 years. Also consider the XMLHttpRequest API. The API is central to today’s applications, but it has taken the industry 15 years to standardize the API  and build the tools to make mainstream developers productive with asynchronous requests and dynamic DOM updates.

Should Angular 2.0 be backward compatible? Or should Angular 2.0 follow Py3k?

Python 3.0, also known as “Python 3000” or “Py3K”, is the first ever intentionally backwards incompatible Python release. There are more changes than in a typical release, and more that are important for all Python users. Nevertheless, after digesting the changes, you’ll find that Python really hasn’t changed all that much – by and large, we’re mostly fixing well-known annoyances and warts, and removing a lot of old cruft.

Surfing the Waves of Change

Web development feels like a fast changing environment, but a closer look will show we mostly churn in the turbulence of small, incremental improvements. It’s rare for a wave to arrive and move everyone forward.

I still believe Angular 1.x is the best wave to ride today. I already have applications in production with Angular 1.2, and at least one more on the way with 1.3.  With the core Angular code base being only 25k lines of JSDoc’ed, tested, working, healthy code, I believe the wave can keep can keep rolling for years to come.

I also believe Angular 2.0 should be a new wave that makes a break from Angular 1.x and evolves without being encumbered by backward compatibility or designs for an easy migration path. We’re still early in the history of application development on the web, and there will one day be a newer, bigger, better swell. It’s name might be Angular 2, or maybe something entirely new will come along. That’s life in the rough seas of web development, where you can either fight the waves and drown, or surf the waves and stay on top.

by K. Scott Allen K.Scott Allen
My Pluralsight Courses
The Podcast!