vlambda博客
学习文章列表

在JS项目中引入Typescript


TypeScript是由微软开发的自由和开源的编程语言,本文作者通过举例对Typescript的优点做了简单的介绍,并对在JS项目中引入Typescript做了示范。



  01. 使用typescript的好处


1.静态类型检查

js 环境下,当我们定义了对象a,并不小心取错了他的属性名,如下图a.c,这时候在代码编写时,我们无从得知这种很常见的拼写错误。直到在运行时才会发现

在JS项目中引入Typescript

而下图ts,编译器则会直接报错
在JS项目中引入Typescript

在JS项目中引入Typescript

当然也有特殊的情况,假如我就是需要取a.c这时候应该怎么办呢?

在JS项目中引入Typescript

2.IDE配合

举一个稍微复杂一点点的例子
下面是一个typescript编写的按钮组件

import React from 'react'
interface IProps { text: string; onClick?():void;}
const MyButton:React.FC<IProps> = (props) => <button onClick={props.onClick}>{props.text}</button>
export default MyButton

import React from 'react'import MyButton from './myButton'
const MyPage = () => <div> 这是我的页面 <MyButton /></div>
export default MyPage
因为我们使用了ts,所以在使用组件的时候,我们不需要react的PropsTypes [1] 来校验组件props,IDE本身就可给予我们智能提示
在JS项目中引入Typescript
当我们传错参数类型时,同样会有提示
在JS项目中引入Typescript
在JS项目中引入Typescript
3.方便重构

  02.引入基本的typescript库和声明文件


npm install --save typescript @types/node @types/react @types/react-dom

01/ tsconfig.json
配置可以随意,下面给出一个demo
{ "compilerOptions": { "baseUrl": "src/", /* Basic Options */ "target": "es2015" /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017','ES2018' or 'ESNEXT'. */, "lib": [ "DOM", "ESNext" ] /* Specify library files to be included in the compilation. */, "skipLibCheck": true, "allowJs": false, /* Allow javascript files to be compiled. */ // "checkJs": true, /* Report errors in .js files. */ "jsx": "react" /* Specify JSX code generation: 'preserve', 'react-native', or 'react'. */, "declaration": true /* Generates corresponding '.d.ts' file. */, // "declarationMap": true, /* Generates a sourcemap for each corresponding '.d.ts' file. */ // "sourceMap": true, /* Generates corresponding '.map' file. */ // "outFile": "./", /* Concatenate and emit output to single file. */ // "outDir": "./", /* Redirect output structure to the directory. */ // "rootDir": "./", /* Specify the root directory of input files. Use to control the output directory structure with --outDir. */ // "composite": true, /* Enable project compilation */ // "removeComments": true, /* Do not emit comments to output. */ // "noEmit": true, /* Do not emit outputs. */ // "importHelpers": true, /* Import emit helpers from 'tslib'. */ // "downlevelIteration": true, /* Provide full support for iterables in 'for-of', spread, and destructuring when targeting 'ES5' or 'ES3'. */ // "isolatedModules": true, /* Transpile each file as a separate module (similar to 'ts.transpileModule'). */
/* Strict Type-Checking Options */ "strict": true /* Enable all strict type-checking options. */, "noImplicitAny": false /* Raise error on expressions and declarations with an implied 'any' type. */, "esModuleInterop": true /* Enables emit interoperability between CommonJS and ES Modules via creation of namespace objects for all imports. Implies 'allowSyntheticDefaultImports'. */, // "preserveSymlinks": true, /* Do not resolve the real path of symlinks. */ "typeRoots": ["./src/typings"], "module": "esnext", "moduleResolution": "node" }, "include": ["src/**/*"], "exclude": ["node_modules"]}


02/ 编译typescript

这里有2种方案,一种是typescript自带的tsc集合tsconfig.json编译,还有一种则是使用babel对应的preset。我们之前的webpack js项目往往使用babel,所以下面的方案以babel为例

1.babel中添加typescript Presets


npm install --save-dev @babel/preset-typescrip


{ "presets": ["@babel/preset-typescript"]}


2.babel没有typescript的类型检查怎么办

利用typescript本身的tsc进行类型检查 --noEmit
在package.json 里面添加命令,并在本地运行时执行type-check:watch
{ "script": { "type-check": "tsc --noEmit", "type-check:watch":"npm run type-check -- --watch" }}

  03. webpack还有什么?


Resolve文件解析添加ts,tsx

{ resolve: { extensions: ['.js', '.jsx', '.json', '.ts', '.tsx'], // ... }}
这样我们就可以在项目中直接引用ts文件,而不用指明.ts/.tsx后缀
- import ExpandableText from 'src/components/ExpandableText/index.tsx'import ExpandableText from 'src/components/ExpandableText'


  04. loader 编译添加ts,tsx文件

module: { rules: [ {- test: /\.jsx?$/,+ test: /\.(js|mjs|jsx|ts|tsx)$/, use: [ { loader: 'babel-loader',


eslint ? tslint[2]?

tslint 已经不被推荐使用,所以目前推荐使用eslint的ts校验插件

@typescript-eslint[3]

npm install --save-dev @typescript-eslint/eslint-plugin @typescript-eslint/parser

eslint 配置写入
  1. parser

eslint默认使用Espree[4]作为其解析器,但是我们现在要使用typescript,所要增加typescript的解析器,如下配置 @typescript-eslint/parser[5] 将 TypeScript 转换成与 estree 兼容的形式,以便在ESLint中使用。


{ "parser": "@typescript-eslint/parser",}
Eslint无法识别typescript的特定语法,(如接口),就好像eslint无法理解react jsx语法一样,所以这里还需要配置对应的第三方插件plugin

@typescript-eslint/eslint-plugin [6]

注意!因为是js项目迁移,eslint对ts的编译不应该全局更改parser,而是使用overrides选项,指定ts文件进行校验,从而最小程度的影响原有项目


{ "overrides": [{ "files": ["**/*.ts", "**/*.tsx"], "parser": "@typescript-eslint/parser", "plugins": ["@typescript-eslint"], "extends": [ 'eslint:recommended', 'plugin:react/recommended', 'plugin:@typescript-eslint/eslint-recommended', ], "rules": { "react/prop-types": 0, } }]}


注意,该插件目前仅支持typescript 4.3以下,所以这里我们更改一下需要typescript版本

npm i -S-dev typescript@4.2.4

跳转链接

[1]

Props Types: https://zh-hans.reactjs.org/docs/typechecking-with-proptypes.html#proptypes

[2]

tslint: https://github.com/palantir/tslint

[3]

@typescript-eslint: https://github.com/typescript-eslint/typescript-eslint

[4]

Espree: https://github.com/eslint/espree

[5]

typescript-eslint/parserhttps://github.com/typescript-eslint/typescript-eslint/tree/main/packages/parser

[6]

typescript-eslint/eslint-pluginhttps://github.com/typescript-eslint/typescript-eslint/tree/main/packages/eslint-plugin




「作者简介」


曹炜杰


Vic 信息系统部高级前端工程师

曾创建过多个B端组件物料库,只为让开发变得更简单。




关注 分享 在看就是所长最大的生产力!