aws / serverless-application-model

The AWS Serverless Application Model (AWS SAM) transform is a AWS CloudFormation macro that transforms SAM templates into CloudFormation templates.
https://aws.amazon.com/serverless/sam
Apache License 2.0
9.34k stars 2.38k forks source link

Global Runtime parameter does not work when using CF Modules #2318

Closed wayne-folkes closed 2 years ago

wayne-folkes commented 2 years ago

Description:

When using a CF module in a SAM template the Runtime value specified in the Globals section but not in the AWS::Serverless::Function resource the value appears to be ignored when attempting to deploy and will cause an error to be thrown.

Steps to reproduce:

  1. Create a CF Module
  2. Create a SAM template like the following that uses the module. Omit the runtime value from the AWS::Serverless::Function resource and attempt to deploy
    
    Function:
    Timeout: 3
    Runtime: python3.9

Resources: Function: Type: AWS::Serverless::Function Properties: CodeUri: hello_world/ Handler: app.lambda_handler

MyModule: Type: 'My::Lambda::ALBFunction::MODULE' Properties: VpcId: !ImportValue my-vpc-id SecurityGroupId: !ImportValue my-vpc-sg-id SubnetIds: !ImportValue my-vpc-private-subnet-ids CertificateArn: !ImportValue my-wildcard-cert-arn FunctionArn: !GetAtt Function.Arn HostedZoneId: !ImportValue my-HostedZoneId HostName: !Sub

Observed result:

sam deploy \
                --stack-name wf-module-test-dev \
                --s3-bucket sstk-severless-code-123456789012-us-east-1 \
                --s3-prefix wf-module-test \
                --capabilities CAPABILITY_NAMED_IAM \
                --no-fail-on-empty-changeset \
                --no-progressbar \
                --tags Owner=tech.cloudeng@mycompany.com Team=tech.cloudeng@mycompany.com CostCenter=1525 BusinessUnits=techops Environment=dev Name="Module Test" Application="my-resources" \
                --debug
2022-02-08 16:25:51,366 | Telemetry endpoint configured to be https://aws-serverless-tools-telemetry.us-west-2.amazonaws.com/metrics
2022-02-08 16:25:51,366 | Using config file: samconfig.toml, config environment: default
2022-02-08 16:25:51,366 | Expand command line arguments to:
2022-02-08 16:25:51,366 | --template_file=/Users/wfolkes/dev/alb-lambda/.aws-sam/build/template.yaml --stack_name=wf-module-test-dev --s3_bucket=sstk-severless-code-123456789012-us-east-1 --s3_prefix=wf-module-test --capabilities=('CAPABILITY_NAMED_IAM',) --no_progressbar --tags={'Owner': 'tech.cloudeng@mycompany.com', 'Team': 'tech.cloudeng@mycompany.com', 'CostCenter': '1525', 'BusinessUnits': 'techops', 'Environment': 'dev', 'Name': 'Module Test', 'Application': 'my-resources'} 
2022-02-08 16:25:51,693 | No Parameters detected in the template
2022-02-08 16:25:51,713 | Sam customer defined id is more priority than other IDs. Customer defined id for resource Function is Function
2022-02-08 16:25:51,713 | There is no customer defined id or cdk path defined for resource MyModule, so we will use the resource logical id as the resource id
2022-02-08 16:25:51,714 | Unable to resolve property VpcId: OrderedDict([('Fn::ImportValue', 'shared-vpc-id')]). Leaving as is.
2022-02-08 16:25:51,714 | Unable to resolve property SecurityGroupId: OrderedDict([('Fn::ImportValue', 'shared-vpc-codebuild-default-sg-id')]). Leaving as is.
2022-02-08 16:25:51,714 | Unable to resolve property SubnetIds: OrderedDict([('Fn::ImportValue', 'shared-vpc-private-subnet-ids')]). Leaving as is.
2022-02-08 16:25:51,714 | Unable to resolve property CertificateArn: OrderedDict([('Fn::ImportValue', 'ct-wildcard-cert-arn')]). Leaving as is.
2022-02-08 16:25:51,714 | Unable to resolve property HostedZoneId: OrderedDict([('Fn::ImportValue', 'ct-HostedZoneId')]). Leaving as is.
2022-02-08 16:25:51,714 | Unable to resolve property ZoneId: OrderedDict([('Fn::ImportValue', 'ct-HostedZoneName')]). Leaving as is.
2022-02-08 16:25:51,714 | Unable to resolve property HostName: OrderedDict([('Fn::Sub', ['module-test.${ZoneId}', OrderedDict([('ZoneId', OrderedDict([('Fn::ImportValue', 'ct-HostedZoneName')]))])])]). Leaving as is.
2022-02-08 16:25:51,715 | Unable to resolve property Value: OrderedDict([('Fn::GetAtt', ['MyModuleLoadBalancer', 'DNSName'])]). Leaving as is.
2022-02-08 16:25:51,715 | 2 stacks found in the template
2022-02-08 16:25:51,845 | Sam customer defined id is more priority than other IDs. Customer defined id for resource Function is Function
2022-02-08 16:25:51,845 | There is no customer defined id or cdk path defined for resource MyModule, so we will use the resource logical id as the resource id
2022-02-08 16:25:51,845 | Sam customer defined id is more priority than other IDs. Customer defined id for resource Function is Function
2022-02-08 16:25:52,361 | File with same data already exists at wf-module-test/f28f4bb6f24c12a2984f985b9f45998c, skipping upload
2022-02-08 16:25:52,361 | Sam customer defined id is more priority than other IDs. Customer defined id for resource MyModule is MyModule

        Deploying with following values
        ===============================
        Stack name                   : wf-module-test-dev
        Region                       : us-east-1
        Confirm changeset            : False
        Disable rollback             : False
        Deployment s3 bucket         : sstk-severless-code-123456789012-us-east-1
        Capabilities                 : ["CAPABILITY_NAMED_IAM"]
        Parameter overrides          : {}
        Signing Profiles             : {}

Initiating deployment
=====================
2022-02-08 16:25:52,405 | No Parameters detected in the template
2022-02-08 16:25:52,417 | Sam customer defined id is more priority than other IDs. Customer defined id for resource Function is Function
2022-02-08 16:25:52,417 | Sam customer defined id is more priority than other IDs. Customer defined id for resource MyModule is MyModule
2022-02-08 16:25:52,417 | Unable to resolve property VpcId: OrderedDict([('Fn::ImportValue', 'shared-vpc-id')]). Leaving as is.
2022-02-08 16:25:52,417 | Unable to resolve property SecurityGroupId: OrderedDict([('Fn::ImportValue', 'shared-vpc-codebuild-default-sg-id')]). Leaving as is.
2022-02-08 16:25:52,417 | Unable to resolve property SubnetIds: OrderedDict([('Fn::ImportValue', 'shared-vpc-private-subnet-ids')]). Leaving as is.
2022-02-08 16:25:52,418 | Unable to resolve property CertificateArn: OrderedDict([('Fn::ImportValue', 'ct-wildcard-cert-arn')]). Leaving as is.
2022-02-08 16:25:52,418 | Unable to resolve property HostedZoneId: OrderedDict([('Fn::ImportValue', 'ct-HostedZoneId')]). Leaving as is.
2022-02-08 16:25:52,418 | Unable to resolve property ZoneId: OrderedDict([('Fn::ImportValue', 'ct-HostedZoneName')]). Leaving as is.
2022-02-08 16:25:52,418 | Unable to resolve property HostName: OrderedDict([('Fn::Sub', ['module-test.${ZoneId}', OrderedDict([('ZoneId', OrderedDict([('Fn::ImportValue', 'ct-HostedZoneName')]))])])]). Leaving as is.
2022-02-08 16:25:52,418 | Unable to resolve property Value: OrderedDict([('Fn::GetAtt', ['MyModuleLoadBalancer', 'DNSName'])]). Leaving as is.
2022-02-08 16:25:52,418 | 2 stacks found in the template
2022-02-08 16:25:52,418 | No Parameters detected in the template
2022-02-08 16:25:52,434 | Sam customer defined id is more priority than other IDs. Customer defined id for resource Function is Function
2022-02-08 16:25:52,435 | Sam customer defined id is more priority than other IDs. Customer defined id for resource MyModule is MyModule
2022-02-08 16:25:52,435 | Unable to resolve property VpcId: OrderedDict([('Fn::ImportValue', 'shared-vpc-id')]). Leaving as is.
2022-02-08 16:25:52,435 | Unable to resolve property SecurityGroupId: OrderedDict([('Fn::ImportValue', 'shared-vpc-codebuild-default-sg-id')]). Leaving as is.
2022-02-08 16:25:52,435 | Unable to resolve property SubnetIds: OrderedDict([('Fn::ImportValue', 'shared-vpc-private-subnet-ids')]). Leaving as is.
2022-02-08 16:25:52,435 | Unable to resolve property CertificateArn: OrderedDict([('Fn::ImportValue', 'ct-wildcard-cert-arn')]). Leaving as is.
2022-02-08 16:25:52,435 | Unable to resolve property HostedZoneId: OrderedDict([('Fn::ImportValue', 'ct-HostedZoneId')]). Leaving as is.
2022-02-08 16:25:52,435 | Unable to resolve property ZoneId: OrderedDict([('Fn::ImportValue', 'ct-HostedZoneName')]). Leaving as is.
2022-02-08 16:25:52,435 | Unable to resolve property HostName: OrderedDict([('Fn::Sub', ['module-test.${ZoneId}', OrderedDict([('ZoneId', OrderedDict([('Fn::ImportValue', 'ct-HostedZoneName')]))])])]). Leaving as is.
2022-02-08 16:25:52,436 | Unable to resolve property Value: OrderedDict([('Fn::GetAtt', ['MyModuleLoadBalancer', 'DNSName'])]). Leaving as is.
2022-02-08 16:25:52,436 | 2 resources found in the stack 
2022-02-08 16:25:52,436 | No Parameters detected in the template
2022-02-08 16:25:52,452 | Sam customer defined id is more priority than other IDs. Customer defined id for resource Function is Function
2022-02-08 16:25:52,452 | Sam customer defined id is more priority than other IDs. Customer defined id for resource MyModule is MyModule
2022-02-08 16:25:52,452 | Unable to resolve property VpcId: OrderedDict([('Fn::ImportValue', 'shared-vpc-id')]). Leaving as is.
2022-02-08 16:25:52,452 | Unable to resolve property SecurityGroupId: OrderedDict([('Fn::ImportValue', 'shared-vpc-codebuild-default-sg-id')]). Leaving as is.
2022-02-08 16:25:52,452 | Unable to resolve property SubnetIds: OrderedDict([('Fn::ImportValue', 'shared-vpc-private-subnet-ids')]). Leaving as is.
2022-02-08 16:25:52,452 | Unable to resolve property CertificateArn: OrderedDict([('Fn::ImportValue', 'ct-wildcard-cert-arn')]). Leaving as is.
2022-02-08 16:25:52,453 | Unable to resolve property HostedZoneId: OrderedDict([('Fn::ImportValue', 'ct-HostedZoneId')]). Leaving as is.
2022-02-08 16:25:52,453 | Unable to resolve property ZoneId: OrderedDict([('Fn::ImportValue', 'ct-HostedZoneName')]). Leaving as is.
2022-02-08 16:25:52,453 | Unable to resolve property HostName: OrderedDict([('Fn::Sub', ['module-test.${ZoneId}', OrderedDict([('ZoneId', OrderedDict([('Fn::ImportValue', 'ct-HostedZoneName')]))])])]). Leaving as is.
2022-02-08 16:25:52,453 | Unable to resolve property Value: OrderedDict([('Fn::GetAtt', ['MyModuleLoadBalancer', 'DNSName'])]). Leaving as is.
2022-02-08 16:25:52,976 | File with same data already exists at wf-module-test/f1aea30b5563155b8f0ed3f4fa96bfaf.template, skipping upload

Waiting for changeset to be created..
2022-02-08 16:25:58,645 | Sending Telemetry: {'metrics': [{'commandRun': {'requestId': '3a1a43fa-765a-4662-b536-011d2cb9db1d', 'installationId': '351e2a74-4ff1-4af4-919c-cfbe2b0c58bd', 'sessionId': '7c72a6fb-f142-4f8a-8fa2-8a9f4cb82652', 'executionEnvironment': 'CLI', 'ci': False, 'pyversion': '3.8.12', 'samcliVersion': '1.37.0', 'awsProfileProvided': False, 'debugFlagProvided': True, 'region': '', 'commandName': 'sam deploy', 'metricSpecificAttributes': {'projectType': 'CFN'}, 'duration': 7278, 'exitReason': 'ChangeSetError', 'exitCode': 1}}]}
2022-02-08 16:25:58,982 | Telemetry response: 200
Error: Failed to create changeset for the stack: wf-module-test-dev, ex: Waiter ChangeSetCreateComplete failed: Waiter encountered a terminal failure state: For expression "Status" we matched expected path: "FAILED" Status: FAILED. Reason: Transform AWS::Serverless-2016-10-31 failed with: Invalid Serverless Application Specification document. Number of errors found: 1. Resource with id [Function] is invalid. Runtime and Handler needs to be present when PackageType is of type `Zip`
make: *** [deploy] Error 1

Expected result:

The stack should deploy. To get around this issue I have to add the Runtime property to the Function.

If the module is removed from the template the function will deploy as expected when the Runtime value is only specified in the Globals section

Additional environment details (Ex: Windows, Mac, Amazon Linux etc)

  1. OS: MacOS
  2. If using SAM CLI, sam --version: SAM CLI, version 1.37.0
  3. AWS region: us-east-1

Add --debug flag to any SAM CLI commands you are running

CoshUS commented 2 years ago

Hey @wayne-folkes, Thanks for the feedback. SAM transform is a CloudFormation Macro which runs before resolving any other resources. SAM does not have insight into custom modules and its resources. Closing as this is a limitation with CloudFormation template resolving order. Let me know if there are other issues and I'll reopen this.