Svelte+Inertia项目最终构建体积过大问题求助
我有一个仅含3个页面(登录页+2个其他页面)的Svelte+Inertia小型应用。开发模式下,其中一个页面组件大小为5KB,但构建后,rollup-plugin-visualizer显示该组件未压缩大小达62KB,以“库模式”构建的最终JS文件总大小为250KB,远超出预期的50KB左右。
- 编辑发现1:移除所有Inertia引用,仅在main.js中导入示例页面(无其他页面),结果仍相同:可视化工具显示该示例页面组件未压缩大小为62KB,而对应的MainPage.svelte文件在文件系统中仅为5KB。看起来可视化工具给出的是导入内容合并后的大小,尽管它仍将导入内容与Svelte组件分别显示为独立区块。
- 编辑发现2:在StackBlitz中从头尝试后发现,仅使用@inertiajs/svelte中的router就会立即使最终文件(已压缩、未缩小)增加110KB。
最终文件包含多个node模块:svelte占31KB、inertia占30KB、axios占95KB、qs占30KB、object-inspect占19KB等,这些模块未压缩总大小为250KB;而我自己的应用文件未压缩大小高达350KB,是文件系统中实际大小(含注释等共120KB)的三倍。
我无法理解为何单个文件从实际5KB变为可视化工具显示的62KB“rollup大小”。我一直偏好使用轻量库来最大化减小应用体积(考虑到移动网络较慢),但尝试Svelte后对如此微小应用的最终体积感到失望,希望将体积缩减至50KB左右。
是否有解决思路?我希望尽可能保留Svelte,若无法实现,是否有其他超轻量前端框架可选?
附上我的vite配置:
build: { outDir: '../server/dist', emptyOutDir: false, lib: { entry: path.resolve(__dirname, 'src/main.js'), name: 'xyz', // 该参数为必填,但实际不会用到 }, rollupOptions: { output: { entryFileNames: `js/[name].js`, chunkFileNames: `js/[name].js`, assetFileNames: `js/[name].[ext]` } } }
1. 切换构建模式,禁用库模式
当前使用lib模式构建会强制打包所有依赖,且无法应用应用级树摇优化,改为普通应用模式:
build: { outDir: '../server/dist', emptyOutDir: false, // 删除lib配置项 rollupOptions: { output: { entryFileNames: `js/[name].js`, chunkFileNames: `js/[name].js`, assetFileNames: `js/[name].[ext]` }, treeshake: 'strict' // 开启严格树摇 } }
2. 替换Inertia的冗余依赖
Inertia默认依赖的axios和qs是体积大头,可针对性替换:
- 用原生
fetch封装HTTP适配器,替代axios - 手动实现简单的查询参数拼接逻辑,移除qs依赖
3. 优化Svelte编译配置
在vite.config.js中添加Svelte专属优化:
import { svelte } from '@sveltejs/vite-plugin-svelte'; export default { plugins: [svelte({ compilerOptions: { dev: false, // 禁用开发特性 css: true // 开启CSS代码分割 }, onwarn: (warning, handler) => { if (warning.code === 'css-unused-selector') return; // 忽略未使用CSS选择器警告 handler(warning); } })], build: { compress: true, // 开启gzip压缩 reportCompressedSize: true // 输出压缩后体积报告 } }
4. 正确解读可视化工具数据
rollup-plugin-visualizer显示的“组件大小”是该组件及其所有导入依赖(如Svelte运行时、工具函数等)的合并体积,并非单个文件的原始大小。可点击区块展开,定位具体冗余依赖后针对性移除。
5. 代码层面精简
- 移除组件中未使用的导入和代码,开启ESLint的
no-unused-vars规则 - 避免导入整个库,仅引入需要的模块(如
import { debounce } from 'lodash-es'而非import _ from 'lodash') - 抽离通用逻辑为工具函数,避免重复打包
若上述优化仍无法达到体积要求,可考虑以下框架:
- Preact:React替代方案,核心体积仅4KB左右,API兼容React,生态完善
- SolidJS:编译型框架,类似Svelte,核心未压缩体积约7KB,性能优异
- Alpine.js:轻量交互框架,体积约7KB,无需构建,适合简单场景
- 原生JS:零依赖,完全自定义,体积最小
内容的提问来源于stack exchange,提问作者Aghyul Kyoku

