BinMaker 最早的项目用 Webpack:
npm run dev启动要等 40 秒,改一个字的样式也要等它重新编译。后来接手 Vite 项目——命令一点就开,改代码保存瞬间刷新。同样写前端,开发体验差了一个数量级。这篇按「会用」的标准讲 Vite:三条命令、常用配置、生产构建,够日常开发跑通。
一、Vite 是什么:dev 时根本不用打包
老一代构建工具(Webpack)的思路是打包:把所有模块(JS、CSS、图片)分析依赖、合并压缩成一个 bundle,浏览器才能跑。项目一大,打包就要等很久。
Vite 换了个思路:dev 时根本不打包。现代浏览器原生支持 ES Module——<script type="module"> 可以直接 import 别的文件。Vite 就把源码原样发给浏览器,浏览器自己按 import 链加载:
| 对比 | Webpack(老一代) | Vite |
|---|---|---|
| dev 时 | 先把全部模块打包成 bundle | 不打包,浏览器直接按 import 加载 |
| 启动速度 | 等打包,项目越大越慢 | 秒级,几乎不受项目规模影响 |
| 改代码刷新 | 重新编译相关模块 | 按模块热更新,改哪刷哪 |
| 生产构建 | 打包压缩 | 依然打包(用 Rollup) |
所以 Vite 有两套链路:dev 用「原生 ESM + esbuild」主打快,build 用「Rollup」主打稳。为什么生产构建不也用 esbuild,见 Vite 为什么这么快:dev 与 build 的双引擎。
二、三条命令跑起来
# 1. 初始化项目(--template 指定模板,vue / react / vanilla / svelte...)
npm create vite@latest my-app -- --template vue
# 2. 装依赖
cd my-app
npm install
# 3. 开发
npm run dev # 秒级启动,终端输出本地地址 http://localhost:5173
# 生产构建 + 预览
npm run build # 输出到 dist/(压缩、带 hash)
npm run preview # 本地起一个静态服务,预览 dist/ 产物不用脚手架也能用:一个 index.html + 一个 main.js + 一个 vite.config.js,装个 vite 就开跑,适合给老页面渐进引入:
<!-- index.html -->
<script type="module" src="/main.js"></script>// main.js —— 原生 ESM,浏览器直接加载
import { renderTable } from './table.js';
renderTable();三、目录结构:index.html 是入口
和 Webpack 最大的不同:入口是根目录的 index.html(Webpack 是 src 里的 JS 入口),Vite 以它为起点解析整个 import 链:
my-app/
├── index.html # 入口,script type="module" 指向 /src/main.js
├── vite.config.js # 配置(别名、代理、插件)
├── public/ # 原样拷贝的静态文件,路径写 /xxx.png
└── src/
├── main.js # 应用入口
├── App.vue
└── assets/ # 会被打包处理的资源(走 import 引入)四、常用配置三件套:别名、代理、环境变量
vite.config.js 用 defineConfig 包一层(为了 IDE 提示):
import { defineConfig } from 'vite';
import vue from '@vitejs/plugin-vue';
import path from 'node:path';
export default defineConfig({
plugins: [vue()],
resolve: {
alias: {
// 别名:@ 指到 src,写 import 不用数 ../../ 了
'@': path.resolve(__dirname, 'src'),
},
},
server: {
proxy: {
// 代理:前端请求 /api 自动转发到后端,联调必备
'/api': {
target: 'http://localhost:8080',
changeOrigin: true, // 让后端看到的是来自它的请求,不是 localhost:5173
},
},
},
});环境变量:项目根目录放 .env / .env.development / .env.production,只有 VITE_ 前缀的变量会暴露给前端:
# .env.development
VITE_API_BASE=/api// 代码里读:import.meta.env.VITE_API_BASE
const base = import.meta.env.VITE_API_BASE;三个环境(dev / build / preview)自动加载对应文件:dev 读 .env.development,build 读 .env.production,公共的放 .env。为什么用 import.meta.env 而不是 process.env——因为 dev 跑在浏览器里根本没有 Node 的 process,import.meta.env 是 Vite 在编译期注入的,build 后变量值直接替换进代码。
五、静态资源:public 和 assets 怎么选
| 目录 | 行为 | 适合放 |
|---|---|---|
public/ | 原样拷贝到 dist 根目录,路径写死 /logo.png | 不会被引用的(favicon)、要固定路径的 |
src/assets/ | 走 import 引入,打包时压缩 + 加内容 hash | 图片、字体等代码里用到的资源 |
判断标准:代码里用 import 引的就是 assets(享受 hash 缓存),否则放 public。assets 加 hash 的好处是文件名变了浏览器就知道该重新下载,public 的文件永远同名、容易命中过期缓存。
六、生产构建:dist 里有什么
npm run build产物在 dist/:JS/CSS 压缩合并、文件名带内容 hash(如 index-3f2a1b.js),静态资源按类型分目录。npm run preview 可以在本地起个静态服务模拟生产环境验证产物,上线前先跑它看一眼。
总结
| 要记住的 | 一句话 |
|---|---|
| dev 不打包 | 浏览器原生 ESM 加载源码,所以秒启 |
| 入口是 index.html | 根目录那个,不是 src 里的 JS |
| 配置三件套 | alias(路径)、proxy(联调)、env(环境变量) |
| build 用 Rollup | 生产才打包,压缩 + hash |
| 静态资源 | import 的走 assets,路径写死的走 public |
版本提醒:Vite 本文基于 Vite 8 实测;它不绑定 Vue,React、Svelte、原生 JS 都能用,模板不同而已。Vite 的 dev server 也是 Vue 快速入门 里 npm create vue@latest 的底层。
链式导航:想知道 Vite 为什么这么快(esbuild 预构建、HMR 原理、为什么 build 用 Rollup),看 Vite 为什么这么快:dev 与 build 的双引擎;模板语法和响应式是 Vue 快速入门 的内容;Vue 项目里状态管理用 Pinia 状态管理详解。
