- 10 Practical JavaScript Tricks
- Intro to Functional JavaScript
- Closures : Counter Using Functional Approach in Javascript
- The best Javascript features since ES6
- Recursion : Recursion in JavaScript with ES6, destructuring and rest/spread
- Recursion : Impress interviewers with recursion in JavaScript with ES6 features
ES6
Affectations déstructurées
var httpOptions = { timeout: 2000, isCache: true };
// ES5 :
var httpTimeout = httpOptions.timeout;
var httpCache = httpOptions.isCache;
// ES6 :
const { timeout: httpTimeout, isCache: httpCache } = httpOptions;
// or
const { timeout, isCache } = httpOptions;
// you now have a variable named 'timeout' and one named 'isCache' with correct values
avec des objets imbriqués :
const httpOptions = { timeout: 2000, cache: { age: 2 } };
// later
const { cache: { age } } = httpOptions;
// you now have a variable named 'age' with value 2
avec des tableaux :
const timeouts = [1000, 2000, 3000];
// later
const [shortTimeout, mediumTimeout] = timeouts;
// you now have a variable named 'shortTimeout' with value 1000
// and a variable named 'mediumTimeout' with value 2000
avec des fonctions :
function randomPonyInRace() {
const pony = { name: 'Rainbow Dash' };
const position = 2;
// ...
return { pony, position };
}
const { position, pony } = randomPonyInRace();
// ou
const { pony } = randomPonyInRace();
Paramètres optionnels et valeurs par défaut
function getPonies(size, page) {
size = size || 10;
page = page || 1;
// ...
server.get(size, page);
}
ou
function getPonies(size = 10, page = 1) {
// ...
server.get(size, page);
}
avec appel de fonction :
function getPonies(size = defaultSize(), page = size - 1) {
// if page is not provided, it will be set to the value
// of the size parameter minus one.
// ...
server.get(size, page);
}
avec une affectation déstructurée :
const { timeout = 1000 } = httpOptions;
Rest Operator
function addPonies(...ponies) {
for (let pony of ponies) {
poniesInRace.push(pony);
}
}
const [winner, ...losers] = poniesInRace;
// assuming 'poniesInRace' is an array containing several ponies
// 'winner' will have the first pony,
// and 'losers' will be an array of the other ones
const ponyPrices = [12, 3, 4];
const minPrice = Math.min(...ponyPrices);
Classes
class Pony {
get color() {
console.log('get color');
return this._color;
}
set color(newColor) {
console.log(`set color ${newColor}`);
this._color = newColor;
}
static defaultSpeed() {
return 10;
}
}
const pony = new Pony();
pony.color = 'red';
// 'set color red'
console.log(pony.color);
// 'get color' (red')
Héritage
class Animal {
speed() {
return 10;
}
}
class Pony extends Animal {
speed() {
return super.speed() + 10;
}
}
const pony = new Pony();
console.log(pony.speed()); // 20, as Pony overrides the parent method
class Animal {
constructor(speed) {
this.speed = speed;
}
}
class Pony extends Animal {
constructor(speed, color) {
super(speed);
this.color = color;
}
}
const pony = new Pony(20, 'blue');
console.log(pony.speed); // 20
Promises
getUser(login)
.then(function (user) {
return getRights(user);
})
.then(function (rights) {
updateMenu(rights);
})
Une promise a trois états :
- pending (« en cours ») : quand la promise n’est pas réalisée
par exemple quand l’appel serveur n’est pas encore terminé. - fulfilled (« réalisée ») : quand la promise s’est réalisée avec succès
par exemple quand l’appel HTTP serveur a retourné un status 200-OK. - rejected (« rejetée ») : quand la promise a échoué
par exemple si l’appel HTTP serveur a retourné un status 404-NotFound.
const getUser = function (login) {
return new Promise(function (resolve, reject) {
// async stuff, like fetching users from server, returning a response
if (response.status === 200) {
resolve(response.data);
} else {
reject('No user');
}
});
};
Une gestion d’erreur par promise :
getUser(login)
.then(function (user) {
return getRights(user);
}, function (error) {
console.log(error); // will be called if getUser fails
return Promise.reject(error);
})
.then(function (rights) {
return updateMenu(rights);
}, function (error) {
console.log(error); // will be called if getRights fails
return Promise.reject(error);
})
Une gestion d’erreur globale pour toute la chaîne :
getUser(login)
.then(function (user) {
return getRights(user);
})
.then(function (rights) {
return updateMenu(rights);
})
.catch(function (error) {
console.log(error); // will be called if getUser or getRights fails
})
arrow functions
getUser(login)
// ES5
.then(function (user) {
return getRights(user); // getRights is returning a promise
})
.then(function (rights) {
return updateMenu(rights);
})
// ES6
.then(user => getRights(user))
.then(rights => updateMenu(rights))
Le return est implicite s’il n’y a pas de bloc : pas besoin d’écrire user ⇒ return getRights(user).
les arrow functions ont une particularité bien agréable que n’ont pas les fonctions normales : le this reste attaché lexicalement, ce qui signifie que ces arrow functions n’ont pas un nouveau this comme les fonctions normales :
var maxFinder = {
max: 0,
find: function (numbers) {
// ES5
numbers.forEach(
function (element) {
if (element > this.max) {
this.max = element;
}
}, this); // on doit passer le this en second paramètre
// ES6
numbers.forEach(element => {
if (element > this.max) {
this.max = element;
}
});
}
};
maxFinder.find([2, 3, 4]);
// log the result
console.log(maxFinder.max);
Collections
Map
const cedric = { id: 1, name: 'Cedric' };
const users = new Map();
users.set(cedric.id, cedric); // adds a user
console.log(users.has(cedric.id)); // true
console.log(users.size); // 1
users.delete(cedric.id); // removes the user
Set
const cedric = { id: 1, name: 'Cedric' };
const users = new Set();
users.add(cedric); // adds a user
console.log(users.has(cedric)); // true
console.log(users.size); // 1
users.delete(cedric); // removes the user
for…of
for (let user of users) {
console.log(user.name);
}
Template de string
// ES5
const fullname = 'Miss ' + firstname + ' ' + lastname;
// ES6
const fullname = `Miss ${firstname} ${lastname}`;
Modules
Dans races_service.js :
export function bet(race, pony) { ... }
export function start(race) { ... }
Dans un autre fichier :
import { bet, start } from './races_service';
// later
bet(race, pony1);
start(race);
// import avec alias
import { start as startRace } from './races_service';
// tout importer
import * as racesService from './races_service';
// default :
// pony.js
export default class Pony {}
// races_service.js
import Pony from './pony';