Top 5 ES6 Features Every JavaScript Developer Must Know

1. Default Parameters in ES6

Remember we had to do these statements to define default parameters:

var link = function (height, color, url) {
    var height = height || 50
    var color = color || 'red'
    var url = url || ''

They were okay until the value was 0 and because 0 is falsy in JavaScript it would default to the hard-coded value instead of becoming the value itself. Of course, who needs 0 as a value (#sarcasmfont), so we just ignored this flaw and used the logic OR anyway… No more! In ES6, we can put the default values right in the signature of the functions:

var link = function(height = 50, color = 'red', url = '') {

2. Template Literals in ES6

Template literals or interpolation in other languages is a way to output variables in the string. So in ES5 we had to break the string like this:

var name = 'Your name is ' + first + ' ' + last + '.'
var url = 'http://localhost:3000/api/messages/' + id

Luckily, in ES6 we can use a new syntax ${NAME} inside of the back-ticked string:

var name = `Your name is ${first} ${last}.`
var url = `http://localhost:3000/api/messages/${id}`

3. Multi-line Strings in ES6

Another yummy syntactic sugar is multi-line string. In ES5, we had to use one of these approaches:

var roadPoem = 'Then took the other, as just as fair,\n\t'
    + 'And having perhaps the better claim\n\t'
    + 'Because it was grassy and wanted wear,\n\t'
    + 'Though as for that the passing there\n\t'
    + 'Had worn them really about the same,\n\t'

var fourAgreements = 'You have the right to be you.\n\
    You can only be you when you do your best.'

While in ES6, simply utilize the backticks:

var roadPoem = `Then took the other, as just as fair,
    And having perhaps the better claim
    Because it was grassy and wanted wear,
    Though as for that the passing there
    Had worn them really about the same,`

var fourAgreements = `You have the right to be you.
    You can only be you when you do your best.`

4. Arrow Functions in ES6

This is probably one feature I waited the most. I love CoffeeScript for its fat arrows. Now we have them in ES6. The fat arrows are amazing because they would make your this behave properly, i.e., this will have the same value as in the context of the function—it won’t mutate. The mutation typically happens each time you create a closure.

Using arrows functions in ES6 allows us to stop using that = this or self = this or _this = this or .bind(this). For example, this code in ES5 is ugly:

var _this = this

This is the ES6 code without _this = this:

$('.btn').click((event) =>{

Sadly, the ES6 committee decided that having skinny arrows is too much of a good thing for us and they left us with a verbose old function instead. (Skinny arrow in CoffeeScript works like regular function in ES5 and ES6).

Here’s another example in which we use call to pass the context to the logUpperCase() function in ES5:

var logUpperCase = function() {
  var _this = this

  this.string = this.string.toUpperCase()
  return function () {
    return console.log(_this.string)
}{ string: 'es6 rocks' })()

While in ES6, we don’t need to mess around with _this:

var logUpperCase = function() {
  this.string = this.string.toUpperCase()
  return () => console.log(this.string)
}{ string: 'es6 rocks' })()

Note that you can mix and match old function with => in ES6 as you see fit. And when an arrow function is used with one line statement, it becomes an expression, i.e,. it will implicitly return the result of that single statement. If you have more than one line, then you’ll need to use return explicitly.

This ES5 code is creating an array from the messages array:

var ids = ['5632953c4e345e145fdf2df8','563295464e345e145fdf2df9']
var messages = (value) {
  return "ID is " + value // explicit return

Will become this in ES6:

var ids = ['5632953c4e345e145fdf2df8','563295464e345e145fdf2df9']
var messages = => `ID is ${value}`) // implicit return

Notice that I used the string templates? Another feature from CoffeeScript… I love them!

The parenthesis () are optional for single params in an arrow function signature. You need them when you use more than one param.

In ES5 the code has function with explicit return:

var ids = ['5632953c4e345e145fdf2df8', '563295464e345e145fdf2df9'];
var messages = (value, index, list) {
  return 'ID of ' + index + ' element is ' + value + ' ' // explicit return

And more eloquent version of the code in ES6 with parenthesis around params and implicit return:

var ids = ['5632953c4e345e145fdf2df8','563295464e345e145fdf2df9']
var messages =, index, list) => `ID of ${index} element is ${value} `) // implicit return

5. Classes in ES6

If you love object-oriented programming (OOP), then you’ll love this feature. It makes writing classes and inheriting from them as easy as liking a comment on Facebook.

Classes creation and usage in ES5 was a pain in the rear, because there wasn’t a keyword class (it was reserved but did nothing). In addition to that, lots of inheritance patterns like pseudo classical, classical, functional just added to the confusion, pouring gasoline on the fire of religious JavaScript wars.

I won’t show you how to write a class (yes, yes, there are classes, objects inherit from objects) in ES5, because there are many flavors. Let’s take a look at the ES6 example right away. I can tell you that the ES6 class will use prototypes, not the function factory approach. We have a class baseModel in which we can define a constructor and a getName() method:

class baseModel {
  constructor(options = {}, data = []) { // class constructor = 'Base'
    this.url = '' = data
    this.options = options

    getName() { // class method
      console.log(`Class name: ${}`)

Notice that I’m using default parameter values for options and data. Also, method names don’t need to have the word function or the colon (:) anymore. The other big difference is that you can’t assign properties this.NAME the same way as methods, i.e., you can’t say name at the same indentation level as a method. To set the value of a property, simply assign a value in the constructor.

The AccountModel inherits from baseModel with class NAME extends PARENT_NAME:

class AccountModel extends baseModel {
  constructor(options, data) {

To call the parent constructor, effortlessly invoke super() with params:

    super({private: true}, ['32113123123', '524214691']) //call the parent method with super = 'Account Model'
     this.url +='/accounts/'

If you want to be really fancy, you can set up a getter like this and accountsData will be a property:

 get accountsData() { //calculated attribute getter
    // ... make XHR

So how do you actually use this abracadabra? It’s as easy as tricking a three-year old into thinking Santa Claus is real:

let accounts = new AccountModel(5)
console.log('Data is %s', accounts.accountsData)

In case you’re wondering, the output is:

Class name: Account Model
Data is %s 32113123123,524214691