0%

ecma-script-version-history

ES5

strict mode

1
"use strict";

JSON

1
2
3
const obj = { a: 1, b: 2, c: 3 };
const json = JSON.stringify(obj);
console.log(json); // {"a":1,"b":2,"c":3}

New array methods:

  • forEach
  • map
  • filter
  • reduce
  • reduceRight

Property getters and setters

1
2
3
4
5
6
7
8
9
10
11
const obj = {
get a() {
return this._a;
},
set a(value) {
this._a = value;
}
};

obj.a = 1;
console.log(obj.a); // 1

Function binding: bind

1
2
3
4
function foo() {
console.log(this);
}
foo.bind({ a: 1 });

ES6(ECMAScript 2015)

ES7(ECMAScript 2016)

Array.prototype.includes

1
2
const arr = [1, 2, 3];
console.log(arr.includes(2)); // true

Exponentiation Operator

1
console.log(2 ** 3); // 8

ES8(ECMAScript 2017)

Object.values

1
2
const obj = { a: 1, b: 2, c: 3 };
console.log(Object.values(obj)); // [1, 2, 3]

Object.entries

1
2
const obj = { a: 1, b: 2, c: 3 };
console.log(Object.entries(obj)); // [["a", 1], ["b", 2], ["c", 3]]

Object.getOwnPropertyDescriptors

1
2
3
4
5
6
7
const obj = { a: 1, b: 2, c: 3 };
console.log(Object.getOwnPropertyDescriptors(obj));
// {
// a: { value: 1, writable: true, enumerable: true, configurable: true },
// b: { value: 2, writable: true, enumerable: true, configurable: true },
// c: { value: 3, writable: true, enumerable: true, configurable: true }
// }

String padding

1
2
console.log("hello".padStart(10, "123")); // 12312hello
console.log("hello".padEnd(10, "123")); // hello12312

Trailing commas in function parameter lists and calls

1
2
3
4
function foo(a, b, c,) {
console.log(a, b, c);
}
foo(1, 2, 3);

ES9(ECMAScript 2018)

Asynchronous Iteration

ES10(ECMAScript 2019)

Array.prototype.flat()

1
2
const arr = [1, 2, [3, 4, [5, 6]]];
console.log(arr.flat()); // [1, 2, 3, 4, [5, 6]]

Array.prototype.flatMap()

1
2
3
const arr = [1, 2, 3];
console.log(arr.map(x => [x * 2])); // [[2], [4], [6]]
console.log(arr.flatMap(x => [x * 2])); // [2, 4, 6]

Object.fromEntries()

1
2
3
const obj = { a: 1, b: 2, c: 3 };
console.log(Object.entries(obj)); // [["a", 1], ["b", 2], ["c", 3]]
console.log(Object.fromEntries(Object.entries(obj))); // { a: 1, b: 2, c: 3 }

String.prototype.trimStart() and String.prototype.trimEnd()

1
2
3
const str = "  hello  ";
console.log(str.trimStart()); // "hello "
console.log(str.trimEnd()); // " hello"

Optional Catch Binding

1
2
3
4
5
try {
throw new Error("error");
} catch {
console.log("caught");
}

JSON.stringify() replacer parameter

The second arguments [“a”, “b”] is a replacer array, which specifies the properties to include in the JSON string.

1
2
const obj = { a: 1, b: 2, c: 3 };
console.log(JSON.stringify(obj, ["a", "b"])); // {"a":1,"b":2}

JSON.stringify() space parameter

The third argument 2 is a space parameter, which specifies the number of spaces to use for indentation.

1
2
3
4
5
6
7
const obj = { a: 1, b: 2, c: 3 };
console.log(JSON.stringify(obj, null, 2));
// {
// "a": 1,
// "b": 2,
// "c": 3
// }

The output is {"a":1,"b":2,"c":3} without the third argument.

ES11(ECMAScript 2020)

BigInt

1
2
3
4
5
const max = Number.MAX_SAFE_INTEGER;
console.log(max); // 9007199254740991
console.log(max + 1); // 9007199254740992
console.log(max + 2); // 9007199254740992
console.log(max + 3n); // 9007199254740994n

Dynamic import

1
const module = await import('./module.js');

Optional chaining operator (?.)

1
2
const obj = { a: { b: { c: 1 } } };
console.log(obj.a?.b?.c); // 1

Nullish coalescing operator (??)

  • leftExpr ?? rightExpr, this expression will return its right-hand side operand when the left-hand side operand is null or undefined. Otherwise, it will return its left-hand side operand.
  • leftExpr || rightExpr, return true if and only if one of the operands is true. Otherwise return false.
1
2
3
4
5
6
7
8
9
const obj = { a: 0, b: "", c: null, d: undefined };
console.log(obj.a || "default"); // default
console.log(obj.b || "default"); // default
console.log(obj.c || "default"); // default
console.log(obj.d || "default"); // default
console.log(obj.a ?? "default"); // 0
console.log(obj.b ?? "default"); // ""(empty string)
console.log(obj.c ?? "default"); // default
console.log(obj.d ?? "default"); // default

Promise.allSettled()

1
2
3
4
5
6
7
8
const promise1 = new Promise((resolve, reject) => setTimeout(resolve, 1000));
const promise2 = new Promise((resolve, reject) => setTimeout(reject, 1000));
Promise.allSettled([promise1, promise2])
.then(results => console.log(results));
// [
// { status: "fulfilled", value: undefined },
// { status: "rejected", reason: undefined }
// ]

globalThis

1
console.log(globalThis);

String.prototype.matchAll()

1
2
3
4
5
6
const str = "hello world";
const regex = /\w+/g;
const matches = str.matchAll(regex);
for (const match of matches) {
console.log(match);
}

ES12(ECMAScript 2021)

Numeric separators

1
2
const num = 1_000_000;
console.log(num); // 1000000

String.prototype.replaceAll()

1
2
const str = "hello world";
console.log(str.replaceAll("o", "0")); // hell0 w0rld

Promise.any()

1
2
3
4
const promise1 = new Promise((resolve, reject) => setTimeout(reject, 1000));
const promise2 = new Promise((resolve, reject) => setTimeout(resolve, 500));
Promise.any([promise1, promise2])
.then(value => console.log(value));

WeakRef

1
2
3
4
let obj = { name: "John" };
const weakRef = new WeakRef(obj);
obj = null;
console.log(weakRef.deref()); // { name: "John" }

FinalizationRegistry

1
2
3
4
let obj = { name: "John" };
const finalizationRegistry = new FinalizationRegistry(key => console.log(key));
finalizationRegistry.register(obj, "custom key");
obj = null;

ES13(ECMAScript 2022)

Top-level await

Private instance fields, methods, and accessors

Static class fields and methods

Static class initialization blocks

Error.cause

Array, String, and TypedArray .at() method

Object.hasOwn()

The Object.hasOwn() static method returns true if the specified object has the indicated property as its own property. If the property is inherited, or does not exist, the method returns false.

1
2
3
4
const obj = { a: 1};
console.log(Object.hasOwn(obj, "a")); // true
console.log(Object.hasOwn(obj, "b")); // false
console.log(Object.hasOwn(obj, "toString")); // false

Object.hasOwn is intended as a replacement of Object.prototype.hasOwnProperty.

RegExp match /d flag

References: