Move the toolchain to eslint 10, typescript-eslint 8 and current plugins

eslint 8 and typescript-eslint 6 are past their support, and the webpack
dev server chain carried the dependency alerts every repository using this
package inherited. Upstream @polkadot/dev still pins the same versions, so
this leaves it on purpose.

The rules are carried over with their options, so the lint means what it
meant:

- eslint-config-standard 17 (written for eslint 8) is replaced by its 161
  rules in config/eslint.standard.js, with their options. Its 48 formatting
  rules, deprecated in eslint core, are the same rules in @stylistic;
  no-new-object and no-new-symbol are no-object-constructor and
  no-new-native-nonconstructor; import/* is import-x/*.
- eslint-plugin-import (eslint <= 9) is eslint-plugin-import-x;
  eslint-plugin-deprecation is @typescript-eslint/no-deprecated; the
  formatting rules of core, typescript-eslint and eslint-plugin-react used
  in eslint.rules.js are their @stylistic versions with the same options.
- typescript-eslint 8's preset swaps core no-unused-expressions for its own
  with default options; standard's (short circuit, ternary and tagged
  templates allowed) are carried over to it.
- eslint-plugin-react and eslint-plugin-header still call context methods
  eslint 10 removed; @eslint/compat's fixupPluginRules supplies them. The
  header rule also gets `schema: false`, as eslint 9+ rejects options for a
  rule with no schema. The original header plugin stays rather than its
  fork: it reports at the first token after leading comments, so a
  generated file's /* eslint-disable */ still covers it, as it always has.

The effective config was compared rule by rule (--print-config) for .ts,
.tsx, .spec.ts and .mjs files before and after. Every rule that left has
its successor active; option differences are eslint 10 spelling out
defaults. New rules come from the eslint 10, typescript-eslint 8 and
react-hooks 7 presets. no-inner-declarations left eslint's preset upstream.

Also current: webpack-dev-server 6, webpack-cli 7, webpack-merge 6, rollup
plugins, madge 8, gh-release 8, globals 17, espree 11; Node >= 20.19 for
the dev package, which eslint 10 requires.

In this repository the new rules found: Function types now named by
no-unsafe-function-type; optional chains, includes() and RegExp#exec where
they say the same thing; createWrapper returns Describe, so its three casts
were redundant; rootCjs.spec casts through unknown, so the lint result does
not depend on whether build/ exists. lint, build and test (149 passed) pass,
and lint leaves the tree unchanged with and without a build.
This commit is contained in:
Satoshi Qazi Muhammed authored and SatoshiQaziMuhammed committed 2026-10-09 08:56:18 +04:00
1 parent 9e6a1ab2a2
commit f9f04f6adc
17 files changed
+3401 -3570

No files matched your search

@@ -122,7 +122,7 @@ function getFilename (r) {
.split('\n')
.map((l) => l.trim())
.filter((l) => l.startsWith('at ') && (l.includes('.spec.') || l.includes('.test.')))
.map((l) => l.match(/\(.*:\d\d?:\d\d?\)$/)?.[0])
.map((l) => (/\(.*:\d\d?:\d\d?\)$/.exec(l))?.[0])
.map((l) => l?.replace('(', '')?.replace(')', ''));
if (stack.length) {
@@ -186,7 +186,7 @@ function complete () {
if (typeof r === 'string') {
console.log(r); // Node.js <= 18.14
} else if (r.file && r.file.includes('@pezkuwi/dev/scripts')) {
} else if (r.file?.includes('@pezkuwi/dev/scripts')) {
// Ignore internal diagnostics
} else {
if (lastFilename !== r.file) {
@@ -328,11 +328,11 @@ if (isMainThread) {
} else {
run({ files: workerData.files, timeout: 3_600_000 })
.on('data', () => undefined)
.on('end', () => parentPort && parentPort.postMessage(stats))
.on('end', () => parentPort?.postMessage(stats))
.on('test:coverage', () => undefined)
.on('test:diagnostic', (/** @type {DiagStat} */data) => {
stats.diag.push(data);
parentPort && parentPort.postMessage({ data: stats, type: 'result' });
parentPort?.postMessage({ data: stats, type: 'result' });
})
.on('test:fail', (/** @type {FailStat} */ data) => {
const statFail = structuredClone(data);
@@ -343,7 +343,7 @@ if (isMainThread) {
stats.fail.push(statFail);
stats.total++;
parentPort && parentPort.postMessage({ data: 'x', type: 'progress' });
parentPort?.postMessage({ data: 'x', type: 'progress' });
if (bail) {
complete();
@@ -361,7 +361,7 @@ if (isMainThread) {
}
stats.total++;
parentPort && parentPort.postMessage({ data: symbol, type: 'progress' });
parentPort?.postMessage({ data: symbol, type: 'progress' });
})
.on('test:plan', () => undefined)
.on('test:start', () => undefined);