将通过Amazon SES收到的电子邮件转发到LINE

更新记录

    • 2022/01/05 Lambda を作成するリージョンについて追記

 

    2022/01/05 コメントでご指摘いただいた typo のあったスクリーンショット修正 ご指摘いただいた記事

目录

作るもの

前提条件

背景

やりたいこと
課題
解決方法
この仕組みのメリット

実装

LINE
Amazon Route53 (ドメイン取得)
ドメイン名の選択
登録者の連絡先入力と購入
Amazon SES
リージョンの選択
Domain Identity 作成

メール受信設定とS3連携

受信メールアドレス登録
S3 への保存設定
動作確認

Amazon S3
ライフサイクルルール作成
AWS Lambda

モジュールレイヤーの作成

LINE Messaging API SDK for nodejs
MAILPARSER
結果確認

Lambda 関数作成
ソースコードデプロイ
環境変数設定
トリガー追加
テスト

制作之物

构成图如下所示。

在构成图中,邮件服务显示为Gmail,但只要能够进行转发设置的邮件服务,就可以将邮件转发到LINE上。

構成図
    在要通知的電子郵件服務中,將郵件轉發設置給AmazonSES。 AmazonSES的電子郵件地址將由Amazon Route 53解析。 收到的郵件將存儲在Amazon S3存儲桶中。 通過S3觸發調用AWS Lambda函數來發送LINE消息。

前提条件

    • 独自ドメインを取得します (場合によってはお金がかかる)

 

    • DNS は Amazon Route53 を利用します

 

    • Amazon SES から 直接 AWS Lambda をコールせずに、一度 Amazon S3 にメールデータを格納します。(SES から Lambda を呼び出すと、メール本文データが取得できなかったため)

 

    • Lambda 関数のランタイムは Node.js です。

 

    • LINE bot は友だち登録します。

 

    LINE に通知されるメールは、友だち登録している全員に送信されます。

背景 – 背景情况

我想做的事情。

我想把收到的某封邮件转发到LINE上。

问题或挑战

    • 転送したいメールは Gmail

 

    • Gmail はメールを受信したときに発火する トリガー の仕組みが無い(?)

 

    ポーリングはしたくない

解决方案

因为 Amazon SES 具有邮件接收触发器,所以可以将邮件转发到 Amazon SES,并从 Lambda 将其转发到 LINE。

这个机制的好处。

只要是能够进行邮件转发设置的邮件服务,不限于Gmail,都可以建立通用机制将邮件转发到LINE上。

实施

LINE:请提供一个中文的同义句。

在LINE Developers上创建一个Messaging API的频道。

创建频道后,请将以下项目复制保存。

    • Basic settings メニューの Channel secret

Messaging API Settings メニューの Channel access token (long-lived)

另外,您可以使用Messaging API设置菜单中的QR码,和这个频道添加好友。

亚马逊 Route53(域名注册)

如果您已经拥有自己的独立域名,请跳过此步骤。

选择域名

在AWS管理控制台上选择Amazon Route53,并点击”域名注册”按钮,开始向导。

如果可以的话,点击“加入购物车”按钮,然后点击屏幕底部的“继续”按钮。

注册者的联系方式输入和购买

在域名查询详情页面上,正确填写域名的注册者和管理员信息。根据顶级域名的不同,输入的信息可能不会被公开,所以请放心。

当输入所有信息完成后,请点击屏幕底部的“继续”按钮。

在联系详情确认页面上,可以查看我们在前一个页面中输入的信息的内容。另外,你可以设置是否启用“每年自动续订域名”的选项,所以请根据需要进行适当的设置。

如果您拥有AWS信用额度,则会显示以下对话框。无法使用AWS信用额度支付域名注册费用,会收取实际费用。请确认内容后点击”完成订单”按钮。

在 Route 53 仪表板的通知栏中,会显示域名注册的进度。我认为直到域名变为可用大约需要30分钟左右。

亚马逊邮件服务 (Amazon SES)

※由于 SES 的设置是在 2021 年 5 月上旬尝试的,所以被引导到旧版控制台。以下的步骤是基于旧版界面的截图。

选择区域

Amazon SES支持接收邮件的区域有限。

请从以下列出的区域中选择一个进行操作。

リージョン名リージョンUS East (N. Virginia)us-east-1US West (Oregon)us-west-2Europe (Ireland)eu-west-1

亚马逊简单电子邮件服务终端节点和配额的公式文件。

创建领域身份

在亚马逊SES上创建一个Identity,以便使用自己的域名。点击屏幕左侧面板中的Identity Management,然后选择Domains。(见图示①)

然后,点击屏幕上方的“验证新域名”按钮。(图中②)

请在“验证新域名”对话框中输入要作为电子邮件地址使用的域名,并单击“验证该域名”按钮进行验证。

请确认是否使用 Route 53 注册 MX记录,然后点击“使用 Route 53”按钮。

稍等一下,您注册的域名身份的验证状态将会变为已验证。

邮件接收设置和S3连接

注册电子邮件地址

我将创建一个规则,用于在Amazon SES收到邮件后将其保存到Amazon S3。

点击左侧画面的“接收电子邮件”栏目下的“规则集”(图中①)。

我們將創建一個相當於郵箱的東西。如果此處未輸入任何內容,將接收所有包括子域名在內的用戶的郵件,因此需要事先創建一個適合的郵件地址作為轉發目標。

在下面的例子中,我们激活了一个名为 test-mail@域名 的电子邮件地址。

输入电子邮件地址后,点击屏幕底部的“下一步”按钮。

将存储设定为S3

在屏幕上,设置如何处理收到的邮件。

在“选择操作类型”下拉菜单中选择S3。

由于切换到 Amazon S3 的设置页面上,点击 S3 bucket 菜单,并选择创建 S3 bucket。如果希望使用现有的 bucket,请选择下拉列表底部列出的可用 bucket。

当选择”创建 S3 存储桶”时,将显示”创建新存储桶”对话框,您需要给它一个在全球范围内唯一的名称,然后点击”创建存储桶”按钮。

使用Amazon SES的区域将创建S3存储桶

在画面上输入规则名称,然后点击”下一步”按钮。

在Review画面上,您可以确认之前输入的设置内容。确认完成后,点击“Create Rule”按钮。

确认操作

我会确认是否正确收到邮件并将其保存到S3中。

将邮件发送到已注册并在SES上激活的邮箱地址。

如果先前的设置是正确的,当发送电子邮件时,会在设置为将对象保存在S3存储桶内的文件夹中创建一个对象。

亚马逊S3

使用这个机制,存储桶中的对象将不断增多。当将邮件通知发送到LINE后,对象将变得无用,因此会自动设置删除对象以实现成本削减。

制定生命周期规则

设定以下内容,使得对象在创建后的第二天被删除。

    1. 生命周期规则名称是输入任意文字。

前缀是输入到S3存储设置中的对象键前缀。

生命周期规则的操作是勾选对象的当前版本过期。

输入1以使对象的当前版本到期。

点击“保存”按钮。

亚马逊 Lambda

创建模块层

为了在AWS Lambda的Node.js运行时中使用npm模块,我们需要创建一个层。
创建和共享Lambda层的文档。

以下的操作将在AWS CloudShell中进行。
文档-CLI aws lambda publish-layer-version

用于Node.js的LINE消息API软件开发工具包

GitHub – Line Bot SDK
GitHub – Line机器人软件开发工具包

#
# AWS ドキュメントに沿ったパス作成
$ mkdir nodejs
$ cd nodejs

#
# パッケージインストール
$ npm install @line/bot-sdk --save

#
# レイヤー用 Zip ファイル作成
$ cd ..
$ zip -r layer1.zip ./nodejs

#
# レイヤー作成
aws lambda publish-layer-version \
 --layer-name line-bot-sdk \
 --description "Line Bot for Node.js" \
 --zip-file fileb://./layer1.zip \
 --compatible-runtimes nodejs12.x nodejs14.x

# {結果のJSON が出力される}

#
# 後片付け
$ rm -rf nodejs/
$ rm layer1.zip

邮件解析器

官方网页 – 邮件解析器

#
# AWS ドキュメントに沿ったパス作成
$ mkdir nodejs
$ cd nodejs

#
# パッケージインストール
$ npm install mailparser --save

#
# レイヤー用 Zip ファイル作成
$ cd ..
$ zip -r layer2.zip ./nodejs

#
# レイヤー作成
aws lambda publish-layer-version \
 --layer-name mailparser \
 --description "mailparser for Node.js" \
 --zip-file fileb://./layer2.zip \
 --compatible-runtimes nodejs12.x nodejs14.x

# {結果のJSON が出力される}

#
# 後片付け
$ rm -rf nodejs/
$ rm layer1.zip

确认结果

在AWS托管控制台上,查看创建的层。

请从AWS Lambda控制台的左侧窗格中选择”其他资源”→”层”进行点击。

请确认已创建了两个图层。

创建Lambda函数

Lambda 需要在与 S3 相同的区域创建。

在函数创建界面中,您需要设置以下项。

    • 1から作成 を選択します。

 

    • 関数名は任意の文字列を入力します。

 

    ランタイムは Node.js 14.x を選択します。

完成设定后,请点击屏幕底部的”创建函数”按钮。

在 Lambda 函数设置页面的底部,点击“添加图层”按钮。

在添加图层的界面上,选择自定义图层,然后从下拉列表中添加line-bot和mailperser。(要添加两个图层时,选择第一个图层后,点击“添加”按钮,然后再次添加第二个图层。)

源代码部署

使用下面的代码,可以将存储在S3中的邮件数据通知到LINE上。

※注意※
lineClient.broadcast() 方法是返回一个异步处理的 Promise。如果没有使用 await 关键字退出 Lambda 函数,会导致发送错误。

在本地环境中,一段没有使用 await 的源代码没有问题,但是在 Lambda 中却无法正常运行,让我困惑了一段时间。

console.log('Loading function');
const aws = require('aws-sdk');
const s3 = new aws.S3({ apiVersion: '2006-03-01' });

const simpleParser = require('mailparser').simpleParser;
const line_bot_sdk = require('@line/bot-sdk');

// LINE 接続情報(ハンドラ外で定義
var lineClient = new line_bot_sdk.Client(
{
    channelAccessToken : process.env.LINE_CHANNEL_ACCESS_TOKEN,
    channelSecret : process.env.LINE_CHANNEL_SECRET
});

exports.handler = async (event, context) => {
    //console.log('Received event:', JSON.stringify(event, null, 2));

    const bucket = event.Records[0].s3.bucket.name;
    const key = decodeURIComponent(event.Records[0].s3.object.key.replace(/\+/g, ' '));
    const params = {
        Bucket: bucket,
        Key: key,
    };
    try {
        const { Body, ContentType } = await s3.getObject(params).promise();
        const mailBody = await simpleParser(Body);

        // Line 送信
        await lineClient.broadcast (
        {
            type: 'text',
            text : `件名 : ${mailBody.subject} \n` +
                   `内容 : ${mailBody.text}` ,
        });
        return ContentType;

    } catch (err) {
        console.log(err);
        const message = `Error getting object ${key} from bucket ${bucket}. Make sure they exist and your bucket is in the same region as this function.`;
        console.log(message);
        throw new Error(message);
    }
};

设定环境变量

将用于发送消息到LINE的访问令牌和通道密钥设置为环境变量。点击屏幕中部的“设置”标签,然后点击“环境变量”菜单。

在环境变量输入框中,设置以下变量:

キー値LINE_CHANNEL_ACCESS_TOKENアクセストークンLINE_CHANNEL_SECRETチャンネルシークレット

添加触发器

设置Lambda函数,以在创建了Amazon S3对象时被触发执行。

在添加触发器的页面上,当在设置触发器的下拉菜单中输入”S3″时,列表中会显示”S3″,请选择。

在触发器设置画面上,您可以设置以下项目。

    • バケットにはSESで受信したメールを保存するバケットを設定します。

 

    • イベントタイプは PUT を選択します。

 

    • プレフィックス・オプションは Object key prefixを設定します。

 

    再帰呼び出し の注意ボックスに表示されている内容を読み、確認チェックボックスにチェックします。

当设置完成后,请点击屏幕底部的“添加”按钮。

考试

让我们将通过 SES 进行的电子邮件接收操作确认所创建的对象更改名称并保存到 S3 存储桶中。当 Lambda 函数成功执行时,将发送通知到 LINE。

应用

我認為在Lambda函數的源代碼中檢查郵件的主題和內容,並只通知符合規則的郵件到LINE上的功能是可以實現的。

广告
将在 10 秒后关闭
bannerAds