Creating a TypeScript Project
To start a Vue 3 project with TypeScript, you can use Vue CLI. Follow these steps:
# Install Vue CLI
npm install -g @vue/cli
# Create a project
vue create my-ts-project
? Check the features needed for your project (Press <space> to select, <a> to toggle all, <i> to invert selection):
❯ TypeScript
Babel
PWA
Router
Vuex
CSS Pre-processors
Linter / Formatter
Unit Testing
E2E Testing
? Pick a TypeScript compiler that should be used in this project (Use arrow keys)
❯ Babel + TypeScript (JavaScript and TypeScript compilation with Babel, powered by @babel/preset-typescript)
TypeScript + ts-loader (Full TypeScript support with ts-loader)
TypeScript + babel-ts-loader (Full TypeScript support with babel-ts-loader)
Select the TypeScript option and complete the configuration as prompted.
Writing TypeScript Components
In Vue 3, you can use TypeScript in .vue files. Here’s an example of a simple component:
// src/components/HelloWorld.vue
<template>
<div>{{ message }}</div>
</template>
<script lang="ts">
import { defineComponent } from 'vue';
export default defineComponent({
name: 'HelloWorld',
props: {
msg: String,
},
setup(props) {
const message = `Hello, ${props.msg}!`;
return { message };
},
});
</script>
This defines a HelloWorld component that accepts a msg prop and displays a message in the template.
Writing a TypeScript Store
Pinia, the recommended state management library for Vue 3, integrates seamlessly with TypeScript.
// src/stores/user.ts
import { defineStore } from 'pinia';
export const useUserStore = defineStore('user', {
state: () => ({
name: '' as string,
age: 0,
}),
getters: {
fullName: (state) => `${state.name} Doe`,
},
actions: {
updateName(name: string) {
this.name = name;
},
},
});
This example defines a user Store with state, a getter, and an action, all typed for safety.
Handling Type Issues
When using TypeScript, you may encounter type-related issues, especially with ref or reactive. Explicitly define types to resolve them:
// src/components/Counter.vue
import { ref } from 'vue';
export default {
setup() {
const count = ref<number>(0);
const increment = () => {
count.value++;
};
return {
count,
increment,
};
},
};
Here, count is explicitly typed as a number to ensure type safety.
Writing TypeScript for Vue Router
Vue Router supports TypeScript, enhancing type safety with type declarations:
// src/router/index.ts
import { createRouter, createWebHistory } from 'vue-router';
import Home from '../views/Home.vue';
const routes = [
{
path: '/',
name: 'Home',
component: Home,
},
];
const router = createRouter({
history: createWebHistory(),
routes,
});
export default router;
This example sets up a type-safe router with a single route.
Writing TypeScript for Vue CLI Plugins
When developing Vue CLI plugins, TypeScript provides better type checking and editor support.
// src/plugin.ts
import { PluginObject } from '@vue/cli-service';
const plugin: PluginObject<any> = {
install: (_options, context) => {
context.service.addCommand({
name: 'my-command',
description: 'A custom command',
action: async () => {
console.log('Running my-command');
},
});
},
};
export default plugin;
This plugin defines a custom CLI command with TypeScript.
Writing TypeScript for Vue 3 Plugins
Vue 3 plugins can be written in TypeScript to ensure type correctness.
// src/plugins/my-plugin.ts
import { App } from 'vue';
const install = (app: App) => {
app.config.globalProperties.$myMethod = () => {
console.log('Calling myMethod');
};
};
export default { install };
This plugin adds a global method to the Vue app with type safety.
Writing TypeScript for Unit Tests
TypeScript enhances unit tests by ensuring type correctness in test code.
// tests/unit/components/HelloWorld.spec.ts
import { shallowMount } from '@vue/test-utils';
import HelloWorld from '@/components/HelloWorld.vue';
describe('HelloWorld.vue', () => {
it('displays the correct message', () => {
const wrapper = shallowMount(HelloWorld, {
props: {
msg: 'World',
},
});
expect(wrapper.text()).toContain('Hello, World!');
});
});
This test verifies the HelloWorld component’s output with type-safe code.
Writing TypeScript for Custom Directives
Vue 3 allows custom directives to be written in TypeScript for type safety.
// src/directives/focus.ts
import { DirectiveBinding } from 'vue';
const focus: DirectiveBinding<() => void> = {
mounted(el) {
el.focus();
},
};
export default focus;
This custom directive automatically focuses an element on mount, with typed bindings.
Writing TypeScript for Vue 3 Directives
Vue 3’s built-in directives can also leverage TypeScript for enhanced type safety.
Code Analysis
- Project Setup: Vue CLI simplifies creating TypeScript-enabled Vue 3 projects with configurable compiler options.
- Components: TypeScript in
.vuefiles ensures type-safe props and setup logic usingdefineComponent. - State Management: Pinia integrates seamlessly with TypeScript for typed stores, getters, and actions.
- Routing: Vue Router supports TypeScript for type-safe route definitions.
- Plugins and Directives: TypeScript enhances Vue CLI plugins, Vue 3 plugins, and custom directives with strict typing.
- Testing: TypeScript ensures type safety in unit tests, improving reliability and maintainability.



