CloudFormation: Conditional List Items

Hello!

Many CloudFormation resources take parameters whose values are lists. Like tags on a Load Balancer:

Lb:
  Type: AWS::ElasticLoadBalancingV2::LoadBalancer
  Properties:
    Name: MyLb
    Scheme: internal
    Subnets: !Ref Subnets
    Tags:
      - Key: TagA
        Value: Unconditionally present

I often find that I want to add an item to the list, but only if a condition is true. That’s possible, but the syntax is a little funky.

In addition to conditions, we need AWS::NoValue. It’s a CloudFormation “Pseudo Parameter” that removes properties from templates. It allows you to dynamically include or remove properties based on conditions; you can pass AWS::NoValue to either the true or false case of the condition and it’s as if you never wrote that property into the template. The docs demonstrate it for top-level properties like Name and Scheme, but it also works for list items:

Conditions:
  AlwaysTrue: !Equals [true, true]
  AlwaysFalse: !Equals [true, false]

Resources:
  Lb:
    Type: AWS::ElasticLoadBalancingV2::LoadBalancer
    Properties:
      Name: MyLb
      Scheme: internal
      Subnets: !Ref Subnets
      Tags:
        - Key: TagA
          Value: Unconditionally present
        - !If
          - AlwaysTrue
          - Key: TagB
            Value: Always present
          - !Ref 'AWS::NoValue'
        - !If
          - AlwaysFalse
          - Key: TagC
            Value: Never present
          - !Ref 'AWS::NoValue'

These conditions (which of course are hacks just to make the demo easy) will only create TagA and TagB:

ConditionalTags

That’s it!

Before we wrap up, though, it’s worth highlighting a detail. There are two list here, the list of tags and the list of arguments to the !If function:

- !If
  - AlwaysFalse
  - Key: TagC
    Value: Never present
  - !Ref 'AWS::NoValue'

The second element of the arguments list (line 3) is a map that will become the value of an element of the tags list (line 1). In long templates with complicated conditions I find this detail turns in to a tripping point. If you’re getting errors, make sure your indentation is clean and you’re not mixing up the two lists.

Happy automating!

Adam

Need more than just this article? I’m available to consult.

You might also want to check out these related articles: