Enable Lambda Insight using CloudFormation

Enable Lambda Insight using CloudFormation

Enable Lambda Insight using CloudFormation

The content is related to monitoring and troubleshooting, which is also part of the scope of the AWS DVA.

One of the features provided by Lambda and CloudWatch is Lambda Insights.

CloudWatch Lambda Insights is a monitoring and troubleshooting solution for serverless applications running on AWS Lambda. The solution collects, aggregates, and summarizes system-level metrics including CPU time, memory, disk and network usage.

Using Lambda Insights in Amazon CloudWatch

This page will review how to create a Lambda function with Lambda Insights enabled using CloudFormation with reference to the following page.

https://docs.aws.amazon.com/AmazonCloudWatch/latest/monitoring/Lambda-Insights-Getting-Started-cloudformation.html

[affi id=22]

Environment

Diagram of enabling Lambda Insight using CloudFormation

Create three Lambda functions.

Associate a Lambda layer with each function.
This is a necessary step to enable Lambda Insights.

Similarly, associate an IAM role with each function.
This is also required for Lambda Insights to work.

Metrics collected by Lambda Insights are stored in CloudWatch.

CloudFormation template files

The above configuration is built with CloudFormation.
The CloudFormation template is placed at the following URL

https://github.com/awstut-an-r/awstut-dva/tree/main/05/004

Explanation of key points of template files

Lambda

Function 1

Resources:
  Function1:
    Type: AWS::Lambda::Function
    Properties:
      Architectures:
        - !Ref Architecture
      Code:
        ZipFile: |
          import datetime

          def lambda_handler(event, context):
            print('awstut!')
            return {
              'statusCode': 200,
              'body': str(datetime.datetime.now())
            }
      FunctionName: !Sub "${Prefix}-function1"
      Handler: !Ref Handler
      Layers:
        - !Ref LambdaInsightsLayer
      MemorySize: !Ref MemorySize
      Runtime: !Ref Runtime
      Role: !GetAtt FunctionRole.Arn
      Timeout: !Ref Timeout

  FunctionUrl:
    Type: AWS::Lambda::Url
    Properties:
      AuthType: NONE
      TargetFunctionArn: !GetAtt Function1.Arn

  FunctionUrlPermission:
    Type: AWS::Lambda::Permission
    Properties:
      Action: lambda:InvokeFunctionUrl
      FunctionName: !GetAtt Function1.Arn
      FunctionUrlAuthType: NONE
      Principal: "*"
Code language: YAML (yaml)

The key to enabling Lambda Insights is the Lambda layer.

Lambda Insights uses a new CloudWatch Lambda Insights extension, which is provided as a Lambda layer. When you enable this extension on a Lambda function for a supported runtime, it collects system-level metrics and emits a single performance log event for every invocation of that Lambda function.

How Lambda Insights monitors serverless applications

The Lambda layer that should be used to enable Lambda Insights depends on the region and architecture in which the function is deployed.
Please see the following page for more details, but for example, in our environment (Tokyo region, ARM64), we would select the following

https://docs.aws.amazon.com/AmazonCloudWatch/latest/monitoring/Lambda-Insights-extension-versions.html

arn:aws:lambda:ap-northeast-1:580247275435:layer:LambdaInsightsExtension-Arm64:2

Specify the above string to the Layers property.

Define the code to be executed by the Lambda function in inline notation.
For more information, please see the following page.

https://awstut.com/en/2022/02/02/3-parterns-to-create-lambda-with-cloudformation-s3-inline-container

The code returns the date and time the function was executed.

Also use the print function to output a string.
This is to check the output destination in the text log described below.

This function activates the Function URL.
If this function is enabled, an HTTPS endpoint is generated and this function can be executed when the URL is accessed.
For more information about Function URL, please see the following page.

https://awstut.com/en/2022/04/24/lambda-function-url-by-cloudformation-auth-type-none-en

Function 2

Resources:
  Function2:
    Type: AWS::Lambda::Function
    Properties:
      Architectures:
        - !Ref Architecture
      Environment:
        Variables:
          FUNCTION_URL: !GetAtt FunctionUrl.FunctionUrl
      Code:
        ZipFile: |
          import json
          import os
          import urllib.request

          function_url = os.environ['FUNCTION_URL']
          limit = 5

          def lambda_handler(event, context):
            responses = [urllib.request.urlopen(function_url).read().decode("utf-8") for i in range(limit)]

            return {
              'statusCode': 200,
              'body': json.dumps(responses, indent=2)
            }
      FunctionName: !Sub "${Prefix}-function2"
      Handler: !Ref Handler
      Layers:
        - !Ref LambdaInsightsLayer
      MemorySize: !Ref MemorySize
      Runtime: !Ref Runtime
      Role: !GetAtt FunctionRole.Arn
      Timeout: !Ref Timeout
Code language: YAML (yaml)

The contents of this function invoke the aforementioned function 1 five times.

To enable Lambda Insights, configure to use the Lambda layer described earlier.

Function 3

Resources:
  Function3:
    Type: AWS::Lambda::Function
    Properties:
      Architectures:
        - !Ref Architecture
      Code:
        ZipFile: |
          def lambda_handler(event, context):
            while True:
              pass
      FunctionName: !Sub "${Prefix}-function3"
      Handler: !Ref Handler
      Layers:
        - !Ref LambdaInsightsLayer
      MemorySize: !Ref MemorySize
      Runtime: !Ref Runtime
      Role: !GetAtt FunctionRole.Arn
      Timeout: !Ref Timeout
Code language: YAML (yaml)

The contents of the while statement repeats an empty loop.
It repeats until the timeout passes and the function fails to execute and exits.

To enable Lambda Insights, configure to use the Lambda layer described earlier.

IAM Role

Resources:
  FunctionRole:
    Type: AWS::IAM::Role
    DeletionPolicy: Delete
    Properties:
      AssumeRolePolicyDocument:
        Version: 2012-10-17
        Statement:
          - Effect: Allow
            Action: sts:AssumeRole
            Principal:
              Service:
                - lambda.amazonaws.com
      ManagedPolicyArns:
        - arn:aws:iam::aws:policy/service-role/AWSLambdaBasicExecutionRole
        - arn:aws:iam::aws:policy/CloudWatchLambdaInsightsExecutionRolePolicy
Code language: YAML (yaml)

Another key point in enabling Lambda Insights is the IAM role.

Add the CloudWatchLambdaInsightsExecutionRolePolicy IAM policy to your function execution role.

Using AWS CloudFormation to enable Lambda Insights on an existing Lambda function

In addition, attach the AWS management policy AWSLambdaBasicExecutionRole.
This grants the necessary permissions to deliver text logs to CloudWatch Logs.

EventBridge

Resources:
  Rule1:
    Type: AWS::Events::Rule
    Properties:
      Name: !Sub "${Prefix}-EventsRule-01"
      ScheduleExpression: rate(1 minute)
      State: ENABLED
      Targets:
        - Arn: !Ref FunctionArn1
          Id: !Ref Function1

  EventsRulePermission1:
    Type: AWS::Lambda::Permission
    Properties:
      FunctionName: !Ref Function1
      Action: lambda:InvokeFunction
      Principal: events.amazonaws.com
      SourceArn: !GetAtt Rule1.Arn
Code language: YAML (yaml)

We will cover function 1.
Functions 2 and 3 are similarly configured.

Define an EventBridge rule to execute the function periodically.
For more information, please see the following page.

https://awstut.com/en/2022/11/13/schedule-expressions-in-eventbridge-cloudwatch-events-to-execute-lambda-functions-periodically-en

This time, each function is set to run every minute.

Architecting

Use CloudFormation to build this environment and check its actual behavior.

Create CloudFormation stacks and check the resources in the stack

Create CloudFormation stacks.
For information on how to create stacks and check each stack, please see the following page.

https://awstut.com/en/2021/12/11/cloudformations-nested-stack

After reviewing the resources in each stack, information on the main resources created in this case is as follows

  • Lambda function 1: dva-05-004-function1
  • Lambda function 2: dva-05-004-function2
  • Lambda function 3: dva-05-004-function3

Lambda functions are also checked from the AWS Management Console.

Detail of Lambda 1.
Detail of Lambda 2.
Detail of Lambda 3.

Three functions have been successfully created.

Check the EventBridge rules.

Detail of EventBridge 1.

Three rules are created.
The content of each calls 3 functions every minute.

Operation Check

Now that you are ready, check the Lambda Insights console screen.

Detail of Lambda 4.

Various metrics on the three functions are graphed.

The characteristic graphs are identified.

Duration and Errors are high for function 3.
This is because the loop is repeated with a while statement, which waits until the timeout and finally fails to execute the function.

For Invocations, function 1 has a high value.
This is due to the fact that it is executed every minute by the EventBridge rule and is frequently called by Function 2.

Function 2 has a high value for Network Usage.
As mentioned earlier, this is due to frequent calls to Function 1 via Function URL.

A graph can also be drawn by specifying a function.

Detail of Lambda 5.

Above is an image focusing on function 1.

The various metrics for Lambda Insights are log data delivered to the following CloudWatch Logs.

Detail of CloudWatch Logs 1.

As a sample, check the log group for function 1.

Detail of CloudWatch Logs 2.

Indeed, data for various metrics are stored.

Incidentally, no text logs will be distributed to this log group.

Detail of CloudWatch Logs 3.

Above is the contents of function 1, this time stored in the default log group /aws/lamba/dva-04-003-function1.

Summary

We have seen how to use CloudFormation to create a Lambda function with Lambda Insights enabled.