About Javascript Best Practices, ECMAScript 5

2015/12/299 min read
bookmark this
Responsive image

Table of Contents

  1. Javascript render in the browser
  2. inline scripts
  3. external scripts
  4. deferred scripts
  5. event driven scripts
  6. dynamically loaded scripts
  7. With
  8. Javascript module patterns
  9. List of pattern of using module design patterns
  10. Inheritance by using module pattern
  11. sub module or module pattern with namespace
  12. New line at end of Javascript file
  13. .jshintrc
  14. Global
  15. Strict mode
  16. for
  17. javascript shortHand
  18. jQuery
  19. Types
  20. Objects
  21. Arrarys
  22. Declares
  23. Javasscript ShortCut
  24. Declare Functions
  25. Semicolons
  26. Name conventions
  27. Reserved Words
  28. HttpGet
  29. HttpPost

Following is about javascript ECMAScript 5.

Javascript render in the browser

It should be good that use external scripts by default and sometime inline scripts. Should avoid use event driven scripts or dynamically loaded scripts.

inline scripts

Some time we write inline script.


var inline = function(){
return "hi";
};

external scripts

But we should try to move all javascript as external js file.



deferred scripts

You might want to load javascript as delay which after page load.



event driven scripts

We should avoid use like this.

sample


dynamically loaded scripts

Also, should avoid load js like this too.

var head= document.getElementsByTagName('head')[0];
   var script= document.createElement('script');
   script.type= 'text/javascript';
   script.src= 'helper.js';
   head.appendChild(script);

With

Should avoid use With, see [MDN - With

//example use
//not good
with (document.head.style)
{
cssText = "test";
alignContent = "testContent";
}

// good
var headStyle = document.head.style;
headStyle.cssText = "test";
headStyle.alignContent = "testContent";

Javascript module patterns

Pattern #1 - revealing module pattern

I like this, because you'll get namespace of javascript, avoid global scope. Also, you will get encapsulation. In additional, I changed the minification for js that anything between START-UNITEST and END-UNITTEST will remove from javascript file. But when you reference it from your unit test file, you can call the method for your testing. The most important to me are, easy to see what's private, public, where's the function and variables.


// anonymous express function, which will execute immediately and any method inside this scope will contains privacy as closure.
var yourModule = (function($, _otherJs) {
var _private1 = function(){
return "hi";
};

var _private2 = function(number) {
return number * 10;
};

var _importantPrivate = function() {
// Doing crazy, important stuff.
};

// return module as public interface
return {
// START-UNITTEST
TEST1 : _importantPrivate,
// END-UNITTEST
calc1 : _private2,
get : _private1
};
// here you define what dependency module used at here
})(jQuery, otherJs);

List of pattern of using module design patterns

// Good
var myModule = (function(){

var _private = function(){
};

return {
 public : _private
};
})();
// Good
var myModule = (function(){

var _myModule = {};

var _private = function(){
};

_myModule.public = _private;

return _myModule;

})();
// Good
var myModule = (function(_myModule){

var _private = function(){
};

_myModule.public = _private;

return _myModule;

})(myModule);

or
// Good
(function(_myModule){

var _private = function(){
};

_myModule.public = _private;

return _myModule;

})(myModule);

or
// Good
var module = (function(_myModule){

var _private = function(){
};

_myModule.public = _private;

return _myModule;

})(module || {});

Following code is return everything at the end, it's hard to see the code and change or modulize the functions. I don't like doing in this way.

// Not good
(function() {
var _private = function() {
};

return {
public: function() {
 return "some logic";
},
public2 : function() {
 return "hi";
},
public 3 : function () {
},
// keep going with lots of more public method
}

})();

Inheritance by using module pattern

var firstModule = (function(){

var _private = function() {
return "hi";
};

return {
public : _private
};
})();

var overrideFirst = (function(_firstModule) {

var myOverrided = _firstModule;
myOverided.public = function() {
return "hello";
};

return myOverrided;
})(firstModule);

sub module or module pattern with namespace

I think this should be good for big organization to use as module patterns

// module.js
var module = (function()){
return {
};
})();

// module.child.js
module.child = (function()) {
return {};
})();

// module.child.son.js
module.child.son = (function()) {
return {};
})();

// module.child2.js
module.child2 = (function()) {
return {};
})();

New line at end of Javascript file

New Line Necessary

General reason is like following comment without new line, your javascript will break. But I think lots of bundling & minification library already handler this case. I wonder if there're any other case should use new Line.

asfda = "asdf"; // comment function method() {

.jshintrc

Global

avoid define as global in Javascript.

To avoid, i'm trying to use module pattern and closures.

// not good
// what's issue? so person A defined call() and will return 1000.
function call(){
// some work
return 1000;
}

// after load above script, let's assume your page load following script which use the same method name.
function call(){
// some work
return true;
}

// and this will return true.
call();

However, there're many ways.

// not good
// although you can define as namespace, but will be huge list and hard to see the code.
// and everything are accessiable.
var myModule = {
method1: function(){
return 1000;
},
method2: function(){
return true;
}
}

// not good
// this is use Revealing Module Pattern wich i use a lot and like it, but I don't like it return all the function at the end. It will end up hard to see at the last part and hard to differenitate what are public and private what could be move to shared location.
var myModule = function() {
var _private = {};
var _privateMethod = function(){
};

return {
   publicMethod : function(){
    return 1000;
   },
   publicMethod2 : function(){
    return true;
   }
}

}();

// good
var myModule = function($, otherSvc){
"use strict";
var _privateMethod = function(){
return 1000;
};

var _privateMethod2 = function(){
return true;
}

return {
public1 : _privateMethod,
public2 : _privateMethod2
};

}(jQuery, otherService);

// will return 1000;
console.info(myModule.public1);

Strict mode

Strict mode will check certain syntax error in javascript. I'll try to put the "use strict" first line of the module.

var myModule = function(){
"use strict";
var _privateMethod = function(){
return 1000;
};


return {
public1 : _privateMethod
};

}();

For more information about strict mode in javascript, you can reference following links.

mozilla - strict mode

w3c school - strict mode

http://cjihrig.com/blog/javascripts-strict-mode-and-why-you-should-use-it/

for

Foreach for arrary
array.forEach(function(item, i){

});


// one way
var list = [];
for (var i=0;i 1000);

javascript shortHand

 // before
var test;
if (condition) {
 test = true;
}
else {
 test = false;
}

// after
var test = (codition);

// before
// check Null, Undefined, Empty
var myStr2;
if (myStr !== null || myStr !== undefined || myStr !== '') {
myStr2 = myStr;
}

// after
var myStr2 = myStr || '';

// or
// before
if (myStr !== null || myStr !== undefined || myStr !== '') {
// do work
}

// after
if (myStr || '') {
// do work
}

// object arrary notation
// before, very old school way
var myArrary = new Arrary();
myArrary[0] = "1";
myArrary[1] = "a";

// after
var myArrary = ["1", "a"];

// or nother
var myArrary = new Arrary();
myArrary['test'] = "a";
myArrary['test1'] = "b";

// after
var myArrary = {
'test' : "a",
'test1' : "b"
}

// declare variable
// before
var a;
var b;
var c;

// after
var a,b, c;

// before
for (var i = 0; i < list.length; i++) {
}

// after
for (var i in list) {
}

// before
// get string's char
"string".charAt(0);

// after
"string"[0];

// short function calling
// before
if (condition) {
c_true();
}
else {
c_false();
}

// after
((condition) ? c_true : c_false)();

// switch statement
// before
switch (condition) {
case a:
 doA();
 break;
case b:
 doB();
 break;

}

// after
var switchCase = {
a: doA,
b: doB
};

if (switchCase[parameter]) {
  switchCase[parameter]();
}

// zero number
// before
var x = 10000000;

// after
var x = 1e7;

jQuery

// prefix with $
// not good
var name = $(".name");

// good
var $name = $(".name");

// cache jquery object, why? access DOM element is expensive
// not good
$(".name").hide();
$(".name").show();

// good
$name = $(".name");
$name.hide();
$name.show();

Types

String Number Boolean Arrary Object Undefined

Other - NaN is not a number, when you do "af" - "afs" will return NaN; Undefined type is Undefined; empty string "" is string type; null is Object type.

Objects

use {}following to create object.

// not good
var objectVar = new Object();
// good
var objectVar = {};

Arrarys

Use following syntax when deal with arrary.

// Use push to add value to arrary
var someList = [];
someList.push("hi");
someList.push("hello");
// console.info(someList); display -> ["hi", "hello"]

Declares

// better
// this way faster to load javascript, save few keystrokes, 'one'// var so better to read.
var myString = "",
myNumber = 0,
myArrary = [],
myObject = {},
myRegex =  /()/,
myFunction = function(){};

// or
var myString,
myNumber = 100;
myString = true;

// or
var myStr1 = "",
myNum = 0,
myDate;

// not good
var mystr1 = "";
var myStr2 = "";
var myNum1 = 0;
var myDate;

Javasscript ShortCut

// not good
var name = "";
if (name !== '')
{

}

// good
if (name)
{}

// not good
if (name.length > 0){
}

// good
if (name.length)
{
}

Declare Functions

// named function declaration
function testFunc(para1, para2) {
}

// call function
testFunc("test", "asfd");

// named function with call back
function testFunc(para1, callback) {
callback(para1);
}

// call function
testFunc("tefa", function(para1) {
}

// anonymous function expression
var test = function() {
return true;
}

// named function expression
var test = function test() {
retu
}

Semicolons

// safety, in case two self-invoking function have no semicolons.
;(function() {
// some logic.
})();

However, I'm still not sure should I use ! or ; to define module function.

!(function() {
'use strict';
// some logic.
})();

Name conventions

// private property us underscore
this._name = "name";

// define private this use underscore
var _this = this;

Reserved Words

Don't use reserved words, see Javascript Reserved words

HttpGet

Http Get - JSON Response
var request = new XMLHttpRequest();
request.open('GET', '/url', true);

request.onload = function() {
  if (request.status >= 200 && request.status < 400) {
    // Success!
    var data = JSON.parse(request.responseText);
  } else {
    // http status code not 200 and 300.
  }

  // more standard see -> https://xhr.spec.whatwg.org/
request.onerror = function() {
 };

request.send();
Http Get - Request
var request = new XMLHttpRequest();
request.open('GET', '/url', true);

request.onload = function() {
  if (request.status >= 200 && request.status < 400) {
    // Success!
    var data = request.responseText;
  } else {
   // http status code not 200 and 300.
  }
};

// more standard see -> https://xhr.spec.whatwg.org/
request.onerror = function() {

};

request.send();

More info about XMLHttpRequest

HttpPost

var request = new XMLHttpRequest();
request.open('POST', '/url', true);
request.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded; charset=UTF-8');
request.send(data);
References for Javascript - Reading

JavaScript Patterns

JavaScript Application Design: A Build First Approach

You don't need jQuery

Airbnb JavaScript Style Guide

all Http Status Code Definition

All Http Method Definitions

JSHint](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/with)

JSLint

JSPerf JavaScript performance playground

Annotated ES5

JavascriptJavascript

Mozilla - Javascript

Javascript es5 - Compatibility table

JS: The Right Way

google Javascript Style Guide

Javascript Standard

Javascript idiomaticPrinciples of Writing Consistent, Idiomatic JavaScript

ECMAScript5 Official Document (PDF)

References for Javascript - Reading
  • EditorConfig maintain consistent coding styles

confusing, bugs