Coding Guidelines by Google

Document and share your code style guide with your team.

USE TEMPLATE

Coding Guidelines by Google

google

Google JavaScript Style Guide

Example code in this document is non-normative. That is, while the examples are in Google Style, they may not illustrate the only stylish way to represent the code. Optional formatting choices made in examples must not be enforced as rules.

Formatting

Terminology Note: block-like construct refers to the body of a class, function, method, or brace-delimited block of code. Note that, by Array literals and Object literals (see below), any array or object literal may optionally be treated as if it were a block-like construct.

Tip: Use clang-format. The JavaScript community has invested effort to make sure clang-format does the right thing on JavaScript files. clang-format has integration with several popular editors.

Braces

Braces are used for all control structures

Braces are required for all control structures (i.e. if, else, for, do, while, as well as any others), even if the body contains only a single statement. The first statement of a non-empty block must begin on its own line.

Illegal:

if (someVeryLongCondition())
doSomething();
for (let i = 0; i < foo.length; i++) bar(foo[i]);

Exception: A simple if statement that can fit entirely on a single line with no wrapping (and that doesn’t have an else) may be kept on a single line with no braces when it improves readability. This is the only case in which a control structure may omit braces and newlines.

if (shortCondition()) return;

Nonempty blocks: K&R style

Braces follow the Kernighan and Ritchie style (Egyptian brackets) for nonempty blocks and block-like constructs:

  • No line break before the opening brace.

  • Line break after the opening brace.

  • Line break before the closing brace.

  • Line break after the closing brace if that brace terminates a statement or the body of a function or class statement, or a class method. Specifically, there is no line break after the brace if it is followed by else, catch, while, or a comma, semicolon, or right-parenthesis.

Example:

class InnerClass {
constructor() {}
/** @param {number} foo */
method(foo) {
if (condition(foo)) {
try {
// Note: this might fail.
something();
} catch (err) {
recover();
}
}
}
}

Empty blocks: may be concise

An empty block or block-like construct may be closed immediately after it is opened, with no characters, space, or line break in between (i.e. {}), unless it is a part of a multi-block statement (one that directly contains multiple blocks: if/else or try/catch/finally).

Example:

function doNothing() {}

Illegal:

if (condition) {
// …
} else if (otherCondition) {} else {
// …
}
try {
// …
} catch (e) {}

Block indentation: +2 spaces

Each time a new block or block-like construct is opened, the indent increases by two spaces. When the block ends, the indent returns to the previous indent level. The indent level applies to both code and comments throughout the block. (See the example in 4.1.2 Nonempty blocks: K&R style).

Array literals: optionally block-like

Any array literal may optionally be formatted as if it were a “block-like construct.” For example, the following are all valid (not an exhaustive list):

const a = [
0,
1,
2,
];
const b =
[0, 1, 2];
const c = [0, 1, 2];
someMethod(foo, [
0, 1, 2,
], bar);

Other combinations are allowed, particularly when emphasizing semantic groupings between elements, but should not be used only to reduce the vertical size of larger arrays.

Object literals: optionally block-like

Any object literal may optionally be formatted as if it were a “block-like construct.” The same examples apply as Array literals: optionally block-like. For example, the following are all valid (not an exhaustive list):

const a = {
a: 0,
b: 1,
};
const b =
{a: 0, b: 1};
const c = {a: 0, b: 1};
someMethod(foo, {
a: 0, b: 1,
}, bar);

Class literals

Class literals (whether declarations or expressions) are indented as blocks. Do not add semicolons after methods, or after the closing brace of a class declaration (statements—such as assignments—that contain class expressions are still terminated with a semicolon). Use the extends keyword, but not the @extends JSDoc annotation unless the class extends a templatized type.

Example:

class Foo {
constructor() {
/** @type {number} */
this.x = 42;
}
/** @return {number} */
method() {
return this.x;
}
}
Foo.Empty = class {};
/** @extends {Foo<string>} */
foo.Bar = class extends Foo {
/** @override */
method() {
return super.method() / 2;
}
};
/** @interface */
class Frobnicator {
/** @param {string} message */
frobnicate(message) {}
}

Function expressions

When declaring an anonymous function in the list of arguments for a function call, the body of the function is indented two spaces more than the preceding indentation depth.

Example:

prefix.something.reallyLongFunctionName('whatever', (a1, a2) => {
// Indent the function body +2 relative to indentation depth
// of the 'prefix' statement one line above.
if (a1.equals(a2)) {
someOtherLongFunctionName(a1);
} else {
andNowForSomethingCompletelyDifferent(a2.parrot);
}
});
some.reallyLongFunctionCall(arg1, arg2, arg3)
.thatsWrapped()
.then((result) => {
// Indent the function body +2 relative to the indentation depth
// of the '.then()' call.
if (result) {
result.use();
}
});

Switch statements

As with any other block, the contents of a switch block are indented +2.

After a switch label, a newline appears, and the indentation level is increased +2, exactly as if a block were being opened. An explicit block may be used if required by lexical scoping. The following switch label returns to the previous indentation level, as if a block had been closed.

A blank line is optional between a break and the following case.

Example:

switch (animal) {
case Animal.BANDERSNATCH:
handleBandersnatch();
break;
case Animal.JABBERWOCK:
handleJabberwock();
break;
default:
throw new Error('Unknown animal');
}

Statements

One statement per line

Each statement is followed by a line-break.

Semicolons are required

Every statement must be terminated with a semicolon. Relying on automatic semicolon insertion is forbidden.

Column limit: 80

JavaScript code has a column limit of 80 characters. Except as noted below, any line that would exceed this limit must be line-wrapped, as explained in Line-wrapping.

Exceptions:

  1. Lines where obeying the column limit is not possible (for example, a long URL in JSDoc or a shell command intended to be copied-and-pasted).

  2. goog.module and goog.require statements (see goog.module statement and goog.require statements).

Line-wrapping

Terminology Note: Line-wrapping is defined as breaking a single expression into multiple lines.

There is no comprehensive, deterministic formula showing exactly how to line-wrap in every situation. Very often there are several valid ways to line-wrap the same piece of code.

Note: While the typical reason for line-wrapping is to avoid overflowing the column limit, even code that would in fact fit within the column limit may be line-wrapped at the author's discretion.

Tip: Extracting a method or local variable may solve the problem without the need to line-wrap.

Where to break

The prime directive of line-wrapping is: prefer to break at a higher syntactic level.

Preferred:

currentEstimate =
calc(currentEstimate + x * currentEstimate) /
2.0f;

Discouraged:

currentEstimate = calc(currentEstimate + x *
currentEstimate) / 2.0f;

In the preceding example, the syntactic levels from highest to lowest are as follows: assignment, division, function call, parameters, number constant.

Operators are wrapped as follows:

  1. When a line is broken at an operator the break comes after the symbol. (Note that this is not the same practice used in Google style for Java.)

    1. This does not apply to the dot (.), which is not actually an operator.

  2. A method or constructor name stays attached to the open parenthesis (() that follows it.

  3. A comma (,) stays attached to the token that precedes it.

Note: The primary goal for line wrapping is to have clear code, not necessarily code that fits in the smallest number of lines.

Indent continuation lines at least +4 spaces

When line-wrapping, each line after the first (each continuation line) is indented at least +4 from the original line, unless it falls under the rules of block indentation.

When there are multiple continuation lines, indentation may be varied beyond +4 as appropriate. In general, continuation lines at a deeper syntactic level are indented by larger multiples of 4, and two lines use the same indentation level if and only if they begin with syntactically parallel elements.

Horizontal alignment: discouraged addresses the discouraged practice of using a variable number of spaces to align certain tokens with previous lines.

Whitespace

Vertical whitespace

A single blank line appears:

  1. Between consecutive methods in a class or object literal

    1. Exception: A blank line between two consecutive properties definitions in an object literal (with no other code between them) is optional. Such blank lines are used as needed to create logical groupings of fields.

  2. Within method bodies, sparingly to create logical groupings of statements. Blank lines at the start or end of a function body are not allowed.

  3. Optionally before the first or after the last method in a class or object literal (neither encouraged nor discouraged).

  4. As required by other sections of this document (e.g. 3.4 goog.require statements).

Multiple consecutive blank lines are permitted, but never required (nor encouraged).

Horizontal whitespace

Use of horizontal whitespace depends on location, and falls into three broad categories: leading (at the start of a line), trailing (at the end of a line), and internal. Leading whitespace (i.e., indentation) is addressed elsewhere. Trailing whitespace is forbidden.

Beyond where required by the language or other style rules, and apart from literals, comments, and JSDoc, a single internal ASCII space also appears in the following places only.

  1. Separating any reserved word (such as if, for, or catch) from an open parenthesis (() that follows it on that line.

  2. Separating any reserved word (such as else or catch) from a closing curly brace (}) that precedes it on that line.

  3. Before any open curly brace ({), with two exceptions:

    1. Before an object literal that is the first argument of a function or the first element in an array literal (e.g. foo({a: [{c: d}]})).

    2. In a template expansion, as it is forbidden by the language (e.g. abc${1 + 2}def).

  4. On both sides of any binary or ternary operator.

  5. After a comma (,) or semicolon (;). Note that spaces are never allowed before these characters.

  6. After the colon (:) in an object literal.

  7. On both sides of the double slash (//) that begins an end-of-line comment. Here, multiple spaces are allowed, but not required.

  8. After an open-JSDoc comment character and on both sides of close characters (e.g. for short-form type declarations or casts: this.foo = /** @type {number} */ (bar); or function(/** string */ foo) {).

Horizontal alignment: discouraged

Terminology Note: Horizontal alignment is the practice of adding a variable number of additional spaces in your code with the goal of making certain tokens appear directly below certain other tokens on previous lines.

This practice is permitted, but it is generally discouraged by Google Style. It is not even required to maintain horizontal alignment in places where it was already used.

Here is an example without alignment, followed by one with alignment. Both are allowed, but the latter is discouraged:

{
tiny: 42, // this is great
longer: 435, // this too
};
{
tiny: 42, // permitted, but future edits
longer: 435, // may leave it unaligned
};

Tip: Alignment can aid readability, but it creates problems for future maintenance. Consider a future change that needs to touch just one line. This change may leave the formerly-pleasing formatting mangled, and that is allowed. More often it prompts the coder (perhaps you) to adjust whitespace on nearby lines as well, possibly triggering a cascading series of reformattings. That one-line change now has a blast radius. This can at worst result in pointless busywork, but at best it still corrupts version history information, slows down reviewers and exacerbates merge conflicts.

Function arguments

Prefer to put all function arguments on the same line as the function name. If doing so would exceed the 80-column limit, the arguments must be line-wrapped in a readable way. To save space, you may wrap as close to 80 as possible, or put each argument on its own line to enhance readability. Indentation should be four spaces. Aligning to the parenthesis is allowed, but discouraged. Below are the most common patterns for argument wrapping:

// Arguments start on a new line, indented four spaces. Preferred when the
// arguments don't fit on the same line with the function name (or the keyword
// "function") but fit entirely on the second line. Works with very long
// function names, survives renaming without reindenting, low on space.
doSomething(
descriptiveArgumentOne, descriptiveArgumentTwo, descriptiveArgumentThree) {
// …
}
// If the argument list is longer, wrap at 80. Uses less vertical space,
// but violates the rectangle rule and is thus not recommended.
doSomething(veryDescriptiveArgumentNumberOne, veryDescriptiveArgumentTwo,
tableModelEventHandlerProxy, artichokeDescriptorAdapterIterator) {
// …
}
// Four-space, one argument per line. Works with long function names,
// survives renaming, and emphasizes each argument.
doSomething(
veryDescriptiveArgumentNumberOne,
veryDescriptiveArgumentTwo,
tableModelEventHandlerProxy,
artichokeDescriptorAdapterIterator) {
// …
}

Grouping parentheses: recommended

Optional grouping parentheses are omitted only when the author and reviewer agree that there is no reasonable chance that the code will be misinterpreted without them, nor would they have made the code easier to read. It is not reasonable to assume that every reader has the entire operator precedence table memorized.

Do not use unnecessary parentheses around the entire expression following delete, typeof, void, return, throw, case, in, of, or yield.

Parentheses are required for type casts: /** @type {!Foo} */ (foo).

Comments

This section addresses implementation comments. JSDoc is addressed separately in 7 JSDoc.

Block comment style

Block comments are indented at the same level as the surrounding code. They may be in /* … */ or //-style. For multi-line /* … */ comments, subsequent lines must start with * aligned with the * on the previous line, to make comments obvious with no extra context. “Parameter name” comments should appear after values whenever the value and method name do not sufficiently convey the meaning.

/*
* This is
* okay.
*/
// And so
// is this.
/* This is fine, too. */
someFunction(obviousParam, true /* shouldRender */, 'hello' /* name */);

Comments are not enclosed in boxes drawn with asterisks or other characters.

Do not use JSDoc (/** … */) for any of the above implementation comments


Full guide available here: Google JavaScript Style Guide

Live Preview

About this template

VIEW ALL

Coding can be a very personal practice. While there are fixed rules that need to be followed in order to make the product function correctly, developers are still left with a lot of flexibility and room to apply their personal preferences and habits.

But when you have to share your code with others, in the absence of clear coding guidelines, problems always arise. And the more people touch the source code, the harder it becomes to keep things consistent. Working out these contradictions can drastically slow down development.

All this makes it critical to sit together with your team and define what constitutes ‘quality code’. Creating a shared understanding of what quality code should be like helps new developers quickly get up to speed on a code base, and then write code that other developers can easily understand. Google offers a great example of what a code style guide should look like.

Originally published here: Google JavaScript Style Guide.

How to build your code style guide

The first step in thinking about a code style guide is to research the common standards. Don’t reinvent the wheel – many languages have a recommended style guide. Google style guides are widely used and could be a great starting point for your team. Simply copy it and use it as a template for your own code style guide, adapting it based on your workflow.

Your code style guide would only be useful if it's easy to discover and consult. Keep it somewhere accessible, such as in a company wiki – which can be easily set up in Nuclino. Keep your coding guidelines relevant and update them with all new decisions about standards and practices.

The style guide needs to be discussed with your team and evolved collaboratively – for example, during a developer's onboarding, when writing code, when writing tests, and during code review. In Nuclino, you can easily leave comments and @-mention your team members to provide feedback and discuss different aspects of your style guide.

You can find more examples of coding guidelines here: A curated list of high-quality coding style conventions and standards.

Related templates