在PUG引擎中使用Nodemailer遭遇require未定义问题求助
解决PUG中使用Nodemailer时"require is not defined"的问题
这个错误的核心原因很直白:require是Node.js专属的模块加载语法,浏览器环境(包括PUG渲染后在前端运行的<script>标签)完全不支持这个功能。你的Nodemailer代码是纯服务器端逻辑,根本不能直接放到客户端脚本里执行。
下面是具体的解决方案,分两步走:
1. 把Nodemailer代码留在服务器端,封装成API接口
先保留你原本能正常运行的Nodemailer代码,把它改成可被接口调用的函数,比如用Express框架创建一个POST接口:
// 服务器端的 mail-service.js 文件 "use strict"; const nodemailer = require("nodemailer"); let config = require("../js/config"); // 封装邮件发送函数 async function sendStudyListEmail() { // 创建 transporter 实例(和你原来的代码一致) let transporter = nodemailer.createTransport({ host: "mail.mywebsite.com", port: 8889, secure: false, // true 对应465端口,其他端口用false auth: { user: config.user, pass: config.pass }, }); // 可选:验证服务器连接 transporter.verify(function(error, success) { if (error) { console.error("邮件服务器连接失败:", error); } else { console.log("邮件服务器已就绪"); } }); // 发送邮件 let info = await transporter.sendMail({ from: '"E-Mail Service ☕" <me@mywebsite.com>', to: "customer@domain.com", subject: "Your List of Selected Studies 📌", html: "<b>Test e-mail</b> starts here. And ends <i>here</i>", }); console.log("邮件已发送,Message ID:", info.messageId); return info; } // 导出函数供路由使用 module.exports = sendStudyListEmail;
然后在你的Express路由中添加一个POST接口,用来触发这个邮件发送函数:
// 服务器端的 routes/email.js 文件 const express = require('express'); const router = express.Router(); const sendStudyListEmail = require('../mail-service.js'); // 创建发送邮件的接口 router.post('/send-study-email', async (req, res) => { try { const emailInfo = await sendStudyListEmail(); res.status(200).json({ success: true, message: "邮件发送成功", messageId: emailInfo.messageId }); } catch (err) { console.error("发送邮件出错:", err); res.status(500).json({ success: false, message: "邮件发送失败", error: err.message }); } }); module.exports = router;
别忘了把这个路由挂载到你的Express主应用里:
// 服务器端的 app.js 文件 const emailRoutes = require('./routes/email'); app.use('/api', emailRoutes);
2. 在PUG的客户端脚本中调用服务器接口
现在,你可以在PUG文件里写客户端脚本,通过AJAX请求调用上面的服务器接口,触发邮件发送:
// 你的PUG文件内容 html body h1 邮件发送测试 // 添加一个按钮触发邮件发送 button#sendEmailBtn 发送测试邮件 script. // 客户端脚本:调用服务器接口 const sendBtn = document.getElementById('sendEmailBtn'); sendBtn.addEventListener('click', async () => { try { sendBtn.disabled = true; sendBtn.textContent = '发送中...'; const response = await fetch('/api/send-study-email', { method: 'POST', headers: { 'Content-Type': 'application/json' // 如果需要动态传递收件人、邮件内容,可以在这里加body // body: JSON.stringify({ to: 'user@example.com', subject: '自定义主题' }) } }); const result = await response.json(); if (result.success) { alert(`邮件发送成功!Message ID: ${result.messageId}`); } else { alert(`邮件发送失败:${result.message}`); } } catch (err) { console.error('请求出错:', err); alert('请求出错,请稍后重试'); } finally { sendBtn.disabled = false; sendBtn.textContent = '发送测试邮件'; } });
重要注意事项
- 绝对不要把邮箱的账号密码暴露在客户端代码里:你的
config.js里的user和pass必须留在服务器端,一旦泄露到前端,任何人都可以用你的邮箱发送垃圾邮件。 - 如果需要动态传递邮件内容(比如用户输入的收件人、自定义正文),可以通过POST请求的
body参数传给服务器,服务器接收后再调整sendMail的参数即可。 - 确保你的服务器已经正确配置了CORS(如果前端和后端不在同一个域名下),不过如果是同域名部署的话,这一步可以忽略。
内容的提问来源于stack exchange,提问作者mustafau.
相关产品推荐
相关产品推荐

