Skip to main content

ES6 як найважливіше оновлення JS

ES6 (ECMAScript 2015) це версія стандарту, ухвалена в червні 2015 року, яка кардинально змінила мову. До неї JavaScript довгі роки не отримував великих оновлень: попередня помітна версія, ES5, вийшла ще у 2009 році. ES6 став тим рубежем, після якого JS перетворився з «мови для браузера» на повноцінну сучасну мову програмування.

Теорія

TL;DR

  • ES6 приніс сучасний синтаксис: let і const, стрілкові функції, шаблонні рядки, деструктуризацію, spread і rest, класи.
  • Уперше з'явилися офіційні модулі import / export, до того їх заміняли IIFE, CommonJS, AMD і RequireJS.
  • Promise зробив асинхронний код лінійним і став фундаментом для async/await з ES2017.
  • Додалися структури даних Map, Set, WeakMap, WeakSet і методи на кшталт Array.from() та Object.assign().
  • З'явилися Symbol, ітератори й генератори, тобто механіка, на якій тримаються for...of і сучасна асинхронність.
  • Разом це уніфікувало мову для браузера й сервера та відкрило дорогу збирачам, транспіляторам і фреймворкам.

Швидкий приклад

javascript
// math.js export const sum = (a, b) => a + b; // main.js import { sum } from './math.js'; const users = [{ name: 'Maria', age: 30 }]; const [{ name, age }] = users; console.log(`${name} is ${age}, sum = ${sum(2, 3)}`);

Новий синтаксис, наближений до сучасних мов

ES6 додав багато конструкцій, які зробили код зрозумілішим, коротшим і безпечнішим.

НововведенняЩо робитьПриклад
let / constБлокова область видимості замість varlet x = 10; const y = 20;
Стрілкові функціїКомпактний синтаксис, лексичний thisarr.map(x => x * 2)
Шаблонні рядкиЗручна інтерполяція і багаторядковість`Hello, ${name}!`
ДеструктуризаціяПросте витягання данихconst { name, age } = user;
Spread / RestГнучке об'єднання і розділенняconst all = [...arr1, ...arr2];
КласиСинтаксичний цукор над прототипамиclass User { constructor(name) {} }
Параметри за замовчуваннямПрибрали перевірки на undefinedfunction f(a, b = 1) {}

Окремо варто виділити let і const: вони прибрали найбільш болючу пастку var, коли змінна витікала з блоку, і зламали класичну задачу з var у циклі та setTimeout. Стрілкові функції зняли потребу в const self = this і в .bind(this).

Модулі import і export

До ES6 у JS не було стандартизованих модулів, доводилося використовувати:

  • IIFE, тобто функції, що викликають самі себе,
  • або зовнішні системи на кшталт CommonJS (Node.js), AMD чи RequireJS.

ES6 уперше ввів офіційну систему модулів:

javascript
// math.js export const sum = (a, b) => a + b; // main.js import { sum } from './math.js';

Це стало основою для сучасних інструментів: Webpack, Rollup, Vite, Parcel, Next.js і так далі. Важлива деталь: модулі ES6 статичні, тобто набір імпортів відомий до виконання. Саме тому збирачі вміють робити tree shaking і викидати невикористаний код, чого CommonJS з його динамічним require() не дозволяє.

Promise і кінець callback hell

До ES6 асинхронний код виглядав жахливо, це називали «callback hell»:

javascript
getData(function (res) { process(res, function (result) { save(result, function () { console.log('Done'); }); }); });

ES6 приніс Promise, а з ним лінійний і читабельний код:

javascript
getData() .then(process) .then(save) .then(() => console.log('Done'));

Проміси дали також єдиний спосіб обробки помилок через .catch() замість окремого аргументу err у кожному колбеку. Пізніше, в ES2017, на їхній основі з'явився синтаксис async/await, який працює поверх тих самих промісів.

Об'єкти, масиви, символи, ітератори й генератори

Розширені можливості об'єктів і масивів:

  • покращені літерали об'єктів: скорочений запис властивостей і методів, обчислювані ключі,
  • нові методи Array.from(), Array.of(), Object.assign(),
  • нові структури даних Map, Set, WeakMap, WeakSet.
javascript
const obj = { a: 1, b: 2 }; const copy = Object.assign({}, obj); const key = 'dynamic'; const built = { [key]: 1, copy };

Рівнем нижче лежить механіка самої мови:

  • Symbol це новий примітивний тип даних, зокрема для унікальних ключів і протоколів на кшталт Symbol.iterator,
  • Iterator і Generator це основа для for...of, yield і, зрештою, для async/await.
javascript
function* counter() { yield 1; yield 2; yield 3; } for (const num of counter()) console.log(num);

Уніфікація середовищ і підсумок

ES6 зробив мову універсальною: Node.js, браузери й фронтенд-фреймворки почали говорити однією мовою, з'явилися стандартизовані збирачі, транспілятори (Babel) і фреймворки (React, Vue, Angular), які спираються на модулі й класи зі стандарту.

ПричинаКоротко
Новий сучасний синтаксисЗробив JS зручним і безпечнішим
МодуліНавели лад у структурі проєктів
Асинхронність через PromiseПрибрала callback hell
Нові структури данихПідвищили ефективність і виразність
Уніфікація середовищJS став серйозною мовою і на фронтенді, і на бекенді

Простіше кажучи: до ES6 JavaScript сприймали як «іграшку для браузера», після ES6 це сучасна, потужна й зріла мова, що стоїть в одному ряду з Python, Java і C#.

Типові помилки

  • Вважати, що let і const не мають hoisting. Вони теж підіймаються, але потрапляють у temporal dead zone, тому звернення до них до оголошення кидає ReferenceError.
  • Плутати const з незмінністю. const забороняє перепризначення, але вміст об'єкта чи масиву змінювати можна; для незмінності потрібен Object.freeze() або структурне копіювання.
  • Використовувати стрілкову функцію як метод об'єкта чи конструктор. У неї немає власного this, arguments і prototype, тому new з нею не працює.
  • Плутати модулі ES6 з CommonJS. import статичний і асинхронний, require() синхронний; змішування двох систем в одному файлі дає помилки збірки.
  • Думати, що клас це нова модель успадкування. class це синтаксичний цукор над прототипами, під ним та сама прототипна модель.
  • Вважати, що Promise робить код паралельним. Він лише впорядковує асинхронність; для одночасних операцій потрібен Promise.all() чи Promise.allSettled().

Коротка відповідь

Для співбесіди
Premium

Коротка відповідь допоможе вам впевнено відповідати на цю тему під час співбесіди.