返回

Vue + TypeScript 踩坑记录

前端

前言

使用 Vue + TypeScript 可以带来很多好处,例如类型检查、代码重用性更高,以及更好的代码组织。但如果你是一个 Vue + TypeScript 的新手,那么你可能会遇到一些问题。本文记录了我个人在使用 Vue + TypeScript 时踩过的坑,希望能够帮助其他开发者避免这些问题。

踩过的坑

将 shims-vue.d.ts 文件一分为二

当你第一次使用 Vue + TypeScript 时,你会看到一个名为 shims-vue.d.ts 的文件。这个文件包含了 Vue.js 的类型声明,它可以帮助 TypeScript 编译器理解 Vue.js 的代码。

但是,这个文件很大,而且它包含了很多我们不需要的类型声明。因此,我们可以将这个文件一分为二。我们可以创建一个名为 shims-vue.base.d.ts 的文件,它只包含 Vue.js 的核心类型声明。然后,我们可以创建一个名为 shims-vue.user.d.ts 的文件,它包含我们自己写的类型声明。

使用 TypeScript 的非空断言运算符 (!)

TypeScript 的非空断言运算符 (!) 可以让我们告诉编译器,我们确信某个值不是 null 或 undefined。这可以帮助我们避免一些错误,但它也可能会导致一些问题。

例如,如果你有一个组件,它有一个名为 name 的属性。如果你想在组件的模板中使用这个属性,你可能会写出这样的代码:

<template>
  <div>{{ name }}</div>
</template>

但是,如果组件的 name 属性是 null 或 undefined,那么这段代码就会抛出一个错误。为了避免这个错误,你可以使用非空断言运算符:

<template>
  <div>{{ name! }}</div>
</template>

但是,如果你真的不确定 name 属性是否为 null 或 undefined,那么你最好不要使用非空断言运算符。因为这样可能会导致一些难以调试的错误。

使用 TypeScript 的可选链操作符 (?.)

TypeScript 的可选链操作符 (?.) 可以让我们安全地访问对象属性。例如,如果你有一个组件,它有一个名为 user 的属性,而 user 属性又有一个名为 name 的属性。如果你想在组件的模板中使用 user.name,你可能会写出这样的代码:

<template>
  <div>{{ user.name }}</div>
</template>

但是,如果 user 属性是 null 或 undefined,那么这段代码就会抛出一个错误。为了避免这个错误,你可以使用可选链操作符:

<template>
  <div>{{ user?.name }}</div>
</template>

这样,如果你想访问 user.name 时,user 属性是 null 或 undefined,那么可选链操作符就会返回 undefined,而不会抛出一个错误。

使用 TypeScript 的 generics

TypeScript 的 generics 可以让我们编写可重用的代码。例如,你可以编写一个名为 List 的组件,它可以接受任何类型的元素。然后,你就可以用这个组件来创建列表,其中包含任何类型的元素。

// List.vue
<template>
  <ul>
    <li v-for="item in items" :key="item">
      {{ item }}
    </li>
  </ul>
</template>

<script>
export default {
  props: {
    items: {
      type: Array,
      required: true,
    },
  },
};
</script>
<!-- App.vue -->
<template>
  <List :items="['a', 'b', 'c']" />
  <List :items="['1', '2', '3']" />
</template>

<script>
import List from './List.vue';

export default {
  components: {
    List,
  },
};
</script>

但是,如果你想使用 generics,你需要注意一些问题。例如,你不能使用 generics 来访问对象的属性。如果你想访问对象的属性,你需要使用类型断言。

// List.vue
<template>
  <ul>
    <li v-for="item in items" :key="item">
      {{ (item as any).name }}
    </li>
  </ul>
</template>

避免在 Vue 的 computed 属性中使用箭头函数

如果你在 Vue 的 computed 属性中使用箭头函数,那么你可能会遇到一些问题。例如,你不能在箭头函数中使用 this 。如果你想在箭头函数中使用 this 关键字,那么你必须使用一个箭头函数。

// App.vue
export default {
  computed: {
    // 不要使用箭头函数
    name() {
      return this.firstName + ' ' + this.lastName;
    },
    // 使用箭头函数
    fullName: () => {
      return this.firstName + ' ' + this.lastName;
    },
  },
};

总结

这些是我在使用 Vue + TypeScript 时踩过的坑。如果你是一个 Vue + TypeScript 的新手,那么我希望这篇文章能帮助你避免这些问题。