- react
- vue
- angular
- solid
- lit
📰 3 mars
📰 15 mars
📰 15 mars
Plugins
Domains
Multi file analysis
...
(no-floating-promise)
📰 24 mars
Node
Deno
Bun
Bare ?
📰 7 avril
📰 23 avril
// Disposables && using syntax:
function create(data: string) {
console.log(`creating disposable object with data ${data}`);
return {
data: data,
[Symbol.dispose]() {
console.log(`disposing disposable object with data ${data}`);
},
}
}
function main() {
using data1 = create("first");
using data2 = create("second");
console.log(`using ${data1.data} and ${data2.data}`);
}
console.log("before main");
main();
console.log("after main");
// before main
// creating disposable object with data first
// creating disposable object with data second
// using first and second
// disposing disposable object with data second
// disposing disposable object with data first
// after main
try {
throw "Oops; this is not an Error object";
} catch (e) {
if (!Error.isError(e)) {
e = new Error(e);
}
console.error(e.message);
}
Error.isError
- A new static method to check if a value is an Error objectconst pattern = new URLPattern("https://example.com/2022/feb/*");
console.log(pattern.test("https://example.com/2022/feb/xc44rsz")); // true
console.log(pattern.test("https://example.com/2022/Feb/xc44rsz")); // false
AsyncLocalStorage defaults to AsyncContextFrame
URLPattern
as a Global
Undici 7.0.0
Permission Model Improvements
Test Runner Enhancements
V8 v13.4
📰 en juin
type AsyncNegator = (val: number) => number | Promise<number>;
function subtract(a: number, b: number, negate: AsyncNegator): Promise<number> {
return Promise.try(() => negate(b)).then(negB => a + negB);
}
ES2025
type AsyncNegator = (val: number) => number | Promise<number>;
function subtract(a: number, b: number, negate: AsyncNegator): Promise<number> {
return Promise.resolve(negate(b)).then(negB => a + negB);
}
const damnedRegex = /(?<year>[0-9]{4})-[0-9]{2}|[0-9]{2}-(?<year>[0-9]{4})/
// Impossible avant ES2025 d'utiliser <year> 2 fois
ES2025
const RE_DATE = /(?<year>[0-9]{4})-(?<month>[0-9]{2})-(?<day>[0-9]{2})/
const {groups: {day, month, year}} = RE_DATE.exec('1999-12-31')
const myFruits = new Set(['🍎', '🍐', '🥝'])
const yourFruits = new Set(['🥥', '🍐', '🫒'])
myFruits.intersection(yourFruits) // 🍐
myFruits.union(yourFruits) // 🍎, 🍐, 🥝, 🥥, 🫒
myFruits.difference(yourFruits) // 🍎, 🥝
myFruits.symmetricDifference(yourFruits) // 🍎, 🥝, 🥥, 🫒
myFruits.isSubsetOf(new Set(['🍎', '🍐', '🥝', '🥥'])) // true
new Set(['🍎', '🍐', '🥝', '🥥']).isSupersetOf(myFruits) // true
myFruits.isDisjointFrom(yourFruits) // false
ES2025
function clearName(text, name) {
return text.replace(new RegExp(`${name}`, "g"), "");
}
const dynamicNamePattern = ".*"
clearName("My name is Patrice and should not appear here", dynamicNamePattern)
// ""
ES2025
function clearName(text, name) {
return text.replace(new RegExp(`${RegExp.escape(name)}`, "g"), "");
}
const dynamicNamePattern = ".*"
clearName("My name is Patrice and should not appear here", dynamicNamePattern)
// "My name is Patrice and should not appear here"
function* naturals() {
let i = 0;
while (true) {
yield i;
i += 1;
}
}
const result = naturals()
.map(value => {
return value * value;
});
result.next(); // {value: 0, done: false};
result.next(); // {value: 1, done: false};
result.next(); // {value: 4, done: false};
ES2025
function* naturals() {
let i = 0;
while (true) {
yield i;
i += 1;
}
}
const result = naturals()
.filter(value => {
return value % 2 == 0;
});
result.next(); // {value: 0, done: false};
result.next(); // {value: 2, done: false};
result.next(); // {value: 4, done: false};
ES2025
function* naturals() {
let i = 0;
while (true) {
yield i;
i += 1;
}
}
const result = naturals()
.take(3);
result.next(); // {value: 0, done: false};
result.next(); // {value: 1, done: false};
result.next(); // {value: 2, done: false};
result.next(); // {value: undefined, done: true};
ES2025
const sunny = ["It's Sunny in", "", "California"].values();
const result = sunny
.flatMap(value => value.split(" ").values());
result.next(); // {value: "It's", done: false};
result.next(); // {value: "Sunny", done: false};
result.next(); // {value: "in", done: false};
result.next(); // {value: "", done: false};
result.next(); // {value: "California", done: false};
result.next(); // {value: undefined, done: true};
ES2025
function* naturals() {
let i = 0;
while (true) {
yield i;
i += 1;
}
}
const result = naturals()
.take(5)
.reduce((sum, value) => {
return sum + value;
}, 3);
result // 13
ES2025
function* naturals() {
let i = 0;
while (true) {
yield i;
i += 1;
}
}
const result = naturals()
.take(5)
.toArray();
result // [0, 1, 2, 3, 4]
ES2025
function* naturals() {
let i = 0;
while (true) {
yield i;
i += 1;
}
}
const iter = naturals().take(4);
iter.some(v => v > 1); // true
iter.some(v => true); // false, iterator is already consumed.
naturals().take(4).some(v => v > 1); // true
naturals().take(4).some(v => v == 1); // true, acting on a new iterator
ES2025
function* naturals() {
let i = 0;
while (true) {
yield i;
i += 1;
}
}
const iter = naturals().take(10);
iter.every(v => v >= 0); // true
iter.every(v => false); // true, iterator is already consumed.
naturals().take(4).every(v => v > 0); // false, first value is 0
naturals().take(4).every(v => v >= 0); // true, acting on a new iterator
ES2025
class Iter {
next() {
return { done: false, value: 1 };
}
}
const iter = new Iter();
const wrapper = Iterator.from(iter);
wrapper.next() // { value: 1, done: false }
ES2025
import json from "./foo.json" with { type: "json" };
ES2025
new Worker("foo.wasm", { type: "module", with: { type: "webassembly" } });
import json from "./foo.json" with { type: "json" };
ES2025
Et merci :)
ES2025: https://github.com/tc39/proposals/blob/main/finished-proposals.md
tc39 process: https://tc39.es/process-document/
Node 24: https://github.com/nodejs/node/pull/57609
TS en Go: https://devblogs.microsoft.com/typescript/typescript-native-port/
oxlint: https://oxc.rs/blog/2025-03-15-oxlint-beta.html
biome2: https://biomejs.dev/blog/biome-v2-0-beta/
tanstack form: https://tanstack.com/form/latest
tanstcak vs. next: https://www.kylegill.com/essays/next-vs-tanstack
Bare: https://bare.pears.com/#why
JS battle https://deno.com/blog/deno-v-oracle3?ck_subscriber_id=310512965
https://open.nytimes.com/how-the-new-york-times-systematically-migrated-from-enzyme-into-react-testing-library-b3ea538d001c
A FU: https://node-modules.dev/?ck_subscriber_id=310512965