The tipping point

2012-05-13

So here is where I rant. Here's where I've had enough of it. It may actually be the tipping point. Whatever. Feel free to skip this one. I'll try not to hurt your feelings.

Let's start with a confession; I've entered the js realm on a serious level a few months before ES5 was released. I learned about prototype, closures, and contexts somewhere in 2009 and I still consider that required knowledge for one to claim to know js on a decent level. I read the es5 spec completely and thoroughly as soon as it was released, saving me the trouble of having to the same for es3. This does make me lacking a bit of knowledge of es3 compared to es5. I never really considered that a serious problem though. It's never been one either.

I fell in love with js for it's straightforwardness. It's clear, descriptive, concise and has an easy and hard learning curve. The language was basically one of primitives, objects, and properties. A key point for me was that assignments were clear. They weren't magical, you knew what obj.x = 5 would do, no questions asked. This idea was knifed in es5 where you could declare getters and setters. It also allows you to access internal attributes which could "freeze" objects (making it impossible to change their values). I think that wasn't possible in es3, but feel free to correct me on that one.

Now in es.next/es6/harmony (I'll go with "es6") this problem is being excavated further by introducing proxies (and whatever else).

I also like languages that are descriptive in their code. I've been fighting the reduction/removal of the function keyword since it came up. I don't buy the "less typing so more productive" argument. You type function faster than you can speak it. The size argument is squashed with gzip. I'm not sure what other arguments have passed. I got bored of the discussion regarding it. I like the keyword because it tells you in a glance that you're defining a function.

Crockford once posted a thread with the epic title "Grawlix" to es-discuss. I was confused at the whole thread at first but he was talking about the language turning into "a sequence of special characters". In fact, it was a subtle protest against this. I don't agree with everything Douglas says but I do here. For example, in a recent es-discuss thread I saw this snippet of code:

Code:
function* iterTree(tree) {
if (Array.isArray(tree)) {
// inner node
for(let i=0; i < tree.length; i++) {
for(let elem of iterTree(tree[i ])) {
yield elem;
}
}
} else {
// leaf
yield tree;
}
}

Can you guess what I'm referring to? I'll give you a hint; it's *not* the yield keyword.

I probably missed something incredibly important here because the thread seems to talk about this star example as if it's a widely known proposal. function-star what? Anyways, my point is that function* is a prime example of this grawlix. Where function foo(){} is a clear function definition, function* foo(){} just leaves me wondering what the hell's so special about that function.

I love js' explicit syntax. function name(){}, var foo = init;, new Foo(). The new keyword example here was not picked by accident, by the way. It allows you to read the code and see the semantics of most of the code in a whim. Of course that doesn't mean you can't code in a crazy obfuscated way. Look at any minified source. But it does mean you can write clean looking code. Let's look at my examples in more detail.

function foo(){} creates a new function. Just because there's slightly more stuff going on ("hoisting") than meets the eye, doesn't mean you can't write clean code that way. In all fairness, I almost always use the var foo = function(){}; pattern to define functions, unless I'm being lazy. But that doesn't matter. You're creating a function and that's immediately clear. The language could work on the binding of that function but I think that's a different matter. Oh by the way, the language _is_ in fact being worked on in that direction. Just wished it wasn't through the introduction of another way of defining a function...

var foo = init; is also very expressive and very clear; You're creating a new variable and are assigning a value to that variable. Of course, again, there's slightly more to it in js. But let's move on, it's not related to the syntax.

new Foo() creates a new object. And while the expression doesn't _have_ to return an object, a new object is still created. Unless the engine detects the explicit return override and optimises that away. You don't have to use new of course. An instance is just an object like any other, minus the "magic" prototype link to its parent. You can mimic the same kind of structure with a function that returns a new object with methods that access other methods through closures. Some people consider this easier because you don't really have to worry about contexts (the value of this). I really don't like the pattern and will rewrite it to the prototypal pattern without (those) closures whenever I can. I use closures, just not to define my object structure.

The new keyword is actually what triggered my rage. Wait, I've actually been pretty calm about it so far... This thread and in particular Brendan's response made me realise that js is turned into a language I don't fancy too much. The quote "Protocols are fine and perhaps a new-free one will take over some years hence, but not soon." makes me think that Brendan is actually an opponent of the new keyword. Edit: I misinterpreted that comment, Brendan favours new. I'm happy to know that Alex is in fact a proponent of new, so I hope he'll keep it in for a while. But it does beg the question; what is js actually turning into? Or rather, being turned into?

When I look at the proposals for es6 I get a little happy and a very disappointed. I like destructuring, default values, rest, spread, tail calls, modules (kind of), most of the API changes (if not all), and possibly pragmas if they pan out to be useful. Don't really care about the rest. Last I checked classes don't swing my way and I didn't like the way they were going. A quick glance tells me it's still not as elegant as it could be. I'm not sure where the weak-map discussion went off to. It started as a nice idea but last I read it became completely useless. Iterators and generators are an interesting concept but add a lot of complexity to the language. I don't think we need that. Comprehensions are just a complete syntactical mess. Try reading that code in a whim. Encapsulation is just a heap of FUD and might give one the impression that code is "safe". Client side js is never safe (tm).

What worries me more is that the introduction of the complexity and some of the syntactical changes make js very very hard to read, even if you're using the new features in the most elegant of ways. That's worrying! Try reading some of the code examples in various proposals, good luck. And let's not even go deeper into how much proxies are going to screw up our lives. Oh my gawd.

Now don't get me wrong. This isn't meant to be another tc39 bashing thread. I respect the tc39 for what they do. You can't please everybody and with programmers that probably entails that you can't even please two programmers at the same time. But at the danger of coming over as rather conservative, I would really prefer the tc39 to keep js the simple elegant language it actually is. If you're finally ready to make very drastic backwards-compatible-breaking changes, at least take that opportunity to FIX THE DAMN LANGUAGE. There are so many things that could be fixed, simple changes that would improve the sanity of the language. Low hanging fruit that's normally ignored because of the backwards compatibility non-breaking requirement could now be picked because people have to explicitly opt-in to es6 (at least the next ten years or so). This means conscious decisions to run es6 code! But no, instead we get more complexity and in fact a reluctance to fix even the simplest of problems! "Reluctance" does not explicitly apply to the linked message, but more to the more general issue that the problem at hand is not going to be fixed, at all. This is actually kind of infuriating to me. I know it's a simple edge case but it's so silly I really can't figure out why it'd be so hard to solve it. Ugh.

So that email by Brendan about a new-free world got to me. (Edit: even though I misinterpreted it the problems are still there and this isn't the first thread about "new-free" on es-discuss.) I've had it with js. It's going in the wrong direction and I don't like where it's going. I've tried to mix myself into the discussion (on es-discuss) but I don't have the weight or even the proper level to participate there. I'm starting to feel it's a lost cause. One we're losing more and more as time progresses. I guess the only thing I could be happy about is that I don't have to worry about those changes for another three or four years. Because let's face it, es5 is only three years old. And with the loss of a protecting champion (Edit: turns out Ebay will join Ecma!), I can only wonder whether there are any left to protect us. But that probably sounds harsher than it really is...

As for me, I don't know. I'll linger with js for a while to come. Don't worry about that. But I will be looking for a way to jump ship. If only I could go back to Forth and do it my way (tm).