Use Typescript in Existing Vue 3 Project

  1. Install the necessary dependencies
  2. Add TypeScript configuration files
  3. Add scripts
  4. Change file extensions
  5. Refactor the components
    1. Options API
    2. Composition API

Suppose you have created a Vue 3 project with the command npm create vue@latest and it is not integrated with TypeScript yet.

Install the necessary dependencies

To use TypeScript, we will need to need a few dependencies:

1
npm i -D @tsconfig/node20 @types/node @vue/tsconfig npm-run-all2 vue-tsc typescript

Add TypeScript configuration files

We need to add a tsconfig.json file in the root directory of the project. You can generate a basic one by running:

1
npx tsc ---init

Vue has a package called @vue/tsconfig, which contains the configuration files specific for Vue projects.

Based on this package, we can write like this in tsconfig.json:

1
2
3
4
5
6
7
8
9
10
11
{
"files": [],
"references": [
{
"path": "./tsconfig.node.json"
},
{
"path": "./tsconfig.app.json"
}
]
}

tsconfig.node.json:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
{
"extends": "@tsconfig/node20/tsconfig.json",
"include": [
"vite.config.*",
"vitest.config.*",
"cypress.config.*",
"nightwatch.conf.*",
"playwright.config.*"
],
"compilerOptions": {
"composite": true,
"noEmit": true,
"tsBuildInfoFile": "./node_modules/.tmp/tsconfig.node.tsbuildinfo",

"module": "ESNext",
"moduleResolution": "Bundler",
"types": ["node"]
}
}

tsconfig.app.json:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
{
"extends": "@vue/tsconfig/tsconfig.dom.json",
"include": ["env.d.ts", "src/**/*", "src/**/*.vue"],
"exclude": ["src/**/__tests__/*"],
"compilerOptions": {
"composite": true,
"tsBuildInfoFile": "./node_modules/.tmp/tsconfig.app.tsbuildinfo",

"baseUrl": ".",
"paths": {
"@/*": ["./src/*"]
}
}
}

env.d.ts:

1
/// <reference types="vite/client" />

Add scripts

Edit package.json then add or edit the following scripts:

1
2
3
4
5
6
7
8
9
{
"scripts": {
"dev": "vite",
"build": "run-p type-check \"build-only {@}\" --",
"preview": "vite preview",
"build-only": "vite build",
"type-check": "vue-tsc --build --force"
}
}

Change file extensions

Rename vite.config.js and main.js to vite.config.ts and main.ts respectively.

Refactor the components

Options API

To let TypeScript properly infer types inside component options, we need to define components with defineComponent():

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
import { defineComponent } from "vue";

export default defineComponent({
// type inference enabled
props: {
name: String,
msg: { type: String, required: true },
},
data() {
return {
count: 1,
};
},
mounted() {
this.name; // type: string | undefined
this.msg; // type: string
this.count; // type: number
},
});

Composition API

To use TypeScript in SFCs, add the lang="ts" attribute to <script> tags.

1
2
3
4
5
6
7
8
9
10
11
<script setup lang="ts">
// TypeScript enabled
import { ref } from 'vue'

const count = ref(1)
</script>

<template>
<!-- type checking and auto-completion enabled -->
{{ count.toFixed(2) }}
</template>

Now try running the project:

1
npm run dev