Reputation: 1558
My task is basic - I want to use CloudFormation to set up an EC2 instance with some arbitrary AMI that I like. However, for some reason this isn't as simple as just putting in the ID number of the image that I want.
As we see in their tutorial CloudFormation template, for the ImageId section they have:
Properties:
ImageId: !FindInMap [ AWSRegionArch2AMI, !Ref 'AWS::Region' , !FindInMap [ AWSInstanceType2Arch, !Ref InstanceType, Arch ] ]
When searching among the available EC2 images, I don't see anything called "AWSRegionArch2AMI", so I have no idea why this keyword is able to specify their desired AMI and allow this template to function.
So for example say I want to have my CloudFormation template create an instance with this popular, publicly available AMI:
Red Hat Enterprise Linux 8 (HVM), SSD Volume Type - ami-08949fb6466dd2cf3
What should I specify in the ImageId field to get CloudFormation to use this AMI?
Additionally, why is it standard to use these complex programmatic arguments instead of just a UID indicating the image I want?
Upvotes: 2
Views: 6335
Reputation: 1
Incase if someone need to do similar using YAML, here is the code below.
AWSTemplateFormatVersion: "2010-09-09"
Description: AWS CloudFormation Testing.
Metadata:
AWS::CloudFormation::Interface:
ParameterGroups:
- Label:
default: Amazon EC2 Configuration
Parameters:
- InstanceType
- AmiID
ParameterLabels:
InstanceType:
default: Type of EC2 Instance
AmiID:
default: Amazon Machine Image ID
Parameters:
InstanceType:
Description: Enter t2.micro or t2.small. Default is t2.micro.
Type: String
AllowedValues:
- t2.micro
- t2.small
Default: t2.micro
AmiID:
Description: The ID of the AMI.
Type: AWS::EC2::Image::Id
Default: ami-02396cdd13e9a1257
Resources:
WebServerInstance:
Type: AWS::EC2::Instance
Properties:
ImageId: !Ref AmiID
InstanceType: !Ref InstanceType
Tags:
- Key: Name
Value: !Join ['-', [!Ref InstanceType, webserver]]
- Key: InstanceType
Value: !Sub ${InstanceType}
Upvotes: 0
Reputation: 901
Short answer: it isn't necessary to go through this lookup process. If you plan to run in a single region, using a single AMI, then it's perfectly reasonable to specify that AMI as a parameter and use it directly.
The AWS example, however, must be able to run in multiple regions because AWS has customers that use these different regions. To do this it defines mappings (in the Mappings
section of the example template that can be used to translate from instance type to AMI.
Edit: here's an excerpt from a template that I'm currently using that passes the AMI as a parameter (with default). It's in JSON, and leaves out a lot of stuff, but should give you the gist of what's happening:
"Parameters" : {
"AmiId" : {
"Description" : "The ID of the AMI to use for the EC2 instance",
"Default": "ami-059f4aad319ff1bc3",
"Type": "String"
}
"Resources" : {
"EC2Instance" : {
"Type" : "AWS::EC2::Instance",
"Properties" : {
"ImageId" : { "Ref" : "AmiId" },
Upvotes: 5