Lambda execution role may have excessive permissions

Restrict the actual Lambda execution-role permissions to the function’s work and required resources.

Description

Excessive Lambda execution-role permissions can let a code vulnerability or malfunction affect more AWS resources. Inspect attached policies, conditions and other controls rather than relying on role or policy names. A wildcard can still be limited to a particular service or action family, so review the actual allowed scope.

Potential impact

If a function is compromised, operations permitted by its execution role, such as reading, changing or deleting data, may be abused. Unnecessary permissions can broaden the damage.

Remediation

  • Identify the APIs and resources the function uses and limit its execution role accordingly. Avoid accumulating unnecessary permissions from other functions in shared roles.
  • Preserve required logging and service access while removing unnecessary privileges. Test intended calls and rejection of unapproved access.

Examples

These examples define a minimal function returning a fixed response and its execution role. For real code, select a compatible runtime and the permissions that code requires.

Before

yaml
Resources:
  AppendItemToListFunction:
    Type: AWS::Lambda::Function
    Properties:
      Handler: index.handler
      Role: !GetAtt LambdaExecutionRole.Arn
      Runtime: nodejs22.x
      Code:
        ZipFile: |
          exports.handler = async () => ({ statusCode: 200, body: "ok" });

  LambdaExecutionRole:
    Type: AWS::IAM::Role
    Properties:
      AssumeRolePolicyDocument:
        Version: "2012-10-17"
        Statement:
          - Effect: Allow
            Principal:
              Service: lambda.amazonaws.com
            Action: sts:AssumeRole
      Policies:
        - PolicyName: AdminPolicy
          PolicyDocument:
            Version: "2012-10-17"
            Statement:
              - Effect: Allow
                Action: "*"
                Resource: "*"

The role allows all actions and resources, far beyond what a fixed-response function needs.

After

yaml
Resources:
  AppendItemToListFunction:
    Type: AWS::Lambda::Function
    Properties:
      Handler: index.handler
      Role: !GetAtt LambdaExecutionRole.Arn
      Runtime: nodejs22.x
      Code:
        ZipFile: |
          exports.handler = async () => ({ statusCode: 200, body: "ok" });

  LambdaExecutionRole:
    Type: AWS::IAM::Role
    Properties:
      AssumeRolePolicyDocument:
        Version: "2012-10-17"
        Statement:
          - Effect: Allow
            Principal:
              Service: lambda.amazonaws.com
            Action: sts:AssumeRole
      Policies:
        - PolicyName: LimitedPolicy
          PolicyDocument:
            Version: "2012-10-17"
            Statement:
              - Effect: Allow
                Action:
                  - logs:CreateLogGroup
                  - logs:CreateLogStream
                  - logs:PutLogEvents
                Resource: "*"

This policy allows only logging operations. Consider restricting their resource scope to the actual log groups, and add only the specific permissions needed if the function calls other AWS APIs.

References