无法使用SES / Lambda发送电子邮件,但代码适用于容器

问题描述 投票:0回答:1

我有一个lambda函数,它接收一堆信息然后做一些事情就是使用SES发送电子邮件。我目前有代码发送电子邮件在容器中工作,但我已经决定使用AWS步骤函数,所以我将它转换为Lambda函数。从理论上讲,应该没有重大差异,但我无法收到电子邮件。

要求发送电子邮件的功能:

const sendEmail = require('./utils/sendEmail');

lambda函数的第一行/声明函数:

module.exports.sendFirstAlert = async (event, context, callback) => {

调用sendEmail函数:

await sendEmail(""Josh's Email" ${fromEmail}", toEmail, 'Alert!', message);注意这个`'被交换为“只是为了SO格式,但在代码中工作正常

utils/sendEmail

const nodemailer = require('nodemailer');
const ses = require('nodemailer-ses-transport');
const aws = require('aws-sdk');

const accessKeyId = process.env.accessKeyId;
const secretAccessKey = process.env.secretAccessKey;

const transport = nodemailer.createTransport(
    ses({
        accessKeyId: accessKeyId,
        secretAccessKey: secretAccessKey
    })
);

module.exports = function sendEmail(from, to, subject, message) {
    const mailOptions = {
        from,
        to,
        subject,
        html: message
    };
    transport.sendMail(mailOptions, (error, info) => {
        console.log('1');
        if (error) {
            console.log(error);
        }
        if (info) {
            console.log(info);
        }
        console.log('2');
    });
    console.log('3');
};

所以在发送电子邮件功能中我有这3个console.log语句。只有第三个被调用。第一个/第二个没有被调用。这个确切的代码(减去console.log)在容器中运行得非常好。

我正在使用节点无服务器框架来创建我的step / lambda函数。我已经为此开放了AWS SES权限(测试/解决此问题,而不是prod)。

我试图调用的ENV变量工作得非常好。该功能正确地以正确的格式获取所有必需的部分(从,到主题,消息)。

我也使用与容器中相同的API密钥,因此考虑到我发送的电子邮件在lambda函数中与容器中的电子邮件相同,因此发送电子邮件应该没问题。

什么想法可能是错的?

node.js aws-lambda amazon-ses serverless-framework nodemailer
1个回答
2
投票

从你所说的,问题看起来你的sendMail函数不能等待(即它不返回一个promise,或等待transport.sendMail)。

这就是回调中两个控制台日志不会发生的原因,因为lambda函数在调用回调之前完成执行。

您应该在此处查看nodemailer的文档(https://nodemailer.com/about/#example)以获取更多信息,但看起来以下代码应该可以正常工作:

module.exports = async function sendEmail(from, to, subject, message) {
  const mailOptions = { from, to, subject, html: message };
  try { 
    const info = await transport.sendMail(mailOptions);
    console.log(info);
    return true;
  } catch (error) {
    console.log(error);
    return false;
  }
};

注:我想它在本地工作的原因是因为你的容器与远程lambda环境不完全相同。在远程lambda环境中,一旦处理程序返回,所有代码执行都会被冻结,因此您的回调没有时间发生。但是您的本地容器继续在后台运行,这意味着即使您的处理程序已完成,您的回调仍会运行。

热门问题
推荐问题
最新问题