在Vercel部署Express REST API时遇"No exports found in module"错误求助
问题:Express API部署到Vercel出现500内部服务器错误
部署Express REST API到Vercel后,在「Functions」标签页遇到500: INTERNAL_SERVER_ERROR(错误码:FUNCTION_INVOCATION_FAILED),日志信息如下:
2023-02-25T11:38:34.982Z 553b0c7a-952a-4944-8842-acf218dde8a0 ERROR No exports found in module "../src/index.js". 2023-02-25T11:38:34.983Z 553b0c7a-952a-4944-8842-acf218dde8a0 ERROR Did you forget to export a function or a server? RequestId: 553b0c7a-952a-4944-8842-acf218dde8a0 Error: Runtime exited with error: exit status 1 Runtime.ExitError
原因分析
Vercel的Serverless Functions环境要求入口文件必须导出一个可处理HTTP请求的函数或服务器实例,而你的index.js仅执行数据库连接和服务器启动,没有任何导出内容,导致Vercel无法识别处理请求的入口。
同时,本地环境通过app.listen启动服务器是没问题的,但在Serverless环境中,不需要手动启动服务器,而是由Vercel的运行时接管请求转发。
解决方案
1. 修改index.js,导出Express App并优化数据库连接
将原来的代码调整为导出Express实例,并避免重复连接数据库(Serverless环境可能多次初始化实例):
/* eslint-disable no-console */ import dotenv from 'dotenv'; import mongoose from 'mongoose'; import app from './app'; dotenv.config(); const { DATABASE_URL } = process.env; // 避免重复建立数据库连接 const connectDB = async () => { // 检查当前连接状态,0代表未连接 if (mongoose.connection.readyState === 0) { try { await mongoose.connect(DATABASE_URL); console.log('Connected to database'); } catch (error) { console.error('Fail connection to database', error); } } }; // 初始化数据库连接 connectDB(); // 导出Express App供Vercel处理请求 export default app;
2. 适配Babel编译(可选但推荐)
由于你使用了ES模块语法(import/export),需要确保Vercel能正确编译代码。在package.json中添加build脚本:
{ "scripts": { // ...原有脚本 "build": "babel src --out-dir dist" } }
3. 更新vercel.json配置
如果添加了build脚本,修改vercel.json指向编译后的文件;如果直接使用源码,确保配置正确:
编译后的配置(推荐)
{ "version": 2, "builds": [ { "src": "dist/index.js", "use": "@vercel/node" } ], "routes": [ { "src": "/(.*)", "dest": "dist/index.js" } ] }
源码直接使用的配置
{ "version": 2, "builds": [ { "src": "src/index.js", "use": "@vercel/node", "config": { "includeFiles": ["src/**/*"] } } ], "routes": [ { "src": "/(.*)", "dest": "src/index.js" } ] }
4. 验证环境变量
确保Vercel项目的环境变量中已正确配置DATABASE_URL,可以在Vercel项目的「Settings」→「Environment Variables」中检查。
关键注意点
- Serverless环境中不需要调用
app.listen(),Vercel会自动处理请求转发到你的Express App。 - 数据库连接需要做重复连接检查,避免每次函数调用都建立新连接导致资源浪费。
- ES模块语法需要确保Vercel能正确识别,通过Babel编译为CommonJS是最稳妥的方式。
内容的提问来源于stack exchange,提问作者Damian Palavecino
相关产品推荐
相关产品推荐

