Vitest测试Fastify应用报错:Plugin必须是函数或Promise
解决Fastify Autoload在Vitest测试中报错"Plugin must be a function or a promise"的问题
以下是几个针对性的解决方向,按优先级尝试:
1. 修正Vitest的依赖预构建配置
之前的inline依赖方案失效,大概率是Vitest预构建缓存或转译逻辑导致@fastify/autoload的模块格式被破坏。调整vitest.config.mts如下:
import { defineConfig } from 'vitest/config'; export default defineConfig({ test: { optimizeDeps: { // 强制Vitest正确处理autoload模块 include: ['@fastify/autoload', 'fastify'], esbuildOptions: { plugins: [ { name: 'resolve-autoload-correctly', setup(build) { build.onResolve({ filter: /@fastify\/autoload/ }, args => { return { path: require.resolve('@fastify/autoload') }; }); } } ] } }, // 暂时禁用测试缓存,避免旧缓存干扰 cache: false } });
原理:强制Vitest使用Node.js原生的模块解析逻辑加载@fastify/autoload,避免预构建过程中把插件转成Fastify无法识别的对象格式。
2. 测试环境按需注册插件而非使用Autoload
生产环境用Autoload批量加载插件,但测试场景可以手动注册所需插件,彻底绕开Autoload的加载问题:
import { fastify } from 'fastify'; import userRoutes from './routes/user'; import authPlugin from './plugins/auth'; test('user route returns 200', async () => { const app = fastify(); // 只注册当前测试需要的插件/路由 app.register(authPlugin); app.register(userRoutes); await app.ready(); const response = await app.inject({ method: 'GET', url: '/user' }); expect(response.statusCode).toBe(200); await app.close(); });
这种方式不仅能解决Autoload的测试问题,还能让测试更聚焦,避免无关插件干扰。
3. 确认Autoload与Fastify版本兼容性
Fastify 4.x对应@fastify/autoload的5.x版本,若你的Autoload版本不匹配,可能导致插件导出格式错误:
- 锁定兼容版本:
npm install @fastify/autoload@^5.0.0 --save
- 清理依赖缓存后重装:
rm -rf node_modules package-lock.json npm install
4. 调整Vitest的ESM转译设置
如果你的项目使用ESM格式,Vitest的默认转译可能破坏Fastify模块结构,修改配置让Node.js原生处理模块加载:
export default defineConfig({ test: { environment: 'node', esm: true, transformMode: { // 仅对前端文件启用转译,Node.js模块用原生加载 web: [/\.[jt]sx$/] } } });
内容的提问来源于stack exchange,提问作者rrcabrera9625
相关产品推荐
相关产品推荐

