Vue 3 迁移指南
值得注意的新特性
Vue 3 中需要关注的一些新特性包括:
-
来自
@vue/runtime-core的createRendererAPI 用来创建自定义渲染函数 -
Suspense 实验性
*现在也支持在 Vue 2.7 中使用
**Vue 2.7 中支持,但仅用于类型推断
新的框架级别推荐#
Vue 3 的支持库进行了重大更新。以下是新的默认建议的摘要:
- 新版本的 Router, Devtools & test utils 来支持 Vue 3
- 构建工具链: Vue CLI -> Vite
- 状态管理: Vuex -> Pinia
- IDE 支持: Vetur -> Volar
- 新的 TypeScript 命令行工具: vue-tsc
- 静态网站生成: VuePress -> VitePress
- JSX:
@vue/babel-preset-jsx->@vue/babel-plugin-jsx
用于迁移的构建版本
@vue/compat (即“迁移构建版本”) 是一个 Vue 3 的构建版本,提供了可配置的兼容 Vue 2 的行为。
已知的限制
- 基于 Vue 2 内部 API 或文档中未记载行为的依赖。最常见的情况就是使用
VNodes上的私有 property。如果你的项目依赖诸如 Vuetify、Quasar 或 Element UI 等组件库,那么最好等待一下它们的 Vue 3 兼容版本。 - 对 IE11 的支持:Vue 3 已经官方放弃对 IE11 的支持。如果仍然需要支持 IE11 或更低版本,那你仍需继续使用 Vue 2。
- 服务端渲染:该迁移构建版本可以被用于服务端渲染,但是迁移一个自定义的服务端渲染配置还有很多工作要做。大致的思路是将
vue-server-renderer替换为@vue/server-renderer。Vue 3 不再提供一个包渲染器,且我们推荐使用 Vite 以支持 Vue 3 服务端渲染。如果你正在使用 Nuxt.js,可以尝试 Nuxt Bridge,一个 Nuxt.js 2 到 3 的兼容层。对于复杂、生产环境的项目来说,可能更好还是等待一下 Nuxt 3。
非兼容性改变
全局API
模板指令
v-model指令在组件上的使用已经被重新设计,替换掉了v-bind.sync- 在
<template v-for>和没有v-for的节点身上使用key发生了变化 v-if和v-for在同一个元素身上使用时的优先级发生了变化v-bind="object"现在是顺序敏感的v-on:event.native事件修饰符已经被移除
组件
- 函数式组件只能通过纯函数进行创建
- 单文件组件 (SFC)
<template>标签的functionalattribute 和函数式组件的functional选项已被移除 - 异步组件现在需要通过
defineAsyncComponent方法进行创建 - 组件事件现在应该使用
emits选项进行声明
渲染函数
- 渲染函数 API 更改
$scopedSlotsproperty 已移除,所有插槽都通过$slots作为函数暴露$listeners被移除或整合到$attrs$attrs现在包含class和styleattribute
自定义元素
其他小改变
destroyed生命周期选项被重命名为unmountedbeforeDestroy生命周期选项被重命名为beforeUnmount- Props 的
default工厂函数不再可以访问this上下文 - 自定义指令的 API 已更改为与组件生命周期一致,且
binding.expression已移除 data选项应始终被声明为一个函数- 来自 mixin 的
data选项现在为浅合并 - Attribute 强制策略已更改
- Transition 的一些 class 被重命名
<TransitionGroup>不再默认渲染包裹元素- 当侦听一个数组时,只有当数组被替换时,回调才会触发,如果需要在变更时触发,则必须指定
deep选项 - 没有特殊指令的标记 (
v-if/else-if/else、v-for或v-slot) 的<template>现在被视为普通元素,并将渲染为原生的<template>元素,而不是渲染其内部内容。 - 已挂载的应用不会替换它所挂载的元素
- 生命周期的
hook:事件前缀改为vue:
被移除的 API
keyCode作为v-on修饰符的支持- off 和 $once 实例方法
- 过滤器 (filter)
- 内联模板 attribute
$children实例 propertypropsData选项$destroy实例方法。用户不应该再手动管理单个 Vue 组件的生命周期。- 全局函数
set和delete以及实例方法$set和$delete。基于代理的变化检测已经不再需要它们了。