Using typescript in Vue

Time:2020-2-8

Preface

  With all due respect, it’s really hard to write Vue in typescript. Vue’s support for TS is general. Don’t use it in Vue unless you have to. However, it’s said that vue3 will enhance its support for ts. I’d like to look forward to it before it’s officially launched.

This article will not talk too much about TS syntax, focusing on recording the method of using ts in Vue and the process of stepping on the pit.

If you are building a project with Vue cli2, please note that the webpack version may not match the TS loader version. You can reduce the TS loader version to 3.0 + or upgrade the webpack to 4.0 + (the version used in this article is webpack @ 3.6.0 + TS loader @ 3.5.0)

Main steps

1. First, make the Vue project recognize the. TS file. Installation key depends on NPM I typescript ts-loader-d

2. Add TS loader in webpack.base.config.js

//After adding. TS suffix to resolve.extensions, you can import. TS without suffix
{
  test: /\.tsx?$/,
  loader: 'ts-loader',
  exclude: /node_modules/,
  options: { 
    Appendtsuffixto: [/ \. Vue $/], // critical
  }
}

  3. Create the configuration below the tsconfig.json file in the root directory for reference only

{
  "include": [
    "src/**/*"
  ],
  "exclude": [
    "node_modules"
  ],
  "compilerOptions": {
    "allowSyntheticDefaultImports": true,
    "experimentalDecorators": true,
    "allowJs": true,
    "module": "esnext",
    "target": "es5",
    "moduleResolution": "node",
    "isolatedModules": true,
    "lib": [
      "dom",
      "es5",
      "es2015.promise"
    ],
    "sourceMap": true,
    "pretty": true
  }
}

  4. Then we need to ensure that ts can be used normally in Vue. Install Vue class component and Vue property decorator [tslint tslint loader tslint config standard (optional constraint. TS /. TSX code format)], so that you can use decorators such as @ component and @ prop in the Vue file. Note: lang = “ts” should be added to the script tag in the. Vue file. For the use of decorators, please refer to the following article: https://segmentfault.com/a/11900019906321

import { Component, Prop, Vue, Emit } from "vue-property-decorator"
import moment from 'moment'

@Component
export default class CountDown extends Vue {
    @Prop() endDate!: string
    //Variable after! Is not null assertion

    now: any = moment()
    mounted() {
        setInterval((): void =>{
            this.now = moment()
        },1000)
    }
    destroyed() {
        
    }
    get countDown(): object{
        return function(endDate: any): string {
            let m1: any = this.now
            let m2: any = moment(endDate)
            let du: any = moment.duration(m2 - m1, 'ms')
            let hours: number = du.get('hours')
            let mins: number = du.get('minutes')
            let ss: number = du.get('seconds')
            if(hours <= 0 && mins <= 0 && ss <= 0) {
                // this.$emit('timeout')
                this.timeout()
                Return "today is over."
            }else {
                Return ` ${this. Prefixinteger (hours, 2)} < span style = "font size: 16px;" > hour < / span > ${this. Prefixinteger (mins, 2)} < span style = "font size: 16px;" > minute < / span > < span style = "color: # f56c6c;" >`
            }
        }
    }

    @Emit()
    timeout(){}

    
    //Add 0 before the number 
    //Num incoming number, n required character length
    PrefixInteger(num: number, n: number): string {
        return (Array(n).join('0') + num).slice(-n)
    }
}



//...

 

  5. Change main.js to main.ts and change the entry to main.ts in webpack.base.conf.js. This step is very important.

6. Create a new file shims-vue.d.ts in the SRC directory, and tell typescript *. Vue suffix files to be handed over to the Vue module for processing. Note that when importing *. Vue files into the code, you need to write the. Vue suffix. Here, you can refer to the official website description: enhanced type to match plug-in use

declare module "*.vue" {
    import Vue from "vue";
    export default Vue;
}

Record of pits

  1. The error is reported as follows. The first reason is that the entry file has not been changed to TS, and the second reason is that the TS loader error has been introduced into webpack.base.conf.js without options: {appendtsaffixto: [/ \. Vue $/],}

Module build failed: Error: Could not find source file: 'XXX/src/App.vue'.

  2. For example, vue.prototype. $MSG = XXX, the global attribute should be declared in the. D.ts file

import Vue from "vue";
import { AxiosInstance } from "axios";
import { ElMessage } from "element-ui/types/message";

declare module "*.vue" {
    export default Vue;
}

declare module 'vue/types/vue' {
    interface Vue {
        $http: AxiosInstance,
        $message: ElMessage
    }
}

  3. Using the above method to declare global attributes will bring new problems. An error is reported in the “import app from ‘. / APP. Vue”. The module app.vue can’t be found. Although it doesn’t affect compilation, the red wavy line is like rat shit. It’s hard to see. Solution: divide the shims-vue.d.ts file into two parts, separate the global attribute declaration and Vue declaration; create a new vue.d.ts in the same level directory of the shims-vue.d.ts file (the name may not necessarily be Vue, such as XXX. D.ts); the key is to put the following code in a separate. D.ts file

declare module '*.vue' {
  import Vue from 'vue'
  export default Vue
}

Recommended Today

Analysis of new data type instances of ES6 learning notes

An example of this paper describes the new data types of ES6 learning notes. To share with you for your reference, as follows: 1. Data deconstruction assignment 1. Deconstruction and assignment of arrays Basic usage: let [key1, key2…] = [value1, Value2…] Let [name, age, sex] = [‘xiaoming ‘, 24,’ male ‘]; console.log(name); console.log(age); console.log(sex); Note […]