前言
在使用webpack构建项目,或直接用脚手架vue-cli构建的vue项目中,构建速度一直是个令人闹心的问题,有时项目庞大,依赖过多时,那速度更是令人堪忧,开发体验非常的差。于是我就想,vite都出来这么久了,可不可以把我现在在做的项目的构建工具换成vite呢?说干就干,谁怕谁!能跑就行。
了解vite
既然要使用vite构建,那么在使用之前,先简单了解下vite vite官网
迁移vite
大概了解了vite之后,接下来就是进行迁移工作了。
迁移前项目技术栈介绍
- 技术栈: vue2.7(支持部分vue3的语法) + TypeScript(4.1.5) + vue-router(3.6.4) + vuex(3.4.0) + 其它
- 构建工具:vue-cli (4.5.15)
注:由于使用的是vue2.7,项目中还使用了vue3的语法,所以在迁移过程中一些依赖的版本需要注意下,一不小心版本不兼容项目可能就跑不了了
删除不需要的依赖
- 删除vue-cli相关的依赖
vue.config.js配置文件也可以删了
- vite对常用的css预处理器提供了开箱即用的支持,所以sass-loader也可以删除
- 删除vue模板编译器插件vue-template-compiler,vite这个将由vite的插件处理
- babel相关的插件也删掉,不需要了 (Vite 以 原生 ESM 方式提供源码)
babel 相关的配置也删除掉
babel.config.js配置文件也可以删掉了
- 其它不可用插件也需要删除,换成vite支持的,如果没有就可能需要自己写个vite插件或者使用别的替代方案
新增相关依赖
- vite
- node类型支持: @types/node
- vue2解析: @vitejs/plugin-vue2
- eslint: eslint(版本调整)、eslint-plugin-vue(版本调整)、@vue/eslint-config-typescript、vite-plugin-eslint
- 浏览器兼容:@vitejs/plugin-legacy、terser
新增后如下,部分依赖需要注意下版本
添加vite配置文件vite.config.ts
直接上配置(需要更多自定义或扩展功能可以自行配置)
移动并修改index.html文件
- 移动文件
在使用vue-cli构建时,index.html文件可能放在public文件夹中,改成vite构建后,入口文件是index.html,所以需要把index.html文件放到项目的根目录下
- 修改index.html文件
去除文件中的占位符
// index.html
<!--remove-->
<title><%= htmlWebpackPlugin.options.title %></title>
<!--add-->
<title>Hard Coded Title</title>
//...
<!--remove-->
<strong>We're sorry but <%= htmlWebpackPlugin.options.title %> doesn't work properly without JavaScript enabled. Please enable it to continue.</strong>
<!--add-->
<strong>We're sorry but this app doesn't work properly without JavaScript enabled. Please enable it to continue.</strong>
// index.html
<!--remove-->
<link rel="icon" href="<%= BASE_URL %>favicon.ico">
<!--add-->
<link rel="icon" href="/favicon.ico">
javaScript已经不是自动注入了,需要手动引入
package.json修改运行脚本命令
配置环境变量
如果项目中需要用到环境变量,可以配置下环境变量
修改.eslintrc.js
供参考
集成TS类型检查工具vue-tsc
vite只有ts转译的功能,没有集成ts的类型检查,所以想要进行类型检查只能靠IDE或者自己配置集成
本项目将集成vue-tsc作为类型检查工具
首先安装vue-tsc依赖,这里建议版本不要高于1.0.8,不然可能追踪方法会报错导致检查报错
添加校验命令,这里打包的时候也添加了校验,校验失败就会打包失败(
配置到git提交代码之前校验,防止不规范代码的提交(结合husky工具使用)
对vue的template的校验比较恶心,可能还不成熟,个人觉得也没太必要校验,这个在tsconfig.json中配置下跳过就行
解决报错问题
迁移vite的配置相关工作已经基本完成了,接下来就是安装依赖,将项目跑起来了,如果你的项目小,代码少,运气好的话可能一次性就能跑成功了,但是正常项目这时候跑起来一般会有一大推报错,接下来就记录下本人迁移过程中遇到的一些错误及解决方案
- eslint 代码检查方面的报错
解决这个问题就是按照eslint的配置规范修改代码,如果不想修改也可以修改eslint的配置(不建议这么做)
建议可以把eslint的问题放到最后解决,可以在vite.config.ts中先把eslint关了,等项目能够成功跑起来在打开解决eslint问题
- 使用commonJs语法或者node专有的导致的报错问题
1、 process.env.BASE_URL process undefined
可以做以下修改
2、使用require导致的报错
可以改成import的方式显示的引入
使用new URL(url, import.meta.url)
import.meta.globEager替代require.context动态引入方案
- 引入资源找不到问题
比如下面这个问题,引入的是一个静态资源目录中的一个文件
在vite的官网中发现了以下说明
所以需要避免下这种情况,可以考虑改成javaScript动态的方式,比如当前这个问题可以用以这个方法解决
- 解决jsx报错问题
如果项目中使用了jsx语法,script需要加上lang="jsx"
- sockjs-client包引入后包代码有报错
做以下修改解决
- svg图标没了
本迁移项目中使用svg雪碧图,vue-cli构建时使用了svg-sprite-loader这个插件来进行加载,但是这个插件只支持webpack,所以在vite构建环境下是不可用的,这时候就需要寻找其它方法了
在网上找了一圈,没有找到比较好的现成可用的vite插件,于是就自己参考资料写了一个vite插件来处理svg,最后发布到公司内部的npm
插件代码比较少,逻辑也很简单,这里直接粘上代码供参考
const fs = require('fs')
let idPerfix = ''
const svgTitle = /<svg([^>+].*?)>/
const clearHeightWidth = /(width|height)="([^>+].*?)"/g
const hasViewBox = /(viewBox="[^>+].*?")/g
const clearReturn = /(\r)|(\n)/g
// 查找svg文件
function svgFind (e) {
const arr = []
const dirents = fs.readdirSync(e, { withFileTypes: true })
for (const dirent of dirents) {
if (dirent.isDirectory()) arr.push(...svgFind(e + dirent.name + '/'))
else {
const svg = fs.readFileSync(e + dirent.name)
.toString()
.replace(clearReturn, '')
.replace(svgTitle, ($1, $2) => {
let width = 0
let height = 0
let content = $2.replace(clearHeightWidth, (s1, s2, s3) => {
if (s2 === 'width') width = s3
else if (s2 === 'height') height = s3
return ''
})
if (!hasViewBox.test($2)) {
content += `viewBox="0 0 ${width} ${height}"`
}
return `<symbol id="${idPerfix ? idPerfix + '-' : ''}${dirent.name.replace(
'.svg',
''
)}" ${content}>`
})
.replace('</svg>', '</symbol>')
arr.push(svg)
}
}
return arr
}
// 生成svg
exports.loadSvgSprite = (path, perfix = '') => {
if (path === '') return
idPerfix = perfix
const res = svgFind(path)
return {
name: 'svg-transform',
transformIndexHtml (dom) {
return dom.replace(
'<body>',
`<body><svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" style="position: absolute; width: 0; height: 0">${res.join('')}</svg>`
)
}
}
}
- 页面切换慢,特别是资源加载多的时候
针对这个问题,专门写了一篇文章总结了解决方案:vite构建的项目开发环境页面首次加载慢如何解决? - 掘金 (juejin.cn)