Why is this an issue?
Some AWS services create Log Groups
implicitly and don’t let the developer choose the Log Group
name. This means that
CloudFormation does not require the developer to declare the Log Group
that the resource will write to.
If a Log Group
is not declared within CloudFormation, then this Log Group
will be automatically created at run time and
it won’t be managed by CloudFormation. The consequences are that the:
-
Log Group
will not be removed when the Stack
is removed.
-
Log Group
attributes (such as retention) won’t be managed "as code" within CloudFormation.
These automatically created Log Groups
will remain forever which can have huge impact on costs and security (the data stay forever
while this is unexpected from company or regulatory rules).
A good practice is to declare the target Log Group
with CloudFormation, matching the name that the AWS will use so that the Log
Group
resource is managed as code.
This rule applies to the following resources:
- AWS::Lambda::Function
- AWS::Serverless::Function
- AWS::ApiGatewayV2::Api
- AWS::CodeBuild::Project
Noncompliant code example
# There is no "Log Group" declared corresponding to "MyLambdaFunction": logs will not be managed by CloudFormation
MyLambdaFunction:
Type: AWS::Lambda::Function
Properties:
Runtime: nodejs12.x
Description: Example of Lambda Function
Compliant solution
Example with Ref
MyLambdaFunction:
Type: AWS::Lambda::Function
Properties:
Runtime: nodejs12.x
Description: Example of Lambda Function
MyFunctionLogGroup:
Type: AWS::Logs::LogGroup
Properties:
LogGroupName: !Join ['/', ['/aws/lambda', !Ref MyLambdaFunction]]
RetentionInDays: 30
Example with Sub
MyLambdaFunction:
Type: AWS::Lambda::Function
Properties:
Runtime: nodejs12.x
Description: Example of Lambda Function
MyFunctionLogGroupSub:
Type: AWS::Logs::LogGroup
Properties:
LogGroupName: !Sub '/aws/lambda/${MyLambdaFunction}’
RetentionInDays: 30