AWS CloudFormationでVPC設定を自動化する

この記事は約10分で読めます。

AWSリソースの環境構築を行う時、

  • AWSマネージドコンソールでマウスをポチポチしながら環境構築
  • AWS-CLIでコマンドを叩く

のどちらかでやると思います。

よく使うものは自動化したいなと最近思いはじめてましたので、CloudFormationを試してみました。
今回は料金が発生しないVPCのテンプレートを元にCloudFormationを実行します。

スポンサーリンク

CloudFormationのテンプレート

YAML

AWSTemplateFormatVersion: '2010-09-09'
Description:
  VPC & subnet create
Parameters:
  ProjectId:
    Description: Project name id.
    Type: String
    MinLength: "3"
    MaxLength: "10"
    AllowedPattern: "[a-zA-Z0-9]*"
    ConstraintDescription: must specify Project id.

Resources:
# Create VPC
  CFVPC:
    Type: AWS::EC2::VPC
    Properties:
      CidrBlock: 192.168.0.0/16
      EnableDnsSupport: 'true'
      EnableDnsHostnames: 'true'
      InstanceTenancy: default
      Tags:
      - Key: Name
        Value: !Join [ "-", [ "Ref":"ProjectId" ,"vpc" ] ]

# Create Public RouteTable
  CFPublicRouteTable:
    Type: AWS::EC2::RouteTable
    Properties:
      VpcId: !Ref CFVPC
      Tags:
      - Key: Name
        Value: !Join [ "-", [ "Ref":"ProjectId" ,"PublicRouteTable" ] ]

# Create Private RouteTable
  CFPrivateRouteTable:
    Type: AWS::EC2::RouteTable
    Properties:
      VpcId: !Ref CFVPC
      Tags:
      - Key: Name
        Value: !Join [ "-", [ "Ref":"ProjectId" ,"PrivateRouteTable" ] ]

# Create Public Subnet A
  CFPublicSubnetA:
    Type: AWS::EC2::Subnet
    Properties:
      VpcId: !Ref CFVPC
      CidrBlock: 192.168.1.0/24
      AvailabilityZone: "ap-northeast-1a"
      Tags:
      - Key: Name
        Value: !Join [ "-", [ "Ref":"ProjectId" ,"PublicSubnetA" ] ]
  PubSubnetARouteTableAssociation:
    Type: AWS::EC2::SubnetRouteTableAssociation
    Properties:
      SubnetId: !Ref CFPublicSubnetA
      RouteTableId: !Ref CFPublicRouteTable

# Create Public Subnet C
  CFPublicSubnetC:
    Type: AWS::EC2::Subnet
    Properties:
      VpcId: !Ref CFVPC
      CidrBlock: 192.168.100.0/24
      AvailabilityZone: "ap-northeast-1c"
      Tags:
      - Key: Name
        Value: !Join [ "-", [ "Ref":"ProjectId" ,"PublicSubnetC" ] ]
  PubSubnetCRouteTableAssociation:
    Type: AWS::EC2::SubnetRouteTableAssociation
    Properties:
      SubnetId: !Ref CFPublicSubnetC
      RouteTableId: !Ref CFPublicRouteTable

# Create Private Subnet A
  CFPrivateSubnetA:
    Type: AWS::EC2::Subnet
    Properties:
      VpcId: !Ref CFVPC
      CidrBlock: 192.168.2.0/24
      AvailabilityZone: "ap-northeast-1a"
      Tags:
      - Key: Name
        Value: !Join [ "-", [ "Ref":"ProjectId" ,"PrivateSubnetA" ] ]
  PriSubnetARouteTableAssociation:
    Type: AWS::EC2::SubnetRouteTableAssociation
    Properties:
      SubnetId: !Ref CFPrivateSubnetA
      RouteTableId: !Ref CFPrivateRouteTable

# Create Private Subnet C
  CFPrivateSubnetC:
    Type: AWS::EC2::Subnet
    Properties:
      VpcId: !Ref CFVPC
      CidrBlock: 192.168.200.0/24
      AvailabilityZone: "ap-northeast-1c"
      Tags:
      - Key: Name
        Value: !Join [ "-", [ "Ref":"ProjectId" ,"PrivateSubnetC" ] ]
  PriSubnetCRouteTableAssociation:
    Type: AWS::EC2::SubnetRouteTableAssociation
    Properties:
      SubnetId: !Ref CFPrivateSubnetC
      RouteTableId: !Ref CFPrivateRouteTable

# Create InternetGateway
  CFInternetGateway:
    Type: "AWS::EC2::InternetGateway"
    Properties:
      Tags:
      - Key: Name
        Value: !Join [ "-", [ "Ref":"ProjectId" ,"IGW" ] ]
  AttachGateway:
    Type: AWS::EC2::VPCGatewayAttachment
    Properties:
      VpcId: !Ref CFVPC
      InternetGatewayId: !Ref CFInternetGateway
  myRoute:
    Type: AWS::EC2::Route
    DependsOn: CFInternetGateway
    Properties:
      RouteTableId: !Ref CFPublicRouteTable
      DestinationCidrBlock: 0.0.0.0/0
      GatewayId: !Ref CFInternetGateway

Outputs:
  StackVPC:
    Description: The ID of the VPC
    Value: !Ref CFVPC
    Export:
      Name: !Sub "${AWS::StackName}-VPCID"

  StackPubSubnetA:
    Description: The ID of the VPC Subnet
    Value: !Ref CFPublicSubnetA
    Export:
      Name: !Sub "${AWS::StackName}-PublicSubnetA"

  StackPubSubnetB:
    Description: The ID of the VPC Subnet
    Value: !Ref CFPublicSubnetC
    Export:
      Name: !Sub "${AWS::StackName}-PublicSubnetC"

  StackPriSubnetA:
    Description: The ID of the VPC Subnet
    Value: !Ref CFPrivateSubnetA
    Export:
      Name: !Sub "${AWS::StackName}-PrivateSubnetA"

  StackPriSubnetB:
    Description: The ID of the VPC Subnet
    Value: !Ref CFPrivateSubnetC
    Export:
      Name: !Sub "${AWS::StackName}-PrivateSubnetC"

YAMLテンプレートの概要

【Parameters】
CloudFormationの画面でProjectIDという入力項目を設けました。
【Resources】内でProjectID入力値+○○(VPC,RouteTable etc…)という箇所がありますが、こちらでこの形式のNameタグ値も自動設定させています。

【Resources】

  • VPC作成
  • RouteTable作成(Public/Private)
  • PublicSubnet作成(AZ:1a,1c)→PublicRouteTableにアタッチ
  • PrivateSubnet作成(AZ:1a,1c)→PrivateRouteTableにアタッチ
  • InternetGateway作成→PublicRouteTableにアタッチ

【Outputs】
スタック構築後にCloudFormationから出力させる値です。
このテンプレートではVPC,PublicSubnet,PrivateSubnetを出力させていますが、別スタックの処理でこれらの値を参照する事ができます。
(クロススタック参照といいます)
例:別スタックでEC2インスタンス作成する時、このYAMLテンプレートで出力(作成した)しているSubnetにアタッチする。

スポンサーリンク

スタックの作成

CloudFormationコンソールを開きます。

スタックの作成をクリックします。

[テンプレートの選択]-[テンプレートをAmazon S3にアップロード]を選択し、上記YAMLのテンプレートをアップロードして[次へ]をクリックします。
テンプレート用のS3バケットは自動で作ってくれます。

[スタックの名前]と[パラメータ]を入力して[次へ]をクリックします。

[オプション]項目では何も入力をせず[次へ]をクリックします。

cloudformation-vpc-create-stack-option

[作成]をクリックします。

無事できました。
エラーの場合は途中まで生成されたリソースを全て破棄の上、ロールバックされます。

スポンサーリンク

後片付け

作成したスタックを選択し、[アクション]->[スタックの削除]をクリックすれば、スタック内

リソースを全て削除します

スポンサーリンク

まとめ

当記事の内容をマネージドコンソールで実施すると10分以上は掛かると思いますが、スタックの作成では1分程で環境構築が終わりました。
工数短縮や自動化による人為的ミスの排除に効果あると思います。

AWS OpsWorksやAWS CodeDeployも試し、自動化道に精進して行きます。

参考情報

AWSクラウドサービス活用資料集(BlackBelt):CloudFormation
AWS CloudFormation テンプレートの使用(リソース)
AWS リソースプロパティタイプのリファレンス

スポンサーリンク
AWS
ヤマログ
タイトルとURLをコピーしました