found drama

get oblique

an annotated guide to the Google JavaScript Style Guide

by Rob Friesel

Following up on the Google JavaScript Style Guide that made the rounds recently: I did a couple of passes through the document and absorbed as much of it as I could 1. After discussing the style guide with a few peers, I thought that it might make sense to provide some annotations–in part for personal reference 2 but also to engage in the dialogue. There are a few implicit points in there that I thought might be interesting to pull together. And I also felt comfortable indulging in the hubris of splitting hairs.

And so, without further ado: an annotated guide to the Google JavaScript Style Guide:

JavaScript Language Rules

  • var: Agreed. What seems missing (both in Language Rules and in Style Rules) is any comment on the use of commas. Example:

    Show me a minifier that will convert the first into (effectively) the second and I would say that there is your answer. But in the meantime, the third approach is perhaps the most readable while still offering the compression benefits. But beware! UglifyJS converts the first into the second, plus all of the usual minification goodies: so there is your answer. But if you can’t use UglifyJS (or a similarly featured minifier) for some reason and are “stuck” using (for example) YUICompressor or not minifying at all: BEWARE:

    Forget even one comma and you create a debugging nightmare for yourself or (worse) your team members.

  • Constants
  • Semicolons: There is no excuse to omit your semicolons; failing to do so is just sloppy.
  • Nested functions: The question here is more about turning this one on its head. With an object-oriented approach, there is a strong temptation to turn every function into its own named member method. The Google team has an excellent point that using nested functions helps “in the creation of continuations and for the task of hiding helper functions”; so instead it would seem that you should favor nested 3 functions by default and reserve named member functions for when (a) that function needs to be called by n>1 other functions; or (b) the function needs to be exposed to some apparatus external to the class that otherwise contains it.
  • Exceptions and Custom exceptions: They say “go for it”. But they also say that you can’t avoid exceptions. It would seem that the best strategy would be: plan to fail gracefully, and when you can’t, at least fail usefully.
  • Function Declarations Within Blocks: The Google write-up on this is pretty good and is concise. To split hairs though, their “do this instead” example has the var statement inside the if, which feels like the quick road to accidentally re-declaring that var. And also, for what it’s worth: function foo(){} and var foo = function(){}; are functionally equivalent most of the time anyway 4.
  • Standards features
  • Wrapper objects for primitive types: See also: why you should basically never use the Number constructor and/or Subclassing Arrays and Why === Isn’t Always Better Than == and/or How ECMAScript 5 still does not allow to subclass an array 5.
  • Multi-level prototype hierarchies
  • Method definitions
  • Closures
  • eval()
  • with(){}: When you have Function.call() and Function.apply() at your disposal for scope management, why would you ever want to use with(){}?
  • this: Good advice; but don’t let it dissuade you from getting your hands dirty with this. There are some powerful techniques in there if you have the patience to sort through the chaff.
  • for-in loop
  • Associative Arrays: Their advice, shortened: JavaScript has no such thing as an associative array; what you’re otherwise seeing is just an unfortunate side-effect.
  • Multiline string literals
  • Array and Object literals: …they also minify smaller than using the constructors; and if you find yourself dealing with hundreds-of-thousands or more, you might also notice a performance benefit as well 6 7.
  • Modifying prototypes of built-in objects
  • Internet Explorer’s Conditional Comments: They don’t come right out and say it, so I’ll just assume it’s implied… The “other” reason not to use IE conditional comments in your JavaScript is because the guy maintaining your code will have no idea what the hell they are.

JavaScript Style Rules

  • Naming
    • W/r/t/ private members: though they suggest a trailing underscore (i.e., memberName_), most folks that I know prefer the leading underscore (i.e., _memberName) 8. “The point” being that if you’re going to have private members, best to make it obvious and better still to be consistent about it.
    • W/r/t/ namespaces and filenames: depending on how you have your project code organized, it would be a good idea to make your directory structure reflect your namespacing. E.g., if you have a constructor class named foo.bar.Ball then maybe the path to that file should be foo/bar/ball.js
  • Custom toString() methods
  • Deferred initialization
  • Explicit scope
  • Code formatting
    • The implied basics: they don’t come right out and say it, but it sounds like “80 characters per line (unless you can’t help it), indent four space (except where we’ve recommended otherwise), and the whole spaces-vs.-tabs thing is an argument we’re staying out of.”
    • W/r/t/ blank lines:

  • Parentheses
  • Strings: It’s a strong case to make for the single-quotes–but for some of us, this is too much to stomach 9.
  • Visibility (private and protected fields): It’s a good explanation of the intent of private and protected members; but in a lot of cases, we all do well to consider closures for the code-hiding benefits which are usually what we’re really after:

  • JavaScript Types: Short version: never forget that JavaScript is loosely typed; be careful, and be explicit.
  • Comments: JSDoc comments are great, but let’s not forget to emphasize that /* block comments */ inside of a function are obnoxious and rude to your collaborators. // single-line comments only inside of your functions.
  • Inner Classes and Enums
  • Compiling
  • Tips and Tricks
    • W/r/t/ “Iterating over Node Lists”: As one peer points out, the “cute trick” that they recommend for iterating over node lists will work great until it catastrophically and silently fails when processing a sparse Array, or when one of those values is falsy. Consider:

      Granted, if “node list” here means that it is an HTMLCollection, then you should never encounter that scenario. But why would you ever let yourself take that chance?

Updates:

  • 10/12/2010: – Added comments about “Function Declarations Within Blocks” and “Internet Explorer’s Conditional Comments”.
  • 5/3/2012: – Linked from a post by Addy Osmani’s; did a sanity-check sweep over the text to make sure that this was still consistent with my views (needed to update my stance on single- vs. double-quotes) and added the link to “Inner Classes and Enums”.
  1. Nutshell version of my reaction: Well that all seems like common sense, just spelled out rather eloquently; but I’ll be damned if you want me give up my double-quotes. (See the footnote in the section on ‘Strings’ for my change of heart on this.)[]
  2. To aid with digestion.[]
  3. …and anonymous…[]
  4. The key difference being that the former makes the function available immediately during evaluation, not execution.[]
  5. Although that third one there is really more about the intricacies of prototypal inheritance (esp. as it relates to the Array) than it is about JavaScript types and its loosely typed implementation.[]
  6. Though let’s be frank: even at that scale the benefits are trivial.[]
  7. Though YMMV depending on your implementation and your interpreter.[]
  8. If they bother to indicate that a method is private at all.[]
  9. Double-quotes just “feel” more correct. (After doing so much work in Groovy (where single- vs. double-quotes matter, incidentally), I’ve come around on single-quotes.)[]

About Rob Friesel

Software engineer by day. Science fiction writer by night. Weekend homebrewer, beer educator at Black Flannel, and Certified Cicerone. Author of The PhantomJS Cookbook and a short story in Please Do Not Remove. View all posts by Rob Friesel →

6 Responses to an annotated guide to the Google JavaScript Style Guide

Leave a Reply

Your email address will not be published. Required fields are marked *

*

*