Download - ECMAScript 2015 Tips & Traps
![Page 1: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/1.jpg)
![Page 2: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/2.jpg)
ECMAScript 2015Tips & Traps
Adrian-Tudor Panescu
Iasi, November 2015
![Page 5: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/5.jpg)
5
![Page 6: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/6.jpg)
What’s all about?
● 500+ new features● Backwards-compatible● A much-awaited update (~6 years)● Hopefully the step to a yearly release cycle
6
![Page 7: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/7.jpg)
ES6 or ES2015?
https://twitter.com/JavaScriptDaily/status/662020174837583872
7
![Page 8: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/8.jpg)
Where are we?
Source: https://kangax.github.io/compat-table/es6/05.11.2015
8
![Page 10: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/10.jpg)
Where are we?
https://twitter.com/JavaScriptDaily/status/660074434821246976
10
![Page 11: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/11.jpg)
Where am I?
● Using ES2015 in production for ~year● 2nd presentation on ES2015 at CodeCamp● Reported Babel and ESLint bugs:
○ https://github.com/babel/babel/issues/2743○ https://github.com/eslint/eslint/issues/3364○ https://github.com/eslint/eslint/issues/3510
11
![Page 12: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/12.jpg)
Tip: arrow functions and this
function Ping() {
this.count = 1;
setInterval(function() {
this.count += 1;
}.bind(this), 16.6);
}
function Ping() {
this.count = 1;
setInterval(() => {
this.count += 1;
}, 16.6);
}
12
![Page 13: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/13.jpg)
Trap: arrow functions and arguments
function foo() {
console.log(arguments);
}
foo(1); // [1]
var foo = () => {
console.log(arguments);
}
foo(1); // ReferenceError
13
![Page 14: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/14.jpg)
Trap: arrow functions and arguments
● Use rest parameters: (...args) => args● Babel uses arguments from enclosing scope (?)
14
![Page 15: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/15.jpg)
Tip: Classes
class Foo {
constructor(bar) {
this.bar = bar;
}
baz() {
return 42;
}
}
var Foo = function(bar) {
this.bar = bar;
}
Foo.prototype.baz = function() {
return 42;
}
15
![Page 16: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/16.jpg)
Trap: forgetting about super()class Foo {
constructor(baz) {
this.baz = baz;
}
}
class Baz extends Foo {
constructor(baz) {
super(baz);
console.log(this.baz);
}
} 16
class Foo {
shout() {
console.log(‘foo!’);
}
}
class Baz extends Foo {
shout() {
super.shout();
console.log(‘baz!’);
}
}
![Page 17: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/17.jpg)
Tip: block scoping
function foo() {
for (var i = 0; i < 2; i++) {
var a = i;
}
console.log(a); // 1
}
function foo() {
for (var i = 0; i < 2; i++) {
let a = i;
}
console.log(a); // ReferenceError
}
17
![Page 18: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/18.jpg)
Trap: Temporal Dead Zone (TDZ)
{
console.log(x); // undefined
var x = ‘codecamp’;
}
{
console.log(x); // ReferenceError
let x = ‘codecamp’;
}
18
![Page 19: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/19.jpg)
Trap: Temporal Dead Zone (TDZ)
Section 13.3.1 in standard (sorry!):
let and const declarations define variables that are scoped to the running execution context’s LexicalEnvironment. The variables are created when their containing Lexical Environment is instantiated but may not be accessed in any way until the variable’s LexicalBinding is evaluated. [...]
19
![Page 20: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/20.jpg)
Trap: Temporal Dead Zone (TDZ)var _temporalUndefined = {};
var x = _temporalUndefined;
function _temporalAssertDefined(val, name, undef) {
if (val === undef) {
throw new ReferenceError(name + " is not defined - temporal dead zone");
}
return true;
}
console.log(_temporalAssertDefined(x, "x", _temporalUndefined) && x);
x = ‘codecamp’;
20Your performance-related concerns: http://kpdecker.github.io/six-speed/
![Page 21: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/21.jpg)
Tip: Iterators/ Generators and for...of
var a = [1, 3, 3, 7];
for (var e of a) {
console.log(e);
}
var a = [1, 3, 3, 7];
var l = a.length;
for (var i = 0; i < l; i++) {
console.log(a[i]);
}
21
![Page 22: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/22.jpg)
Trap: Iterators and constants
var a = [1, 3, 3, 7];
for (const e of a) {
console.log(e);
}
var a = [1, 3, 3, 7];
var l = a.length;
for (const i = 0; i < l; i++) {
console.log(a[i]);
}
22http://stackoverflow.com/questions/31987465/ecmascript-2015-const-in-for-loops
![Page 23: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/23.jpg)
Trap: Iterators and constants
for (const e of a) {
console.log(e);
}
const it = a[Symbol.iterator]();
let res;
while (res = it.next() && !res.done) {
const e = __res.value;
console.log(e);
}
23http://stackoverflow.com/questions/31987465/ecmascript-2015-const-in-for-loops
![Page 24: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/24.jpg)
Tip: Promises
xhr(‘https://foo.com/’
function(resp) {
readHTML(resp,
function(html) {},
function(err) {})
},
function(err) {}
);
xhr(‘https://foo.com/’)
.then(readHTML)
.then(function(html) {})
.catch(function(err) {});
24
![Page 25: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/25.jpg)
Tip: Promises
function xhr(url) {
return new Promise(function(resolve, reject) {
try {
// do some async work then...
resolve(data);
} catch(e) {
// if something goes wrong...
reject(e);
}
});
}25
![Page 26: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/26.jpg)
Trap: forgetting to return
xhr(‘https://foo.com/’)
.then((data) => {
readHTML(data);
})
.then((html) => {
console.log(html); // nope
}
.catch(console.error.bind(console));
xhr(‘https://foo.com/’)
.then((data) => {
return readHTML(data);
})
.then((html) => {
console.log(html); // okay
}
.catch(console.error.bind(console));
26
![Page 27: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/27.jpg)
Trap: passing a non-function to .then()
xhr(‘https://foo.com/’)
.then(readHTML())
.then((result) => {
// XHR response
});
xhr(‘https://foo.com/’)
.then(readHTML)
.then((result) => {
// HTML response
});
27
![Page 28: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/28.jpg)
Trap: .then(resolve, reject)
xhr(‘https://foo.com’)
.then(() => {
throw new ReferenceError;
}
.catch((err) => {
// never gonna give you up
console.log(err);
});
xhr(‘https://foo.com’)
.then(() => {
throw new ReferenceError;
},
(err) => {
// oblivious
console.log(err);
});
28
![Page 29: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/29.jpg)
Trap: Array.forEach vs. Promises
getURLs()
.then((urls) => {
return
urls.forEach(readHTML);
})
.then(() => {
console.log(‘all urls read?’);
})
.catch(console.error.bind(console));
getURLs()
.then((urls) => {
return
Promise.all(urls.map(readHTML);
})
.then(() => {
console.log(‘all urls read!’);
})
.catch(console.error.bind(console));
29
![Page 30: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/30.jpg)
Tip: Promise-driven architecture
function foo() {
return 42;
}
function foo() {
return Promise.resolve(42);
}
30
![Page 31: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/31.jpg)
Tip: Reflect.apply
a = [99, 111, 100, 101, 99, 97, 109, 112];
String.fromCharCode.apply(null, a);
String.fromCharCode.call(null, a[0], a[1]));
a = [99, 111, 100, 101, 99, 97, 109, 112];
Reflect.apply(String.fromCharCode, null, a);
31
![Page 32: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/32.jpg)
Trap: Reflect.apply expects an array
let a = [‘hello’, ‘world’]
Reflect.apply(
e => console.log(e), null, a);
let a = [‘hello’, ‘world’]
Reflect.apply(
e => console.log(e), null, [a]);
Reflect.apply(console.log, console, a);
32
![Page 33: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/33.jpg)
Tip: simple things
delete foo[‘bar’]
parseInt(‘1337’, 10)
Reflect.deleteProperty(foo, ‘bar’)
Number.parseInt(‘1337’, 10)
33
![Page 34: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/34.jpg)
Fin
● ECMAScript 2015 brings many nice features● Solves some of ES5’s strangeness
○ Hopefully we won’t have to revisit “The Good Parts”● Browsers should really start catching up
○ Babel is here to stay○ Transpilers will always have a performance handicap
● We had 5 ReferenceErrors
34
![Page 35: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/35.jpg)
● http://jsrocks.org/2015/01/temporal-dead-zone-tdz-demystified/
● https://stackoverflow.com/questions/31987465/ecmascript-2015-const-in-for-loops
● http://pouchdb.com/2015/05/18/we-have-a-problem-with-promises.html
Resources
35
![Page 36: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/36.jpg)
![Page 37: ECMAScript 2015 Tips & Traps](https://reader036.vdocuments.us/reader036/viewer/2022062306/58ee69f41a28abd0418b46cf/html5/thumbnails/37.jpg)
www.meetup.com/Iasi-JS/ www.meetup.com/Papers-We-Love-Iasi