在Node.js Firebase函数中导入JSX文件失败的问题排查
解决Firebase函数中导入React JSX文件时的模块找不到问题
问题场景
我在Node.js Firebase函数中尝试导入React JSX文件TestEmail.jsx,导入代码:
import TestEmail from "./TestEmail.jsx";
函数完整代码:
import {SendGridHelper} from "./sendgrid"; import {logError} from "../../../../../helpers/logger"; import TestEmail from "./TestEmail.jsx"; import {render} from '@react-email/render'; export async function getSendEmail(): Promise<void> { const sendGridHelper = new SendGridHelper(process.env.SENDGRID_API_KEY); const emailHtml = render(TestEmail({ username: "Bob" })); await sendGridHelper .sendEmail( "Test", { name: "Name", email: "noreply@example.com", }, "bob@example.com", { html: emailHtml, }, ) .catch((e) => { logError( e, "Error sending email", `Test`, JSON.stringify(e?.response.body) ); }); }
路由配置:
setupRoutes( app, [ { path: "/v1/public/profiles/email", method: HttpMethod.GET, func: getSendEmail, }, ], true ); export const publicProfiles = https.onRequest(app);
React邮件组件代码:
import { Body, Container, Font, Head, Heading, Html, Preview, Tailwind, } from '@react-email/components'; export const TestEmail = ({username = 'Bob', }) => { const previewText = `Join ${username}`; return ( <Html> <Head> <Font fontFamily="Inter" fallbackFontFamily="Verdana" webFont={{ url: 'https://fonts.googleapis.com/css?family=Inter&display=swap', }} fontWeight={400} fontStyle="normal" /> </Head> <Preview>{previewText}</Preview> <Tailwind> <Body className="bg-[#0f0f12] my-auto mx-auto font-sans"> <Container className="rounded-xl my-[40px] mx-auto p-[20px] max-w-[600px] bg-[#18181b]"> <Heading className="text-white text-[24px] font-normal text-center p-0 my-[30px] mx-0"> Join <strong>{username}</strong> </Heading> </Container> </Body> </Tailwind> </Html> ); }; export default TestEmail;
运行Firebase函数模拟器时出现报错:
⬢ functions: Failed to load function definition from source: FirebaseError: Failed to load function definition from source: Failed to generate manifest from function source: Error: Cannot find module './TestEmail.jsx'
IDE可正常定位文件,但模拟器报错,需解决该问题。
解决方案
1. 核对文件路径与大小写
- 确认
TestEmail.jsx与函数文件处于同一目录,注意Firebase部署环境为Linux,文件名区分大小写,需确保导入路径的大小写与实际文件名完全一致(比如testemail.jsx和TestEmail.jsx会被视为不同文件)。 - 检查导入路径的层级是否正确,
./代表当前目录,避免多写或漏写目录层级。
2. 配置Firebase函数支持JSX转译
Firebase函数默认不处理JSX语法,需添加构建工具支持:
- TypeScript环境:在
tsconfig.json中,确保include数组包含.jsx文件,同时compilerOptions设置:{ "compilerOptions": { "jsx": "react-jsx", "moduleResolution": "node16" }, "include": ["src/**/*.ts", "src/**/*.jsx"] } - JavaScript环境:使用Babel转译,在函数目录下创建
babel.config.json:
安装依赖:{ "presets": ["@babel/preset-react", "@babel/preset-env"] }npm install @babel/core @babel/preset-react @babel/preset-env --save-dev - ESBuild配置:在
firebase.json的functions节点添加ESBuild支持,指定JSX loader:"functions": { "source": "functions", "runtime": "nodejs18", "esbuild": { "loader": { ".jsx": "jsx" }, "external": ["firebase-admin"] } }
3. 配置Node.js识别JSX扩展名
Node.js默认不支持.jsx作为模块扩展名,需在package.json中添加配置:
{ "type": "module", "imports": { ".jsx": "./*.jsx" } }
如果使用TypeScript,需在tsconfig.json的compilerOptions中设置:
"moduleResolution": "node16", "allowJs": true, "resolveJsonModule": true
4. 清理Firebase模拟器缓存
缓存可能导致文件检测异常,执行命令清理缓存后重启模拟器:
firebase emulators:start --clear-cache
也可手动删除函数目录下的node_modules/.cache文件夹(若存在)。
5. 确认文件被包含在构建输出中
检查函数的构建脚本,确保.jsx文件被正确转译或复制到构建输出目录。例如,若使用npm run build脚本,需确保构建工具(如ESBuild、Babel)将JSX文件处理为可执行的JavaScript文件。
内容的提问来源于stack exchange,提问作者strangeQuirks
相关产品推荐
相关产品推荐

