The purpose of this is not to be an exhaustive list or a reference for ES6 features. This is intended to share the interesting ideas that are coming down the pipeline and to explore their intentions.
- String methods
- Variable type declarations
- Object features
- Function features
- Classes
- Working Interatively
- Promises
- Modules
- Other neat new features
- References
String.includes() // Anywhere within string
String.startsWith() // does it start with ...
String.endsWith() // does it end with ...var versus let: let is not the new var. This has been said by many of the leading engineers within our community. let was not intended to replace var, but to complement it when block scope is important.
/**********************
* Old way: IIFE were needed to "snapshot" values at time of iteration
*/
for (var i = 0; i < arr.length; i++) {
(asyncFunction(arr[i], function callback(error, data) {
arr[i] = data.value;
}(i)); // This is necessary to capture the value of i at iteration
}
/**********************
* ES6 way
*
* With let, the value at iteration is preserved since
* a new i is created for each cycle
*/
for (let i = 0; i < arr.length; i++) {
asyncFunction(arr[i], function callback(error, data) {
arr[i] = data.value;
};
}
// Be aware: access a let before it's initialized errs out
if (true) {
console.log(name); // ReferenceError!
let name = 'Justin';
} else {
let name = 'James';
}/**********************
* Old way
*/
var PI = 3.14;
PI = 7; // altered
/**********************
* ES6 way
*/
const PI = 3.14;
PI = 7; // throws errorfunction (greeting, name) {
// properties and method are placed without keys
var obj = {
greeting,
name,
sayHello () {
console.log(greeting + ', ' + name + '!');
}
}
return obj;
};Destructuring works in parameters as well as vars and lets. Parameters are the most interesting to me
/**********************
* Old way
*/
function func(obj) {
// Manually destructure object into vars
var color: obj.color,
size: obj.size;
console.log(color); // "red"
console.log(size); // "large"
}
func({
color: "red",
size: "large",
quantity: 5
});
/**********************
* ES6 way
*/
function func({color, size}) {
console.log(color); // "red"
console.log(size); // "large"
}
func({
color: "red",
size: "large",
quantity: 5
});/**********************
* Old way
*/
function func(type, color, size) {
var type = type || "t-shirt",
color = color || "black",
size = size || "large";
console.log(type); // "hoodie"
console.log(color); // "red"
console.log(size); // "large"
}
func("hoodie", null); // for any falsey value, the default will be assigned
/**********************
* ES6 way
*/
function func(type = "t-shirt", color = "black", size = "large") {
console.log(type); // "hoodie"
console.log(color); // null <-- surprised?
console.log(size); // large
}
func("hoodie", null); // only the absence of a value will set a default/**********************
* Old way
*/
function func(user) {
var i = 1; // skip zeroth
// Have to access the arguments function to grab the unknown items
// Have to skip zeroth index to not iterate over the user parameter
for (i; i < arguments.length; i++) {
console.log(arguments[i]); // "SD9G876S98FG", "S9DF7SD98F7", "SDS0G87H8977H"
}
}
func("jlowery", "SD9G876S98FG", "S9DF7SD98F7", "SDS0G87H8977H");
/**********************
* ES6 way
*/
function func(user, ...items) {
for (let i = 0; i < items.length; i++) {
console.log(items[i]); // "SD9G876S98FG", "S9DF7SD98F7", "SDS0G87H8977H"
}
}
func("jlowery", "SD9G876S98FG", "S9DF7SD98F7", "SDS0G87H8977H");var addTwo = (a, b) => a + b;
addTwo(2, 4); // 6
/**********************
* What's interesting is ...
*/
var api = {
el: document.getElementById('listItem'),
bindListener: () => {
this.el.addEventListener('click', () => {
this.clickAction(el); // `this` is api
});
},
clickAction: (el) => {
// logic
}
};
/**********************
* ... replaces ...
*/
var api = {
el: document.getElementById('listItem'),
bindListener: function () {
var that = this;
this.el.addEventListener('click', function () {
that.clickAction(el); // `that` is api because `this` would be global
});
},
clickAction: function (el) {
// logic
}
};
// There's more to arrow functions than what's above, so go explore./**********************
* Realy old way: the constructor/prototype pattern
*/
function Mammal () {
this.gestation = 'placental';
this.food_source = 'mammaries';
}
Mammal.prototype.gestation = function () {
console.log('Gestation is ' + this.gestation);
}
Mammal.prototype.feed = function () {
console.log('Feeding happens through the ' + this.food_source);
}
var cat = new Mammal('placental', 'mammaries');
/**********************
* Better new'ish way: Object.create() and behavior delegation
*/
var actions = {
init: function (gestation, food_source) {
this.gestation = gestation;
this.food_source = food_source;
},
gestation: function () {
console.log('Gestation is ' + this.gestation);
},
feed: function () {
console.log('Feeding happens through the ' + this.food_source);
}
};
var Cat = Object.create(actions);
Cat.init('placental', 'mammaries');
/**********************
* ES6 way: Classes (somewhat contraversial)
*/
class Mammal {
constuctor(gestation, food_source) {
this.gestation = gestation;
this.food_source = food_source;
}
gestation() {
console.log('Gestation is ' + this.gestation);
}
feed() {
console.log('Feeding happens through the ' + this.food_source);
}
}
var cat = new Mammal('placental', 'mammaries');// Using the Mammel class above
class Dog extends Mammal {
vocalize() {
console.log('bark');
}
}// Create iterator
var iteratorMachine = function (arr) {
var i = 0;
return {
callNext: function () {
return {
value: arr[i++],
done: i >= arr.length ? true : false;
}
}
}
};
/**********************
* Old way
*/
var oldIterate = iteratorMachine([1, 2, 3]);
oldIterate.callNext(); // { value: 1, done: false }
oldIterate.callNext(); // { value: 2, done: false }
oldIterate.callNext(); // { value: 3, done: false }
oldIterate.callNext(); // { value: undefined, done: true }
oldIterate.callNext(); // will keep going and going
/**********************
* ES6 way
*/
var es6Iterate = iteratorMachine([1, 2, 3]);
for (let item of es6Iterate) {
console.log(item);
}
// for-in will print out the value property of the returned object
$ 1
$ 2
$ 3
// for-in stops when the done property is truefunction *myGenerator(arr) {
for (let i = 0; i < arr.length; i++) {
yeild arr[i];
}
}
var iterator = myGenerator([1, 2, 3]);
for (let item in iterator) {
console.log(item);
}
$ 1
$ 2
$ 3function asyncRequest(url, verb) {
return new Promise(
function (resolve, reject) {
request(verb, url, function (error, response, body) {
if (request.statusCode === 200) {
// Success
resolve(response);
} else {
// error
reject(new Error(response));
}
}
});
}
asyncRequest('http://paypal.com/users/profile', 'GET').
then(
// Success method
function (response) {
console.log(response);
},
// Error method
function (response) {
console.log(response);
}
);/**********************
* Old way: AMD
*/
require('myComponent', function (myComponent) {
myComonent.init();
});
/**********************
* ES6 way: Modules
*/
import myComponent from 'lib/myComponent';
myComponent.init();- Map, set, weakmap, weakset
- Module loaders
- Proxies
- Template strings
- Super
- Nicholas Zakas: https://github.com/nzakas/understandinges6
- Dr. Axel Rauschmayer: http://www.2ality.com/2014/08/es6-today.html
- Luke Hoban: https://github.com/lukehoban/es6features
Object.assignis also awesome. (essentially_.extend)