使javascript文件知道其typescript定义文件
Typescript允许您为本地javascript文件编写.d.ts定义文件,如下所示:使javascript文件知道其typescript定义文件,javascript,typescript,.d.ts,Javascript,Typescript,.d.ts,Typescript允许您为本地javascript文件编写.d.ts定义文件,如下所示: src/ main.js imported.js imported.d.ts main.js import { func } from './imported'; console.log(func("1", "1")); import { func } from './imported'; /** * Works fine * @param {number} number */
src/
main.js
imported.js
imported.d.ts
main.js
import { func } from './imported';
console.log(func("1", "1"));
import { func } from './imported';
/**
* Works fine
* @param {number} number
*/
const mainFunc1 = (number) =>
func(number, "Hello");
/**
* Argument of type 'string' is not assignable to parameter of type 'number'
* @param {string} string
*/
const mainFunc2 = (string) =>
func(string, "Hello");
imported.js
export const func = (numVal, strVal) =>
`The number is ${numVal}, the string is ${strVal}`;
/**
* @return {string}
* @param {number} numVal
* @param {string} strVal
*/
export const func = (numVal, strVal) =>
`The number is ${funcs.func3(numVal)}, the string is ${strVal}`;
进口丁香糖
export const func: (numVal: number, strVal: string) => string;
这会出现以下错误,选项为noImplicitAny:
最后一个错误是好的,它阻止我们在应该传递数字作为第一个参数时传递字符串。但是对于前两个,在导入的javascript文件中,它不知道已经定义了参数的类型。这会阻止您使用noImplicitAny,但也会阻止您在向需要字符串的函数传递numValue时出错
有没有可能让javascript文件知道它们在typescript中的定义,最好不修改原始javascript。虽然javascript文件不能知道它们的定义文件,typescript 2.3增加了使用JSDoc注释进行类型检查的支持 将项目更改为:
src/
main.js
imported.js
imported.js
export const func = (numVal, strVal) =>
`The number is ${numVal}, the string is ${strVal}`;
/**
* @return {string}
* @param {number} numVal
* @param {string} strVal
*/
export const func = (numVal, strVal) =>
`The number is ${funcs.func3(numVal)}, the string is ${strVal}`;
main.js
import { func } from './imported';
console.log(func("1", "1"));
import { func } from './imported';
/**
* Works fine
* @param {number} number
*/
const mainFunc1 = (number) =>
func(number, "Hello");
/**
* Argument of type 'string' is not assignable to parameter of type 'number'
* @param {string} string
*/
const mainFunc2 = (string) =>
func(string, "Hello");
现在typescript编译器知道numVal是一个数字,strVal是一个字符串。尝试将numVal传递给不接受数字的函数会导致错误。func中的@return在技术上是多余的,因为它知道返回字符串,即使没有JSDoc,它也会知道,但这有利于一致性
虽然这确实需要修改原始javascript,但它只使用注释进行修改
局限性
这并没有完整的类型脚本类型检查的所有功能,但大部分都是这样。例如,如果您有一个模块返回一个对象,其中包含键入的键:
/**
* @param {number} num
*/
const func1 = (num) => num * 2;
export default {
func1,
}
然后将其与:
import imported from './module';
imported.func1(3); // This is okay
imported.func1("3"); // This is an error
imported.func2(3); // This is also okay, but it shouldn't be
对于javascript文件,这不会出错,因为它没有为默认导出生成类型,因此无法确认func2是否不存在。而在Typescript中,它会告诉您类型{func:num:number=>number;}上不存在属性“func2”。您的意思是“func”吗?不必显式声明默认导出的类型
打字稿2.5
Typescript 2.5还添加了对JSDoc类型断言的支持,例如:
// Argument of type 'string | number' is not assignable to parameter of type 'number'.
const func1 = () =>
func(funcReturnsNumberOrString(true), "Hi");
// Fine
const func2 = () =>
func(/** @type {number} */ (funcReturnsNumberOrString(true)), "Hi");
/**
* @returns { number | string }
* @param {boolean} bool
*/
const funcReturnsNumberOrString = (bool) =>
bool ? 2 : "2";
在本例中,我们知道FuncReturnsUnmberorString返回一个数字,因此我们可以这样告诉Typescript。通常.d.ts文件的存在只是为了向您无法控制的文件提供定义,例如外部模块的接口。您不能使用它为项目中的源代码创建并行定义。换句话说,在解释JS文件imported.JS时,它忽略了定义。这真的不应该是一条路;您应该有一个导入的.ts文件,并将其用于实现和定义。