From 880eb39f441ab18929693f0a23c4c9558c3dee09 Mon Sep 17 00:00:00 2001 From: tobySolutions Date: Fri, 26 Jan 2024 15:15:45 +0100 Subject: [PATCH 01/17] fix: error assignment type issue --- .../eslint-plugin/src/rules/no-unsafe-assignment.ts | 12 +++++++++++- .../tests/rules/no-unsafe-assignment.test.ts | 8 ++++++++ packages/type-utils/src/predicates.ts | 10 ++++++++++ 3 files changed, 29 insertions(+), 1 deletion(-) diff --git a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts index 4ce2f6db99a3..2a7d7b2f7f0f 100644 --- a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts +++ b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts @@ -11,6 +11,7 @@ import { getThisExpression, isTypeAnyArrayType, isTypeAnyType, + isTypeErrorType, isTypeUnknownType, isUnsafeAssignment, nullThrows, @@ -38,6 +39,7 @@ export default createRule({ }, messages: { anyAssignment: 'Unsafe assignment of an `any` value.', + errorAssignment: 'Unsafe assignment of an `error` value.', anyAssignmentThis: [ 'Unsafe assignment of an `any` value. `this` is typed as `any`.', 'You can try to fix this by turning on the `noImplicitThis` compiler option, or adding a `this` parameter to the function.', @@ -257,7 +259,10 @@ export default createRule({ return false; } - let messageId: 'anyAssignment' | 'anyAssignmentThis' = 'anyAssignment'; + let messageId: + | 'anyAssignment' + | 'anyAssignmentThis' + | 'errorAssignment' = 'anyAssignment'; if (!isNoImplicitThis) { // `var foo = this` @@ -272,10 +277,15 @@ export default createRule({ } } + if (isTypeErrorType(senderType)) { + messageId = 'errorAssignment'; + } + context.report({ node: reportingNode, messageId, }); + return true; } diff --git a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts index 56da125a97ca..3e539704a9e4 100644 --- a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts +++ b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts @@ -132,6 +132,14 @@ declare function Foo(props: Props): never; }, { code: ` + let value: number; + + value = spooky; + `, + only: true, + }, + { + code: ` declare function Foo(props: { a: string }): never; ; `, diff --git a/packages/type-utils/src/predicates.ts b/packages/type-utils/src/predicates.ts index 26ef59355781..1e490e92f934 100644 --- a/packages/type-utils/src/predicates.ts +++ b/packages/type-utils/src/predicates.ts @@ -95,6 +95,16 @@ export function isTypeAnyType(type: ts.Type): boolean { return false; } +/** + * @returns true if there is the type is an `error` type + */ +export function isTypeErrorType(type: ts.Type): boolean { + if (type.intrinsicName === 'error') { + return true; + } + return false; +} + /** * @returns true if the type is `any[]` */ From 0d14cc4061984f937e2a4fdd94bba43e13d627c1 Mon Sep 17 00:00:00 2001 From: tobySolutions Date: Fri, 26 Jan 2024 15:42:51 +0100 Subject: [PATCH 02/17] refactor: error assignment type --- .../src/rules/no-unsafe-assignment.ts | 33 +++++++++++-------- 1 file changed, 19 insertions(+), 14 deletions(-) diff --git a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts index 2a7d7b2f7f0f..268269259588 100644 --- a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts +++ b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts @@ -38,18 +38,18 @@ export default createRule({ requiresTypeChecking: true, }, messages: { - anyAssignment: 'Unsafe assignment of an `any` value.', - errorAssignment: 'Unsafe assignment of an `error` value.', + anyAssignment: 'Unsafe assignment of an {{sender}} value.', anyAssignmentThis: [ - 'Unsafe assignment of an `any` value. `this` is typed as `any`.', + 'Unsafe assignment of an {{sender}} value. `this` is typed as `any`.', 'You can try to fix this by turning on the `noImplicitThis` compiler option, or adding a `this` parameter to the function.', ].join('\n'), - unsafeArrayPattern: 'Unsafe array destructuring of an `any` array value.', + unsafeArrayPattern: + 'Unsafe array destructuring of an {{sender}} array value.', unsafeArrayPatternFromTuple: - 'Unsafe array destructuring of a tuple element with an `any` value.', + 'Unsafe array destructuring of a tuple element with an {{sender}} value.', unsafeAssignment: 'Unsafe assignment of type {{sender}} to a variable of type {{receiver}}.', - unsafeArraySpread: 'Unsafe spread of an `any` value in an array.', + unsafeArraySpread: 'Unsafe spread of an {{sender}} value in an array.', }, schema: [], }, @@ -90,6 +90,9 @@ export default createRule({ context.report({ node: receiverNode, messageId: 'unsafeArrayPattern', + data: { + sender: isTypeErrorType(senderType) ? 'error' : 'any', + }, }); return false; } @@ -128,6 +131,9 @@ export default createRule({ context.report({ node: receiverElement, messageId: 'unsafeArrayPatternFromTuple', + data: { + sender: isTypeErrorType(senderType) ? 'error' : 'any', + }, }); // we want to report on every invalid element in the tuple didReport = true; @@ -214,6 +220,9 @@ export default createRule({ context.report({ node: receiverProperty.value, messageId: 'unsafeArrayPatternFromTuple', + data: { + sender: isTypeErrorType(senderType) ? 'error' : 'any', + }, }); didReport = true; } else if ( @@ -259,10 +268,7 @@ export default createRule({ return false; } - let messageId: - | 'anyAssignment' - | 'anyAssignmentThis' - | 'errorAssignment' = 'anyAssignment'; + let messageId: 'anyAssignment' | 'anyAssignmentThis' = 'anyAssignment'; if (!isNoImplicitThis) { // `var foo = this` @@ -277,13 +283,12 @@ export default createRule({ } } - if (isTypeErrorType(senderType)) { - messageId = 'errorAssignment'; - } - context.report({ node: reportingNode, messageId, + data: { + sender: isTypeErrorType(senderType) ? 'error' : 'any', + }, }); return true; From 1cecfefc24edb383475358bb091533456e1f0331 Mon Sep 17 00:00:00 2001 From: tobySolutions Date: Fri, 26 Jan 2024 15:47:09 +0100 Subject: [PATCH 03/17] refactor: error assignment type --- packages/eslint-plugin/src/rules/no-unsafe-assignment.ts | 3 +++ 1 file changed, 3 insertions(+) diff --git a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts index 268269259588..5509fcfb4994 100644 --- a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts +++ b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts @@ -398,6 +398,9 @@ export default createRule({ context.report({ node: node, messageId: 'unsafeArraySpread', + data: { + sender: isTypeErrorType(restType) ? 'error' : 'any', + }, }); } }, From af01290619ff2ea4a9525b082f0e4ef912ec9f6d Mon Sep 17 00:00:00 2001 From: tobySolutions Date: Fri, 26 Jan 2024 15:56:07 +0100 Subject: [PATCH 04/17] refactor: error assignment type --- .../tests/rules/no-unsafe-assignment.test.ts | 21 ++++++++++++------- 1 file changed, 14 insertions(+), 7 deletions(-) diff --git a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts index 3e539704a9e4..51850a9863dc 100644 --- a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts +++ b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts @@ -130,14 +130,7 @@ declare function Foo(props: Props): never; }, }, }, - { - code: ` - let value: number; - value = spooky; - `, - only: true, - }, { code: ` declare function Foo(props: { a: string }): never; @@ -198,7 +191,21 @@ class Foo { `, errors: [{ messageId: 'anyAssignment' }], }, + { + code: ` + let value: number; + value = spooky; + `, + errors: [ + { + messageId: 'anyAssignment', + data: { + sender: 'error', + }, + }, + ], + }, { code: ` const [x] = 1 as any; From 61457cb7c48fff0031e1da14a039eed874f339b4 Mon Sep 17 00:00:00 2001 From: tobySolutions Date: Mon, 25 Mar 2024 23:56:22 +0100 Subject: [PATCH 05/17] chore: resolve comments --- .../src/rules/no-unsafe-assignment.ts | 32 ++++++------- .../tests/rules/no-unsafe-assignment.test.ts | 45 +++++++++++++------ 2 files changed, 46 insertions(+), 31 deletions(-) diff --git a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts index 5509fcfb4994..758c2f7ba403 100644 --- a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts +++ b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts @@ -1,7 +1,7 @@ import type { TSESTree } from '@typescript-eslint/utils'; import { AST_NODE_TYPES } from '@typescript-eslint/utils'; import * as tsutils from 'ts-api-utils'; -import type * as ts from 'typescript'; +import * as ts from 'typescript'; import { createRule, @@ -90,9 +90,7 @@ export default createRule({ context.report({ node: receiverNode, messageId: 'unsafeArrayPattern', - data: { - sender: isTypeErrorType(senderType) ? 'error' : 'any', - }, + data: createDataFromSenderType(senderType), }); return false; } @@ -131,9 +129,7 @@ export default createRule({ context.report({ node: receiverElement, messageId: 'unsafeArrayPatternFromTuple', - data: { - sender: isTypeErrorType(senderType) ? 'error' : 'any', - }, + data: createDataFromSenderType(senderType), }); // we want to report on every invalid element in the tuple didReport = true; @@ -220,9 +216,7 @@ export default createRule({ context.report({ node: receiverProperty.value, messageId: 'unsafeArrayPatternFromTuple', - data: { - sender: isTypeErrorType(senderType) ? 'error' : 'any', - }, + data: createDataFromSenderType(senderType), }); didReport = true; } else if ( @@ -286,9 +280,7 @@ export default createRule({ context.report({ node: reportingNode, messageId, - data: { - sender: isTypeErrorType(senderType) ? 'error' : 'any', - }, + data: createDataFromSenderType(senderType), }); return true; @@ -313,8 +305,8 @@ export default createRule({ node: reportingNode, messageId: 'unsafeAssignment', data: { - sender: checker.typeToString(sender), - receiver: checker.typeToString(receiver), + sender: '`' + checker.typeToString(sender) + '`', + receiver:'`' + checker.typeToString(receiver) + '`', }, }); return true; @@ -330,6 +322,12 @@ export default createRule({ ComparisonType.None; } + function createDataFromSenderType(senderType: ts.Type) { + return { + sender: tsutils.isIntrinsicErrorType(senderType) ? 'error' : '`any`', + }; + } + return { 'VariableDeclarator[init != null]'( node: TSESTree.VariableDeclarator, @@ -398,9 +396,7 @@ export default createRule({ context.report({ node: node, messageId: 'unsafeArraySpread', - data: { - sender: isTypeErrorType(restType) ? 'error' : 'any', - }, + data: createDataFromSenderType(restType), }); } }, diff --git a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts index 51850a9863dc..020298588f96 100644 --- a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts +++ b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts @@ -185,12 +185,31 @@ class Foo { }, { code: ` -class Foo { - private a = 1 as any; -} + class Foo { + private a = 1 as any; + } + `, + errors: [{ messageId: 'anyAssignment' }], + }, + { + code: ` + const [x] = spooky; `, errors: [{ messageId: 'anyAssignment' }], }, + { + code: ` + const [[[x]]] = [spooky]; + `, + errors: [{ messageId: 'unsafeArrayPatternFromTuple' }], + }, + { + code: ` + const {x: {y}} = {x: {spooky}}; + `, + only: true, + errors: [{ messageId: 'unsafeArrayPatternFromTuple' }], + }, { code: ` let value: number; @@ -225,8 +244,8 @@ const [x] = [] as any[]; { messageId: 'unsafeAssignment', data: { - sender: 'Set', - receiver: 'Set', + sender: '`Set`', + receiver: '`Set`', }, }, ], @@ -237,8 +256,8 @@ const [x] = [] as any[]; { messageId: 'unsafeAssignment', data: { - sender: 'Map', - receiver: 'Map', + sender: '`Map`', + receiver: '`Map`', }, }, ], @@ -249,8 +268,8 @@ const [x] = [] as any[]; { messageId: 'unsafeAssignment', data: { - sender: 'Set', - receiver: 'Set', + sender: '`Set`', + receiver: '`Set`', }, }, ], @@ -261,8 +280,8 @@ const [x] = [] as any[]; { messageId: 'unsafeAssignment', data: { - sender: 'Set>>', - receiver: 'Set>>', + sender: '`Set>>`', + receiver: '`Set>>`', }, }, ], @@ -337,8 +356,8 @@ const x = [...([] as any[])]; column: 43, endColumn: 70, data: { - sender: 'Set>>', - receiver: 'Set>>', + sender: '`Set>>`', + receiver: '`Set>>`', }, }, ], From 4764ce3c9f58685cba9518c32c74052f273c7732 Mon Sep 17 00:00:00 2001 From: tobySolutions Date: Sun, 2 Jun 2024 20:14:09 +0100 Subject: [PATCH 06/17] fix: error type assignment tests --- .../src/rules/no-unsafe-assignment.ts | 4 ++-- .../tests/rules/no-unsafe-assignment.test.ts | 14 ++++++++------ 2 files changed, 10 insertions(+), 8 deletions(-) diff --git a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts index 758c2f7ba403..d473d051902b 100644 --- a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts +++ b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts @@ -38,7 +38,7 @@ export default createRule({ requiresTypeChecking: true, }, messages: { - anyAssignment: 'Unsafe assignment of an {{sender}} value.', + anyAssignment: 'Unsafe assignment of an {{sender}} typed value.', anyAssignmentThis: [ 'Unsafe assignment of an {{sender}} value. `this` is typed as `any`.', 'You can try to fix this by turning on the `noImplicitThis` compiler option, or adding a `this` parameter to the function.', @@ -306,7 +306,7 @@ export default createRule({ messageId: 'unsafeAssignment', data: { sender: '`' + checker.typeToString(sender) + '`', - receiver:'`' + checker.typeToString(receiver) + '`', + receiver: '`' + checker.typeToString(receiver) + '`', }, }); return true; diff --git a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts index 020298588f96..3217e308c193 100644 --- a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts +++ b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts @@ -177,9 +177,9 @@ const x = 1 as any, }, { code: ` -class Foo { - constructor(private a = 1 as any) {} -} + class Foo { + constructor(private a = 1 as any) {} + } `, errors: [{ messageId: 'anyAssignment' }], }, @@ -205,10 +205,12 @@ class Foo { }, { code: ` - const {x: {y}} = {x: {spooky}}; + const {x: {y: z}} = {x: spooky}; `, - only: true, - errors: [{ messageId: 'unsafeArrayPatternFromTuple' }], + errors: [ + { messageId: 'unsafeArrayPatternFromTuple' }, + { messageId: 'anyAssignment' }, + ], }, { code: ` From e79ae862741a475f551cf01dd2f0b78d9bf6ccf4 Mon Sep 17 00:00:00 2001 From: tobySolutions Date: Sun, 2 Jun 2024 20:31:12 +0100 Subject: [PATCH 07/17] fix: error type assignment tests --- yarn.lock | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/yarn.lock b/yarn.lock index 300faf3f7834..81f1154b9e52 100644 --- a/yarn.lock +++ b/yarn.lock @@ -19699,11 +19699,11 @@ __metadata: "typescript@patch:typescript@npm%3A5.4.5#~builtin": version: 5.4.5 - resolution: "typescript@patch:typescript@npm%3A5.4.5#~builtin::version=5.4.5&hash=5adc0c" + resolution: "typescript@patch:typescript@npm%3A5.4.5#~builtin::version=5.4.5&hash=e012d7" bin: tsc: bin/tsc tsserver: bin/tsserver - checksum: d59e26e74f6b444517d0ba16e0ee16e75c652c2b49a59f2ebdbeb16647a855fd50c7fc786a58987e45f03bce0677092e2dd3333649fd53b11d0b0d271455837c + checksum: 2373c693f3b328f3b2387c3efafe6d257b057a142f9a79291854b14ff4d5367d3d730810aee981726b677ae0fd8329b23309da3b6aaab8263dbdccf1da07a3ba languageName: node linkType: hard From 207d9056e7877fefbde6f121ea5d0ad154b831bd Mon Sep 17 00:00:00 2001 From: tobySolutions Date: Sun, 2 Jun 2024 20:38:27 +0100 Subject: [PATCH 08/17] chore: change yarn lock --- yarn.lock | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/yarn.lock b/yarn.lock index 81f1154b9e52..51215787937f 100644 --- a/yarn.lock +++ b/yarn.lock @@ -19703,7 +19703,7 @@ __metadata: bin: tsc: bin/tsc tsserver: bin/tsserver - checksum: 2373c693f3b328f3b2387c3efafe6d257b057a142f9a79291854b14ff4d5367d3d730810aee981726b677ae0fd8329b23309da3b6aaab8263dbdccf1da07a3ba + checksum: d59e26e74f6b444517d0ba16e0ee16e75c652c2b49a59f2ebdbeb16647a855fd50c7fc786a58987e45f03bce0677092e2dd3333649fd53b11d0b0d271455837c languageName: node linkType: hard From 4b14cd073b2bafe137206aa112a47509e6a244ac Mon Sep 17 00:00:00 2001 From: tobySolutions Date: Sun, 2 Jun 2024 21:02:21 +0100 Subject: [PATCH 09/17] fix: errot type assignments tests --- .../eslint-plugin/src/rules/no-unsafe-assignment.ts | 8 ++++---- .../tests/rules/no-unsafe-assignment.test.ts | 10 ++++++++-- 2 files changed, 12 insertions(+), 6 deletions(-) diff --git a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts index 73c5745fd516..570381d6e100 100644 --- a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts +++ b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts @@ -38,18 +38,18 @@ export default createRule({ requiresTypeChecking: true, }, messages: { - anyAssignment: 'Unsafe assignment of an {{sender}} typed value.', + anyAssignment: 'Unsafe assignment of an {{sender}} value.', anyAssignmentThis: [ - 'Unsafe assignment of an {{sender}} value. `this` is typed as `any`.', + 'Unsafe assignment of an {{sender}} value. `this` is typed as `any`.', 'You can try to fix this by turning on the `noImplicitThis` compiler option, or adding a `this` parameter to the function.', ].join('\n'), unsafeArrayPattern: 'Unsafe array destructuring of an {{sender}} array value.', unsafeArrayPatternFromTuple: - 'Unsafe array destructuring of a tuple element with an {{sender}} value.', + 'Unsafe array destructuring of a tuple element with an {{sender}} value.', unsafeAssignment: 'Unsafe assignment of type {{sender}} to a variable of type {{receiver}}.', - unsafeArraySpread: 'Unsafe spread of an {{sender}} value in an array.', + unsafeArraySpread: 'Unsafe spread of an {{sender}} value in an array.', }, schema: [], }, diff --git a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts index 5f32fa86d1ac..d9df6e26550a 100644 --- a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts +++ b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts @@ -213,8 +213,14 @@ const x = 1 as any, const {x: {y: z}} = {x: spooky}; `, errors: [ - { messageId: 'unsafeArrayPatternFromTuple' }, - { messageId: 'anyAssignment' }, + { + messageId: 'unsafeArrayPatternFromTuple', + data: { sender: 'error', receiver: 'error' }, + }, + { + messageId: 'anyAssignment', + data: { sender: 'error', receiver: 'error' }, + }, ], }, { From da001c9e0edbe0f4a64b6b7f7dc4b0243cc71cff Mon Sep 17 00:00:00 2001 From: tobySolutions Date: Sun, 2 Jun 2024 21:08:50 +0100 Subject: [PATCH 10/17] chore: remove unnecessary error type check function --- .../eslint-plugin/src/rules/no-unsafe-assignment.ts | 1 - packages/type-utils/src/predicates.ts | 10 ---------- 2 files changed, 11 deletions(-) diff --git a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts index 570381d6e100..2bac415e2f02 100644 --- a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts +++ b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts @@ -11,7 +11,6 @@ import { getThisExpression, isTypeAnyArrayType, isTypeAnyType, - isTypeErrorType, isTypeUnknownType, isUnsafeAssignment, nullThrows, diff --git a/packages/type-utils/src/predicates.ts b/packages/type-utils/src/predicates.ts index 1e490e92f934..26ef59355781 100644 --- a/packages/type-utils/src/predicates.ts +++ b/packages/type-utils/src/predicates.ts @@ -95,16 +95,6 @@ export function isTypeAnyType(type: ts.Type): boolean { return false; } -/** - * @returns true if there is the type is an `error` type - */ -export function isTypeErrorType(type: ts.Type): boolean { - if (type.intrinsicName === 'error') { - return true; - } - return false; -} - /** * @returns true if the type is `any[]` */ From 809c291a729babe379df11d6dfdf5c7d4655e06c Mon Sep 17 00:00:00 2001 From: tobySolutions Date: Sun, 2 Jun 2024 21:18:42 +0100 Subject: [PATCH 11/17] refactor: rename every error ocurrence to error typed --- packages/eslint-plugin/src/rules/no-unsafe-assignment.ts | 4 +++- .../eslint-plugin/tests/rules/no-unsafe-assignment.test.ts | 6 +++--- yarn.lock | 2 +- 3 files changed, 7 insertions(+), 5 deletions(-) diff --git a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts index 2bac415e2f02..5028699326d6 100644 --- a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts +++ b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts @@ -323,7 +323,9 @@ export default createRule({ function createDataFromSenderType(senderType: ts.Type) { return { - sender: tsutils.isIntrinsicErrorType(senderType) ? 'error' : '`any`', + sender: tsutils.isIntrinsicErrorType(senderType) + ? 'error typed' + : '`any`', }; } diff --git a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts index d9df6e26550a..e390d5e6220b 100644 --- a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts +++ b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts @@ -215,11 +215,11 @@ const x = 1 as any, errors: [ { messageId: 'unsafeArrayPatternFromTuple', - data: { sender: 'error', receiver: 'error' }, + data: { sender: 'error typed', receiver: 'error typed' }, }, { messageId: 'anyAssignment', - data: { sender: 'error', receiver: 'error' }, + data: { sender: 'error typed', receiver: 'error typed' }, }, ], }, @@ -233,7 +233,7 @@ const x = 1 as any, { messageId: 'anyAssignment', data: { - sender: 'error', + sender: 'error typed', }, }, ], diff --git a/yarn.lock b/yarn.lock index 51215787937f..300faf3f7834 100644 --- a/yarn.lock +++ b/yarn.lock @@ -19699,7 +19699,7 @@ __metadata: "typescript@patch:typescript@npm%3A5.4.5#~builtin": version: 5.4.5 - resolution: "typescript@patch:typescript@npm%3A5.4.5#~builtin::version=5.4.5&hash=e012d7" + resolution: "typescript@patch:typescript@npm%3A5.4.5#~builtin::version=5.4.5&hash=5adc0c" bin: tsc: bin/tsc tsserver: bin/tsserver From 602f6d9f5731ae12b6828cce689a903998566ba8 Mon Sep 17 00:00:00 2001 From: tobySolutions Date: Sun, 2 Jun 2024 21:40:55 +0100 Subject: [PATCH 12/17] refactor: rename every error ocurrence to error typed --- packages/eslint-plugin/src/rules/no-unsafe-assignment.ts | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts index 5028699326d6..dfdb7840f06d 100644 --- a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts +++ b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts @@ -1,7 +1,7 @@ import type { TSESTree } from '@typescript-eslint/utils'; import { AST_NODE_TYPES } from '@typescript-eslint/utils'; import * as tsutils from 'ts-api-utils'; -import * as ts from 'typescript'; +import type * as ts from 'typescript'; import { createRule, @@ -321,7 +321,9 @@ export default createRule({ ComparisonType.None; } - function createDataFromSenderType(senderType: ts.Type) { + function createDataFromSenderType( + senderType: ts.Type, + ): Readonly> | undefined { return { sender: tsutils.isIntrinsicErrorType(senderType) ? 'error typed' From ccb4d43fbf5a902690963a8631d286546e20657b Mon Sep 17 00:00:00 2001 From: tobySolutions Date: Sun, 2 Jun 2024 22:01:35 +0100 Subject: [PATCH 13/17] refactor: rename every error ocurrence to error typed --- .../no-unsafe-assignment.shot | 8 +++---- .../tests/rules/no-unsafe-assignment.test.ts | 22 +++++++++---------- 2 files changed, 15 insertions(+), 15 deletions(-) diff --git a/packages/eslint-plugin/tests/docs-eslint-output-snapshots/no-unsafe-assignment.shot b/packages/eslint-plugin/tests/docs-eslint-output-snapshots/no-unsafe-assignment.shot index 2e1b94899b68..de10a87d5f42 100644 --- a/packages/eslint-plugin/tests/docs-eslint-output-snapshots/no-unsafe-assignment.shot +++ b/packages/eslint-plugin/tests/docs-eslint-output-snapshots/no-unsafe-assignment.shot @@ -29,13 +29,13 @@ class Foo { // generic position examples const x: Set = new Set(); - ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Unsafe assignment of type Set to a variable of type Set. + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Unsafe assignment of type \`Set\` to a variable of type \`Set\`. const x: Map = new Map(); - ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Unsafe assignment of type Map to a variable of type Map. + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Unsafe assignment of type \`Map\` to a variable of type \`Map\`. const x: Set = new Set(); - ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Unsafe assignment of type Set to a variable of type Set. + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Unsafe assignment of type \`Set\` to a variable of type \`Set\`. const x: Set>> = new Set>>(); - ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Unsafe assignment of type Set>> to a variable of type Set>>. + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Unsafe assignment of type \`Set>>\` to a variable of type \`Set>>\`. " `; diff --git a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts index e390d5e6220b..d70ece947230 100644 --- a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts +++ b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts @@ -182,35 +182,35 @@ const x = 1 as any, }, { code: ` - class Foo { - constructor(private a = 1 as any) {} - } +class Foo { + constructor(private a = 1 as any) {} +} `, errors: [{ messageId: 'anyAssignment' }], }, { code: ` - class Foo { - private a = 1 as any; - } +class Foo { + private a = 1 as any; +} `, errors: [{ messageId: 'anyAssignment' }], }, { code: ` - const [x] = spooky; + const [x] = spooky; `, errors: [{ messageId: 'anyAssignment' }], }, { code: ` - const [[[x]]] = [spooky]; +const [[[x]]] = [spooky]; `, errors: [{ messageId: 'unsafeArrayPatternFromTuple' }], }, { code: ` - const {x: {y: z}} = {x: spooky}; +const {x: {y: z}} = {x: spooky}; `, errors: [ { @@ -225,9 +225,9 @@ const x = 1 as any, }, { code: ` - let value: number; +let value: number; - value = spooky; +value = spooky; `, errors: [ { From 7ef8aefd2942640628905f9b275e452748980944 Mon Sep 17 00:00:00 2001 From: tobySolutions Date: Mon, 3 Jun 2024 01:10:09 +0100 Subject: [PATCH 14/17] fix CI issues --- .../eslint-plugin/tests/rules/no-unsafe-assignment.test.ts | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts index d70ece947230..dea4d320c68c 100644 --- a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts +++ b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts @@ -183,7 +183,7 @@ const x = 1 as any, { code: ` class Foo { - constructor(private a = 1 as any) {} + constructor(private a = 1 as any) {} } `, errors: [{ messageId: 'anyAssignment' }], @@ -191,14 +191,14 @@ class Foo { { code: ` class Foo { - private a = 1 as any; + private a = 1 as any; } `, errors: [{ messageId: 'anyAssignment' }], }, { code: ` - const [x] = spooky; +const [x] = spooky; `, errors: [{ messageId: 'anyAssignment' }], }, From 48e03a032a19340e4b5829221a5afe7a5b437305 Mon Sep 17 00:00:00 2001 From: tobySolutions Date: Mon, 3 Jun 2024 01:19:10 +0100 Subject: [PATCH 15/17] fix CI issues --- .../eslint-plugin/tests/rules/no-unsafe-assignment.test.ts | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts index dea4d320c68c..60414574a3ec 100644 --- a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts +++ b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts @@ -210,7 +210,9 @@ const [[[x]]] = [spooky]; }, { code: ` -const {x: {y: z}} = {x: spooky}; +const { + x: { y: z }, +} = { x: spooky }; `, errors: [ { From 7ef85ee4c92fdf4425eaced36e9d1073cf54b292 Mon Sep 17 00:00:00 2001 From: tobySolutions Date: Mon, 3 Jun 2024 03:42:26 +0100 Subject: [PATCH 16/17] refactor: change create data from types function and add test data for test cases --- .../src/rules/no-unsafe-assignment.ts | 35 +++++++++++-------- .../tests/rules/no-unsafe-assignment.test.ts | 14 ++++++-- 2 files changed, 32 insertions(+), 17 deletions(-) diff --git a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts index dfdb7840f06d..eef2d8f9b99a 100644 --- a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts +++ b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts @@ -89,7 +89,7 @@ export default createRule({ context.report({ node: receiverNode, messageId: 'unsafeArrayPattern', - data: createDataFromSenderType(senderType), + data: createData(senderType), }); return false; } @@ -128,7 +128,7 @@ export default createRule({ context.report({ node: receiverElement, messageId: 'unsafeArrayPatternFromTuple', - data: createDataFromSenderType(senderType), + data: createData(senderType), }); // we want to report on every invalid element in the tuple didReport = true; @@ -215,7 +215,7 @@ export default createRule({ context.report({ node: receiverProperty.value, messageId: 'unsafeArrayPatternFromTuple', - data: createDataFromSenderType(senderType), + data: createData(senderType), }); didReport = true; } else if ( @@ -279,7 +279,7 @@ export default createRule({ context.report({ node: reportingNode, messageId, - data: createDataFromSenderType(senderType), + data: createData(senderType), }); return true; @@ -303,10 +303,7 @@ export default createRule({ context.report({ node: reportingNode, messageId: 'unsafeAssignment', - data: { - sender: '`' + checker.typeToString(sender) + '`', - receiver: '`' + checker.typeToString(receiver) + '`', - }, + data: createData(sender, receiver), }); return true; } @@ -321,14 +318,22 @@ export default createRule({ ComparisonType.None; } - function createDataFromSenderType( + function createData( senderType: ts.Type, + receiverType?: ts.Type, ): Readonly> | undefined { - return { - sender: tsutils.isIntrinsicErrorType(senderType) - ? 'error typed' - : '`any`', - }; + if (receiverType) { + return { + sender: '`' + checker.typeToString(senderType) + '`', + receiver: '`' + checker.typeToString(receiverType) + '`', + }; + } else { + return { + sender: tsutils.isIntrinsicErrorType(senderType) + ? 'error typed' + : '`any`', + }; + } } return { @@ -399,7 +404,7 @@ export default createRule({ context.report({ node: node, messageId: 'unsafeArraySpread', - data: createDataFromSenderType(restType), + data: createData(restType), }); } }, diff --git a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts index 60414574a3ec..a65923ab6778 100644 --- a/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts +++ b/packages/eslint-plugin/tests/rules/no-unsafe-assignment.test.ts @@ -200,13 +200,23 @@ class Foo { code: ` const [x] = spooky; `, - errors: [{ messageId: 'anyAssignment' }], + errors: [ + { + messageId: 'anyAssignment', + data: { sender: 'error typed', receiver: 'error typed' }, + }, + ], }, { code: ` const [[[x]]] = [spooky]; `, - errors: [{ messageId: 'unsafeArrayPatternFromTuple' }], + errors: [ + { + messageId: 'unsafeArrayPatternFromTuple', + data: { sender: 'error typed', receiver: 'error typed' }, + }, + ], }, { code: ` From b70a2caf8f2f52f1445231ef51e669fd71850f19 Mon Sep 17 00:00:00 2001 From: tobySolutions Date: Mon, 3 Jun 2024 03:51:19 +0100 Subject: [PATCH 17/17] refactor: remove unnecessary else --- .../eslint-plugin/src/rules/no-unsafe-assignment.ts | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts index eef2d8f9b99a..883783dbd527 100644 --- a/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts +++ b/packages/eslint-plugin/src/rules/no-unsafe-assignment.ts @@ -327,13 +327,12 @@ export default createRule({ sender: '`' + checker.typeToString(senderType) + '`', receiver: '`' + checker.typeToString(receiverType) + '`', }; - } else { - return { - sender: tsutils.isIntrinsicErrorType(senderType) - ? 'error typed' - : '`any`', - }; } + return { + sender: tsutils.isIntrinsicErrorType(senderType) + ? 'error typed' + : '`any`', + }; } return {