如何通过AWS CloudWatch 日志订阅获取Lambda 异常日志通知

本文介绍了如何配置AWS CloudWatch日志订阅,以便在Lambda函数出现特定错误时通过SNS发送包含详细信息的电子邮件通知。通过创建SNS主题、IAM角色、Lambda函数和CloudWatch日志触发器,实现自动监控和通知。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

License: Attribution-NonCommercial-ShareAlike 4.0 International
本文出自 Suzf Blog 。 如未注明,均为 SUZF.NET 原创。
转载请注明: https://suzf.net/post/1460

这篇文章演示了如何使用 Amazon CloudWatch log subscription 自动对特定 AWS Lambda 函数错误发出警报通知。CloudWatch Logs 让您可以在日志条目与模式匹配时调用 Lambda 函数。 Amazon CloudWatch alarms 用于在错误发生时发出通知Lambda 函数;这个通知不会提供有关错误任何的细节。对于您需要在通知中显示具体说明错误的情况,您可以使用 CloudWatch Logs subscription来实现。CloudWatch Logs 订阅让您可以匹配日志中具有特定错误模式的条目,并收到有关这些错误详细信息的通知。这为您节省了额外的步骤解析日志。当在您的 Lambda 函数中检测到该错误模式时,您还可以将其用作构建自动反应措施的蓝图。

这篇文章将向您介绍如何配置触发 AWS Lambda 函数来处理匹配日志的 CloudWatch 日志订阅。Lambda 函数使用 Amazon SNS 发送包含特定错误详细信息和日志位置的电子邮件。

解决方案架构图

此解决方案的架构相对简单。您有一堆 Lambda 函数,您希望收到有关其特定严重错误的通知。CloudWatch Logs 从这些 Lambda 函数中过滤特定模式的日志。例如 ERROR、CRITICAL 或自定义错误。错误处理 Lambda 函数依次向 Amazon SNS 主题发布消息,可以订阅该主题以在发生错误时收到电子邮件。

出于本文的目的,我们将使用以下示例 Lambda 函数生成错误日志:

import logging
import os

logging.basicConfig(level=logging.DEBUG)
logger=logging.getLogger(__name__)


deflambda_handler(event, context):
    logger.setLevel(logging.DEBUG)
    logger.debug("This is a sample DEBUG message.. !!")
    logger.error("This is a sample ERROR message.... !!")
    logger.info("This is a sample INFO message.. !!")
    logger.critical("This is a sample 5xx error message.. !!")

部署教程

前置条件

要实施此解决方案,您必须创建:

  • SNS topic

  • IAM role

  • Lambda function

  • CloudWatch log trigger

步骤 1: 创建 SNS topic

要创建 SNS 主题,请完成以下步骤:

  1. 打开 Amazon SNS console

  1. 在左侧导航栏选择 Topics

  1. 选择创建 topic. 选择 Standard 类型,输入 topic name `MySNSTopic` 点击 Create topic. 创建 成功后自动跳转到 MySNSTopic 页面。详细信息部分显示主题的名称、ARN、显示名称(可选)和主题所有者的 AWS 账户 ID。

  1. 在详情页面,拷贝 topic ARN到粘贴板,比如: arn:aws:sns:us-east-1:123456789012:MySNSTopic

  1. 在做了导航,选择 Subscriptions and Create subscription.

  1. Create subscription 页面,做一下操作:

  1. 输入之前拷贝的 topic ARN: arn:aws:sns:us-east-1:123456789012:MySNSTopic

  1. Protocol 选择 Email

  1. Endpoint, 输入可以接受邮件的邮件地址

  1. 选择 Create subscription.

  1. 请注意,对于电子邮件订阅,您必须通过点击电子邮件收到的确认订阅链接来确认订阅。确认订阅后,您就可以接收电子邮件通知了。

步骤 2: 创建 IAM role

创建 IAM role, 需要完成一下操作。获取更多信息,请看 Creating an IAM role

  1. IAM console 页面, 在左侧导航栏 选择 Policies, 之后选择 Create Policy.

  1. 选择 JSON 选项卡 输入下面 IAM policy, 用之前创建的SNS topic ARN 替换 Topic ARN :

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": "sns:Publish",
            "Resource": "arn:<partition>:sns:<region>:<AWS account number>:<name of the SNS topic from previous step>"},
        {
            "Effect": "Allow",
            "Action": [
                "logs:CreateLogGroup",
                "logs:CreateLogStream",
                "logs:PutLogEvents"
            ],
            "Resource": "arn:<partition>:logs:<region>:<AWS account number>:log-group:/aws/lambda/<name of the lambda function you are going to create in next step>:*"}
    ]
}
  1. 选择 Review policy.

  1. 给这个 policy 输入 name (MyCloudWatchRole) 并 Create policy。记下此策略的名称以供后续步骤使用

  1. 在左侧导航栏, 选择 Roles 点击 Create role.

  1. Select role type 页面, 选择 AWS 服务作为您的可信实体,并在常见用例下选择 Lambda。

  1. 选择 Next: Permissions.

  1. 过滤刚刚创建的策略名称,然后选中该复选框。

  1. 选择 Next: Tags, 并给它一个合适的标签。

  1. 选择 Next: Review. 为这个 IAM 角色指定一个合适的名称,并记下来以备将来使用。

  1. 选择 Create role.

步骤 3: 创建 Lambda function

要创建 Lambda 函数,请完成以下步骤。 获取更多信息,参见 Create a Lambda Function with the console.

  1. Lambda console, 选择 Author from scratch。

  1. Function Name, 输入函数名称。

  1. Runtime, 选择 Python 3.7.

  1. Execution role, 选择 Use an existing role, 选择之间创建的 IAM role.

  1. 选择 Create Function, 移除 default function, 拷贝下列代码到 Function Code 窗口:

# Copyright 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved.
# Licensed under the Apache License, Version 2.0 (the "License").
# You may not use this file except in compliance with the License.
# A copy of the License is located at## http://aws.amazon.com/apache2.0/
# or in the "license" file accompanying this file.
# This file is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
# either express or implied. See the License for the specific language governing permissions
# and limitations under the License.
# Description: This Lambda function sends an email notification to a given AWS SNS topic when a particular
#              pattern is matched in the logs of a selected Lambda function. The email subject is
#              Execution error for Lambda-<insert Lambda function name>.
#              The JSON message body of the SNS notification contains the full event details.

# Author: Sudhanshu Malhotra

import base64
import boto3
import gzip
import json
import logging
import os

from botocore.exceptions import ClientError

logging.basicConfig(level=logging.INFO)
logger = logging.getLogger(__name__)


def logpayload(event):
    logger.setLevel(logging.DEBUG)
    logger.debug(event['awslogs']['data'])
    compressed_payload = base64.b64decode(event['awslogs']['data'])
    uncompressed_payload = gzip.decompress(compressed_payload)
    log_payload = json.loads(uncompressed_payload)
    return log_payload


def error_details(payload):
    error_msg = ""
    log_events = payload['logEvents']
    logger.debug(payload)
    loggroup = payload['logGroup']
    logstream = payload['logStream']
    lambda_func_name = loggroup.split('/')
    logger.debug(f'LogGroup: {loggroup}')
    logger.debug(f'Logstream: {logstream}')
    logger.debug(f'Function name: {lambda_func_name[3]}')
    logger.debug(log_events)
    for log_event in log_events:
        error_msg += log_event['message']
    logger.debug('Message: %s' % error_msg.split("\n"))
    return loggroup, logstream, error_msg, lambda_func_name


def publish_message(loggroup, logstream, error_msg, lambda_func_name):
    sns_arn = os.environ['snsARN']  # Getting the SNS Topic ARN passed in by the environment variables.
    snsclient = boto3.client('sns')
    try:
        message = ""
        message += "\nLambda error  summary" + "\n\n"
        message += "##########################################################\n"
        message += "# LogGroup Name:- " + str(loggroup) + "\n"
        message += "# LogStream:- " + str(logstream) + "\n"
        message += "# Log Message:- " + "\n"
        message += "# \t\t" + str(error_msg.split("\n")) + "\n"
        message += "##########################################################\n"

        # Sending the notification...
        snsclient.publish(
            TargetArn=sns_arn,
            Subject=f'Execution error for Lambda - {lambda_func_name[3]}',
            Message=message
        )
    except ClientError as e:
        logger.error("An error occured: %s" % e)


def lambda_handler(event, context):
    pload = logpayload(event)
    lgroup, lstream, errmessage, lambdaname = error_details(pload)
    publish_message(lgroup, lstream, errmessage, lambdaname)
  1. Environment variables 中,输入以下键值对:

  • Key= snsARN

  • Value= the ARN of the MySNSTopic created earlier

  1. 点击 Save.

步骤 4. 创建 CloudWatch log trigger

  1. 要添加触发器,请选择添加触发器,然后从下拉列表中选择 CloudWatch Logs。

  1. Log group 下拉列表,选择要获取错误通知的 Lambda 函数的 CloudWatch 日志组名称。在我们的例子中,这将是上面讨论的示例错误生成 Lambda 函数的日志组。

  1. 在过滤器名称输入适当的值,并在过滤器模式下,输入您希望收到通知的日志的过滤器值。例如 - “?ERROR ?WARN ?5xx” 将过滤 日志中包含 ERROR、WARN 或 5xx 的日志。 Log filter and pattern syntax 中包含更多其他复杂模式的示例。

  1. 启用 trigger & 添加

解决方案验证

为验证我的解决方案,我将运行生成错误日志 Lambda 函数并过滤日志中包含 “?ERROR ?WARN ?5xx” 的日志进行邮件通知,如下所示:

同样,我可以为任何特定错误创建一个过滤器模式,例如过包含 5xx 的日志,并仅针对该错误日志获得以下通知:

卸载

为了避免持续收费,删除在前面的步骤中创建的资源,包括 CloudWatch Events rule Lambda function SNS topic

结论

这篇文章演示了如何使用 CloudWatch Log 过滤器来解析 Lambda 函数的日志并通过电子邮件通知过滤到的错误信息。有关进一步阅读,请参阅:

此文为翻译 源链接为 https://aws.amazon.com/blogs/mt/get-notified-specific-lambda-function-error-patterns-using-cloudwatch/
感谢 Sudhanshu Malhotra 和 Rajat Mathur 的分享

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值