Vercel与本地构建Nuxt项目体积差异过大致部署失败求助
Nuxt部署Vercel遇Serverless函数体积超限问题
"Serverless函数"index"体积为119.68MB,超出50MB的最大限制。"
将Nuxt项目通过GitLab部署至Vercel时触发上述构建失败报错,但本地构建后dist文件夹仅约7.92MB,两者差异反常。需解答:
- 本地与Vercel构建体积差异的原因
- 如何排查Vercel上Nuxt项目的构建体积
- 针对该问题的解决方案
项目配置文件
nuxt.config.js
export default { // Global page headers: https://go.nuxtjs.dev/config-head head: { title: 'maimbau', htmlAttrs: { lang: 'en' }, meta: [ { charset: 'utf-8' }, { name: 'viewport', content: 'width=device-width, initial-scale=1' }, { hid: 'description', name: 'description', content: '' }, { name: 'format-detection', content: 'telephone=no' } ], link: [ { rel: 'icon', type: 'image/x-icon', href: '/favicon.ico' } ] }, // Server Configuration server: { port: 8000, // default: 3000 host: 'localhost', // default: localhost }, // other configs // Global CSS: https://go.nuxtjs.dev/config-css css: [ ], // Plugins to run before rendering page: https://go.nuxtjs.dev/config-plugins plugins: [ { src: '@/plugins/vue-awesome-swiper', mode: 'client' }, { src: "@/plugins/aos", ssr: false } ], // Auto import components: https://go.nuxtjs.dev/config-components components: true, // Modules for dev and build (recommended): https://go.nuxtjs.dev/config-modules buildModules: [ // https://go.nuxtjs.dev/eslint '@nuxtjs/eslint-module', // https://go.nuxtjs.dev/stylelint '@nuxtjs/stylelint-module', // https://go.nuxtjs.dev/tailwindcss '@nuxtjs/tailwindcss', ], tailwindcss: { configPath: 'tailwind.config.js', exposeConfig: false, config: {}, injectPosition: 0, }, // Modules: https://go.nuxtjs.dev/config-modules modules: [ // https://go.nuxtjs.dev/axios '@nuxtjs/axios', ], // Axios module configuration: https://go.nuxtjs.dev/config-axios axios: {}, // Build Configuration: https://go.nuxtjs.dev/config-build build: { postcss: { plugins: { tailwindcss: {}, autoprefixer: {}, "postcss-custom-properties": false }, }, }, buildDir: 'dist', router: { extendRoutes(routes, resolve) { routes.push({ name: 'demo_recipient', path: '/demo/undangan/:theme/:greeting/:recipient', component: resolve(__dirname, 'pages/demo/undangan/_theme.vue') }), routes.push({ name: 'webview_recipient', path: '/:catin/:greeting/:recipient', component: resolve(__dirname, 'pages/_catin/index.vue') }) } } }
package.json
{ "name": "maimbau", "version": "1.0.0", "private": true, "scripts": { "dev": "nuxt --hostname 0.0.0.0 --port 8000", "build": "nuxt build", "start": "nuxt start", "dev:local": "nuxt", "analyze": "nuxt build --analyze", "generate": "nuxt generate", "lint:js": "eslint --ext \"js,.vue\" --ignore-path .gitignore .", "lint:style": "stylelint \"**/*.{vue,css}\" --ignore-path .gitignore", "lint": "npm run lint:js && npm run lint:style" }, "dependencies": { "@nuxtjs/axios": "^5.13.6", "aos": "^2.3.4", "core-js": "^3.15.1", "firebase": "^9.8.0", "nuxt": "^2.15.8", "swiper": "^5.4.5", "vue-awesome-swiper": "^4.1.1", "vue-sweetalert2": "^5.0.2", "vue-tailwind-modal": "^1.0.7" }, "devDependencies": { "@babel/eslint-parser": "^7.14.7", "@nuxtjs/eslint-config": "^6.0.1", "@nuxtjs/eslint-module": "^3.0.2", "@nuxtjs/stylelint-module": "^4.0.0", "@nuxtjs/tailwindcss": "^4.2.1", "eslint": "^7.29.0", "eslint-config-prettier": "^8.3.0", "eslint-plugin-nuxt": "^2.0.0", "eslint-plugin-vue": "^7.12.1", "postcss": "^8.3.5", "prettier": "^2.3.2", "stylelint": "^13.13.1", "stylelint-config-prettier": "^8.0.2", "stylelint-config-standard": "^22.0.0" } }
问题分析与解决方案
本地与Vercel构建体积差异的核心原因
- 本地
dist文件夹仅包含Nuxt编译后的前端静态资源与服务端编译产物,但不包含运行时依赖包(即node_modules里的内容)。 - Vercel部署SSR模式的Nuxt项目时,会将整个服务端运行环境打包进Serverless函数,包括
dependencies下的所有依赖(比如体积较大的firebase全量包),这才是导致函数体积超限的关键。
排查Vercel构建体积的方法
- 查看Vercel构建日志:在项目控制台的构建记录中,找到Serverless函数打包阶段的输出,里面会有依赖包体积的明细,能快速定位大体积依赖。
- 本地生成构建分析报告:执行
npm run analyze,打开生成的分析页面,重点查看server bundle的组成,对应Vercel Serverless函数的核心内容。 - 检查依赖树:用
npm ls命令排查是否有冗余依赖、重复依赖被打包。
针对该项目的具体优化措施
优化Firebase引入方式
Firebase v9支持模块化导入,避免全量引入整个库,大幅减少体积:// 替换全量导入 import { initializeApp } from 'firebase/app' import { getFirestore } from 'firebase/firestore' // 仅导入你需要的模块,比如认证、存储等切换构建模式(可选)
如果项目不需要SSR渲染,将Vercel的构建命令改为nuxt generate,生成纯静态文件部署,完全规避Serverless函数体积限制。启用Nuxt代码分割与Tree-shaking
在nuxt.config.js的build配置中添加:build: { // 已有postcss配置... terser: { terserOptions: { compress: { drop_console: true } } }, splitChunks: { layouts: true, pages: true, commons: true }, extend(config, { isServer }) { if (isServer) { config.externals = { // 尝试将部分大依赖设为外部依赖,由Vercel环境提供(需确认兼容性) firebase: 'firebase' } } } }清理冗余依赖
检查dependencies中的包:swiper与vue-awesome-swiper是否可以替换为更轻量的轮播组件?- 确认
devDependencies中的工具类包没有被错误打包进生产构建(Vercel默认会区分,但可通过nuxt.config.js的build.exclude配置手动排除)。
内容的提问来源于stack exchange,提问作者Arbytes
相关产品推荐
相关产品推荐

