2022-04-14使用ts重构vue2项目

一、改动点

1. 安装依赖
  • 如果不使用基于类的组件(使用基本组件)略过这步
    vue-class-component :官方维护的装饰器
    vue-property-decorator :基于vue-class-component的装饰器,社区维护
    npm install --save vue-class-component vue-property-decorator 
    
  • 必须安装
    npm install --save-dev ts-loader typescript
    
  • 其他(eslint相关)
    @typescript-eslint/eslint-plugin
    @typescript-eslint/parser
2. 修改webpack配置(vue.config.js)
configureWebpack: (config) => {
  config.resolve.extensions.push('.ts');   // 添加ts扩展文件:引用ts文件的时候不用写后缀名
  config.module.rules.push({             // 使用ts-loader对ts/tsx文件打包编译
    test: /\.tsx?$/,
    loader: 'ts-loader',
    exclude: /node_modules/,
    options: {
      appendTsSuffixTo: [/\.vue$/],    // ts编译器tsc不能识别.vue文件,所以在 .vue文件后加.ts后缀
    },
  });
}
3. 根目录下新建tsconfig.json文件(或者使用tsc --init自动生成)
  • compilerOptions用于确定如何编译ts文件

  • 使用官方/默认配置即可。

  • 自定义配置参考:

     "compilerOptions": {
       "target": "es5",  // 指定ECMAScript目标版本
       "module": "commonjs",  // 指定生成哪个模块系统代码
       "allowJs": true,   // 允许编译js文件
       "sourceMap": true, // 是否生成map文件
       "strict": true, // 启用所有严格类型检查选项
       "noUnusedLocals": true,
       "baseUrl": ".",   // 工作根目录
       "paths": {          // 和webpack中resolve.alias配置一样
           "@/*": [
             "src/*"     
           ]
        }, 
       "esModuleInterop": true, // 支持使用esm的方式引入commonjs包
       "experimentalDecorators": true, // 启用试验性的es装饰器(如果要使用装饰器的话)
       "skipLibCheck": true, // 忽略所有的声明文件的类型检查。
       "forceConsistentCasingInFileNames": true. // 禁止对同一个文件的不一致的引用(将强制区分大小写)。
     }
    
    1. path路径查找注释:minimatch,用来模式匹配字符串的库。
    • *匹配 0 个或多个字符,不包含目录分隔符
    • **/递归匹配任意子目录
    1. esModuleInterop作用解析
    2. compilerOptions编译选项
4. 修改.eslintrc.js文件:详见(二、重构问题/踩坑-Q2)
5. src根目录下创建声明文件支持引入.vue文件(必须)
// shims-vue.d.ts
//通配符声明模块
declare module '*.vue' {
    import Vue from 'vue';  // import写里面,不要写外面(原因待补充)
    export default Vue;
}
6. 支持this访问vue原型上定义的功能(非必须)
// type.d.ts
import { default as Axios } from '@/plugins/axios.js'
declare module 'vue/types/vue'{
    interface Vue {
        $axios: Axios;
    }
}

二、重构问题/踩坑

Q1:import Vue from 'vue' => Cannot find module ‘vue’.
原因
解决:tsconfig.json配置

"target": "es5",             
"module": "es6", 

修改为

"target": "es5",             
"module": "commonjs", 

Q2:.vue文件使用ts语法eslint报错
解决:修改.eslintrc文件(目前只针对特定重构目录使用ts解析,后面有更合适的配置会修改)
待解决:怎么对不同目录下的文件分别使用不同的配置。

  • (解决方式:在子目录下配置自己的eslintrc文件。层叠配置使用离要检测的文件最近的 .eslintrc文件作为最高优先级,然后才是父目录里的配置文件。配置冲突时,子目录配置会覆盖根目录配置)eslint-Configuration Cascading and Hierarchy
 overrides: [{
    files: [
      '**/financial_manage/**/*.ts',
      '**/financial_manage/**/*.tsx',
      '**/financial_manage/**/*.vue',
    ],
    plugins: ['@typescript-eslint'],
    parserOptions: {
      parser: '@typescript-eslint/parser',
    },
  }],

Q3:使用this访问定义在vue原型上的功能
解决:在type.d.ts文件进行模块补充(在shims-vue.d.ts声明会使之前对.vue的声明、自定义模块的声明等全部失效。)。重点是模块补充和其他的分开两个文件写,也可以在shims-vue.d.ts中声明原型上的方法属性,在type.d.ts.vue声明ts识别处理vue文件。声明文件名遵循xxx.d.ts就可以。
原因:暂时不知道(待补充)
Q4:ts文件引入js报错
解决:

  1. 方法一:tsconfig.json设置allowJs:true
  2. 方法二:声明文件中声明模块
  3. 方法三:使用require导入

三、tsconfig.json文件配置项

1. target、module、lib
  • ES版本:ES6 == ES2015 ES7 == ES2016 ES8 == ES2017 ESNext(泛指) == es最新版本的下一版本
  • target:指定ECMAScript目标版本
    默认值:ES3
    选值:"ES5", "ES6"/ "ES2015", "ES2016", "ES2017"或 "ESNext"
  • module: 指定生成哪个模块系统代码
    默认值:target === "ES6" ? "ES6" : "commonjs"
    选值:"None", "CommonJS", "AMD", "System", "UMD", "ES6"或 "ES2015"
  • lib:编译过程中需要引入的标准库文件的列表
    默认值: - target ES5:DOM,ES5,ScriptHost
    - target ES6:DOM,ES6,DOM.Iterable,ScriptHos
  • types:要包含的类型声明文件名列表
    默认:所有可见的"@types"包会在编译过程中被包含进来;如果指定了types,只有被列出来的包才会被包含进来
    所以不清楚所有node_modules/@types中全局声明文件意义的时候,尽量不要单独设置types,可能会产生一些例如es语法无法匹配到标准库的bug

你可能感兴趣的:(2022-04-14使用ts重构vue2项目)