例如,函数
JSON.parse(data)
返回 any
类型。所以如果你写这样的东西:
const parsed = JSON.parse('example');
console.log(parsed.somethingThatDoesntExist);
尽管我的
noImplicitAny
中的 true
设置为 tsconfig.json
,并且我的 .eslintrc.js
具有规则 '@typescript-eslint/no-explicit-any': 'error'
,但 VSCode 中没有出现错误。
我还尝试将以下规则添加到我的
eslintrc.js
中,但是它们似乎破坏了所有 TypeScript 错误检查:
'@typescript-eslint/no-unsafe-call': 'error',
'@typescript-eslint/no-unsafe-member-access': 'error',
'@typescript-eslint/no-unsafe-argument': 'error',
'@typescript-eslint/no-unsafe-assignment': 'error',
在理想的世界中,我希望这个
any
被假定为 unknown
,但错误也很大。
这是我的
eslintrc.js
:
module.exports = exports = {
root: true,
parser: '@typescript-eslint/parser',
plugins: ['@typescript-eslint'],
parserOptions: {
ecmaVersion: 2021,
},
extends: ['plugin:@typescript-eslint/recommended', 'prettier', 'plugin:prettier/recommended'],
rules: {
'@typescript-eslint/ban-ts-comment': 'off',
'@typescript-eslint/no-unsafe-call': 'error',
'@typescript-eslint/no-unsafe-member-access': 'error',
'@typescript-eslint/no-unsafe-argument': 'error',
'@typescript-eslint/no-unsafe-assignment': 'error',
'@typescript-eslint/no-explicit-any': 'error',
'prettier/prettier': [
'error',
{
trailingComma: 'all',
tabWidth: 2,
semi: true,
singleQuote: true,
bracketSpacing: true,
printWidth: 120,
endOfLine: 'auto',
},
],
},
};
和
tsconfig.json
:
{
"compilerOptions": {
"strict": true,
"target": "es6",
"module": "commonjs",
"lib": [
"es6",
"ES2021.String"
],
"esModuleInterop": true,
"moduleResolution": "node",
"outDir": "../build/",
"rootDir": ".",
"resolveJsonModule": true,
"composite": true,
"types": [],
"noImplicitAny": true,
"noImplicitThis": true,
"noImplicitReturns": true
}
}
我认为最好的选择是覆盖任何需要显式类型的库。一般来说,内置函数的类型很好(JSON.parse 除外),但是如果您想修复外部库中损坏或存根的类型,这可能会很有帮助。
对于
global.d.ts
中的全局(或内置)
declare global {
interface JSON {
parse<T>(text: string, reviver?: (this: any, key: string, value: any) => T): T
}
}
export {} //this is needed to make it a module
或者模块的不同语法
declare module 'fooLibrary' {
declare function bar<T>(): T
}
// IE. require('fooLibrary') or import * from ('fooLibrary')
现在当你尝试使用
JSON.parse
const foo = JSON.parse('test');
// ^type? => unknown
const bar = JSON.parse<Record<string, any>>(...);
// ^type? => Record<string, any>
不幸的是,我不知道编译器选项或类似的全局解决方案可以提供您想要的结果。但是,您可以制作一个断言函数,不允许在特定表达式上使用
any
:
type NotAny<T> = 0 extends 1 & T ? never : unknown
declare function assertNotAny<T extends NotAny<T>>(value: T): void
assertNotAny('"example"') // okay
assertNotAny(JSON.parse('"example"')) // error
这利用了
any
不能分配给never
这一事实。通过创建解析为 never
的条件类型,您可能会在传入 any
时导致类型错误。
有关更多详细信息,请参阅https://stackoverflow.com/a/77385024/480608