JavaScript Styleguide - HelixDesignSystem/helix-ui GitHub Wiki

ES6+

You have access to modern JavaScript language features, because we use webpack/rollup + babel to compile assets to ES2015/ES5 syntax.

Alphabetize whenever possible

To ensure that definitions are defined in a logical way, take every opportunity to arrange definitions alphanumerically, based on ASCII character values (excluding surrounding syntax) whenever possible.

  • $observedAttributes
  • case statements within a switch structure
  • method and property names

👍 Do


class Foobar {
  static get $observedAttributes () {
    return [
      'another-thing',
      'bang', 
      'bar', 
      'foo',
      'foo-bar', 
    ];
  }

  $onAttributeChange (attr, oldVal, newVal) { 
    switch (attr) {
      case 'another-thing': /* ... */ break;
      case 'bang': /* ... */ break;
      case 'bar': /* ... */ break;
      case 'foo': /* ... */ break;
    }
  }

  get anotherThing () { ... }
  get bang () { ... }
  get bar () { ... }
  get foo () { ... }
}

👎 Don't

class Foobar {
  static get $observedAttributes () {
    return [
      'foo-bar',
      'foo',
      'bar', 
      'bang', 
      'another-thing',
    ];
  }

  $onAttributeChange (attr, oldVal, newVal) { 
    switch (attr) {
      case 'foo': /* ... */ break;
      case 'bar': /* ... */ break;
      case 'bang': /* ... */ break;
      case 'another-thing': /* ... */ break;
    }
  }

  get foo () { ... }
  get bar () { ... }
  get bang () { ... }
  get anotherThing () { ... }
}

Element Class Structure

Element definitions should be organized in a way that places the most important information as close to the top of the file as possible.

Please adhere to the following ordering:

  1. static get is ()
  2. static get template () (optional)
  3. $onCreate ()
  4. $onConnect ()
  5. $onDisconnect ()
  6. static get $observedAttributes ()
  7. $onAttributeChange ()
  8. PUBLIC members*
    1. properties
      • alphabetical
      • getter before setter
      • do not separate getter and setter
    2. methods
  9. PRIVATE members*
    1. properties
    2. methods
  10. DEPRECATED members*
    1. properties
    2. methods

* All members should be organized alphabetically

ESLint

⚠️ Section needs revision

Using ESLint

ESLint is a tool for identifying and reporting on patterns found in ECMAScript/JavaScript code, with the goal of making code more consistent and avoiding bugs.

# install 
yarn install

# check everything in the helix project
yarn run lint

Rules

Avoiding Errors

Bitwise Operators

Never use bitwise operators. (no-bitwise)

Semicolons

Never exclude optional semicolons. (semi)

Variable Hoisting

Never depend on variable hoisting. (no-use-before-define)

Function Hoisting

Function hoisting is allowed (and also necessary for custom element class definitions).

Nesting Depth

Code should not be nested more than 3 levels. This reduces the possibility that logic would exceed maximum cyclomatic complexity. (max-depth)

Naming Conventions

Constants

Constants should be named using UPPERCASE_SNAKE_CASE format.

lowerCamelCase Member Names

Variables, properties, and non-constructor functions should be named using lowerCamelCase format. (camelcase)

Private Member Names

Private members should be named with an underscore prefix to denote that they are meant only to be used internally.

Do

this._doSomething = function () { /* ... */ }
this._elFoo = document.getElementById('foo');

Don't

this.doSomething = function () { /* ... */ }
this.elFoo = document.getElementById('foo');

Capitalized Constructors

Contructor functions and ES6 classes should be named using UpperCamelCase format. (new-cap)

Stylistic Conventions

Indentation

  • Use 4 spaces per indentation. Never use tabs.
  • Always indent case statements inside switch logic.

(indent)

Line Length

Line length should not exceed 120 characters. However, it is highly recommended that line length not exceed 80 characters. (max-len)

One True Brace Style

Follow the one true brace style (1TBS)

Strings

  • Use single-quoted strings for simple values.
  • Use template literals (backtick strings) for complex values.
    • Multi-line strings
    • Strings containing quotes (double-quotes or single-quotes)
    • Strings with variables (variable interpolation

Do

return 'Simple string with no variable interpolation';
return `String with 'single-quoted content'`;
return `String with "double-quoted content"`;
return `
  Template literal with ${variable} interpolation, 
  'single-quoted content', 
  and "double-quoted content"
`;

Don't

return "Any Double-quoted string";
return 'Single-quoted string with "double-quoted" content';
return 'mix-quoted strings with ' + variable + " injection";
return `Simple value template literal`;

Space Inside Parens

Never add space around inside of parens. (space-in-parens)

Space Before Function Paren

Always add a space before function paren. (space-before-function-paren)

Space Around Infix Operators

Always add space around infix operators. (space-infix-ops)

Space Around Keywords

Always add space around keywords. (keyword-spacing)

Space Around Unary Operators

Always add space around unary operators. (space-unary-ops)

Space Inside Curly Braces

Always add space around inside of curly braces. (object-curly-spacing)

Max Consecutive Blank Lines

No more than one blank line between statements. (no-multiple-empty-lines)

Dangling Comma

Always add dangling comma after last array item and last object property. (comma-dangle)

Comma Style

Never use leading commas in lists and objects. Always use trailing commas. (comma-style)