1
votes

I have declared the SNS topic and Subscription like below in my AWS Serverless Application Model template :-

MyTopic:
    Type: AWS::SNS::Topic
    Properties:
      DisplayName: !Sub 'test-${Environment}-${AWS::AccountId}-${AWS::Region}'
      Tags:
       - Key: Environment
         Value: !FindInMap [Environment, FullForm, !Ref Environment]
      TopicName: !Sub 'test-${Environment}-${AWS::AccountId}-${AWS::Region}'

  MySubscription:
    Type: AWS::SNS::Subscription
    Properties:
      Endpoint: !Ref SubscriptionEndPoint
      Protocol: !Ref SubscriptionProtocol
      Region: !Ref 'AWS::Region'
      TopicArn: !Ref MyTopic

And then using the SNS Topic ARN in my Lambda function's environment as following in the same template file :-

MyLambda:
    Type: AWS::Serverless::Function
    Properties:
      Environment:
        Variables:
          RUNTIME_SNS_TOPIC_ARN: !GetAtt MyTopic.Arn

Outputs (in SAM template):-

MyTopic:
    Description: SNS Topic for the Ingest to send notification to
    Export:
      Name: !Sub
        - ${ExportPrefix_}:${AWS::Region}:MyTopic
        - ExportPrefix_: !If
          - HasExportPrefix
          - !Join ['-', [!Ref ExportPrefix, !Ref Environment]]
          - !Join ['-', [!Select [0, !Split ["-", !Ref "AWS::StackName"]], !Ref Environment]]
      Value: !Sub "${MyTopic.Arn}:${MyTopic.Version.Version}"
  MySubscription:
    Description: Subscription to get messages from a topic
    Export:
      Name: !Sub
        - ${ExportPrefix_}:${AWS::Region}:MySubscription
        - ExportPrefix_: !If
          - HasExportPrefix
          - !Join ['-', [!Ref ExportPrefix, !Ref Environment]]
          - !Join ['-', [!Select [0, !Split ["-", !Ref "AWS::StackName"]], !Ref Environment]]
      Value: !Sub "${MySubscription.Arn}:${MySubscription.Version.Version}"

However, I'm getting following error :-

13:30:30 Error: Failed to create changeset for the stack: my-stack, ex: Waiter ChangeSetCreateComplete failed: Waiter encountered a terminal failure state Status: FAILED. Reason: Template error: resource MyTopic does not support attribute type Arn in Fn::GetAtt

2

2 Answers

2
votes

An AWS::SNS:Topic returns the ARN when you use Ref

Check out the Docs on the return values.

Try with

MyLambda:
    Type: AWS::Serverless::Function
    Properties:
      Environment:
        Variables:
          RUNTIME_SNS_TOPIC_ARN: !Ref MyTopic  # Using !Ref
1
votes

Recommend trying the CloudFormation Linter in VSCode to see some of these errors inline while authoring templates:

Visual Studio Code screenshot

Visual Studio Code screenshot

Visual Studio Code screenshot

[cfn-lint] E1010: Invalid GetAtt MyTopic.Arn for resource MyLambda
[cfn-lint] E1019: Parameter MyTopic.Arn for Fn::Sub not found at Outputs/MyTopic/Value/Fn::Sub
[cfn-lint] E1019: Parameter MyTopic.Version.Version for Fn::Sub not found at Outputs/MyTopic/Value/Fn::Sub
[cfn-lint] E1019: Parameter MySubscription.Arn for Fn::Sub not found at Outputs/MySubscription/Value/Fn::Sub
[cfn-lint] E1019: Parameter MySubscription.Version.Version for Fn::Sub not found at Outputs/MySubscription/Value/Fn::Sub

It'll also point out that Value needs to be indented less in the Outputs


AWS::SNS::Topic return values

AWS::SNS::Subscription