LoginSignup
8

More than 3 years have passed since last update.

posted at

updated at

ECR、ECSをCloudFormation化してみた

はじめに

この記事はコンテナ勉強用として試したことまとめたものです。
今回は今まで作成してきたECR、ECSをCloudFormationでソースコード化してみました。

CloudFormationとは

AWSサービスのインフラ構成をコードに記述しテンプレート化し、テンプレートから環境構築できるサービス。VPCやEC2、S3など様々なサービスをプロビジョニングが可能である。テンプレートファイル形式はJSON、YAMLをサポートしている。CloudFormation自体に費用は無料。略してCFnと呼ばれる。

スタック

  • テンプレートからプロビジョニングされるリソースの集合体のことを指す。
  • スタック単位リソースを作成することが可能。
  • スタックを削除すると紐づくリソースをまるっと削除できる。

テンプレートの要素

  • CloudFormationは以下の要素から構成される。Resourcesは必須。
    • AWSTemplateFormatVersion(テンプレートのバージョン)
    • Description(テンプレートの説明)
    • Parameters(CloudFormation実行時のパラメータ設定)
    • Mappings(キーに対応する値のマッピング)
    • Conditions(作成条件を記載)
    • Resources(スタック構成するリソースを定義)
    • Outputs(スタック構築後に出力する値)

ECRを作成するCloudFormation

AWSTemplateFormatVersion: "2010-09-09"
Description: Create ECR Stack Test

Resources:
  ########################################################
  ### ECR Repository
  ########################################################
  TestEcrPoc:
    Type: AWS::ECR::Repository
    Properties:
      RepositoryName: test-ecr-repo

ECSクラスターを作成するCloudFormation

  • ECSクラスターのCloudFormationリファレンスを参考にyamlを記載する。
  • このテンプレートの値をアウトプットして次に作成するテンプレートに読み込ませるように設定する。
  • !Refは指定したパラメータやリソースの値を返す。
AWSTemplateFormatVersion: "2010-09-09"
Description: Create ECS Task Test

Resources:
  ########################################################
  ### ECS Cluster
  ########################################################
  TestEcsCluster:
    Type: "AWS::ECS::Cluster"
    Properties:
      ClusterName: "test-ecs-cls"

  ########################################################
  ###  ECS LogGroup
  ########################################################
  TestEcsLogGroup:
    Type: "AWS::Logs::LogGroup"
    Properties:
      LogGroupName: "/ecs/logs/test-ecs-group"

  ########################################################
  ###  Target Group
  ########################################################
  TestTargetGroup:
    Type: "AWS::ElasticLoadBalancingV2::TargetGroup"
    Properties:
      VpcId: "vpc-11111111111111111"
      Name: "test-target-group"
      Protocol: HTTP
      Port: 80
      TargetType: ip

  ########################################################
  ###  Internet ALB
  ########################################################
  TestInternetAlb:
    Type: "AWS::ElasticLoadBalancingV2::LoadBalancer"
    Properties:
      Name: "test-internet-alb"
      Tags:
        - Key: Name
          Value: "test-internet-alb"
      Scheme: "internet-facing"
      LoadBalancerAttributes:
        - Key: "deletion_protection.enabled"
          Value: false
        - Key: "idle_timeout.timeout_seconds"
          Value: 60
        - Key: "access_logs.s3.enabled"
          Value: true
        - Key: "access_logs.s3.bucket"
          Value: "test-s3b-alb-logs"
      SecurityGroups:
        - "sg-11111111111111111"
      Subnets:
        - "subnet-11111111111111111"
        - "subnet-22222222222222222"

  TestAlbListener:
    Type: "AWS::ElasticLoadBalancingV2::Listener"
    Properties:
      DefaultActions:
        - TargetGroupArn: !Ref TestTargetGroup
          Type: forward
      LoadBalancerArn: !Ref TestInternetAlb
      Port: 80
      Protocol: HTTP

Outputs:
  TestEcsCluster:
    Value: !Ref TestEcsCluster
    Export:
      Name: TestEcsCluster

  TestEcsLogGroup:
    Value: !Ref TestEcsLogGroup
    Export:
      Name: TestEcsLogGroup

  TestTargetGroup:
    Value: !Ref TestTargetGroup
    Export:
      Name: TestTargetGroup

  TestAlbListener:
    Value: !Ref TestAlbListener
    Export:
      Name: TestAlbListener

ECSサービスを作成するCloudFormation

AWSTemplateFormatVersion: "2010-09-09"
Description: Create ECS Task Test

Resources:
  ########################################################
  ###  ECS Task Role
  ########################################################
  TestEcsTaskExecRole:
    Type: "AWS::IAM::Role"
    Properties:
      RoleName: "test-ecs-task-exec-role-policy"
      Path: /
      AssumeRolePolicyDocument:
        Version: 2012-10-17
        Statement:
          - Effect: Allow
            Principal:
              Service: ecs-tasks.amazonaws.com
            Action: sts:AssumeRole
      ManagedPolicyArns:
        - arn:aws:iam::aws:policy/service-role/AmazonECSTaskExecutionRolePolicy

  ########################################################
  ###  ECS TaskDefinition
  ########################################################
  TestEcsTaskDefinition:
    Type: "AWS::ECS::TaskDefinition"
    Properties:
      Cpu: 256
      ExecutionRoleArn: !Ref TestEcsTaskExecRole
      Family: "test-ecs-task"
      Memory: 512
      NetworkMode: awsvpc
      RequiresCompatibilities:
        - FARGATE
      ### ContainerDefinitions
      ContainerDefinitions:
        - Name: "test-ecs-container"
          Image: "111111111111.dkr.ecr.ap-northeast-1.amazonaws.com/test-ecr-repo:latest"
          LogConfiguration:
            LogDriver: awslogs
            Options:
              awslogs-group: !ImportValue TestEcsLogGroup
              awslogs-region: !Ref "AWS::Region"
              awslogs-stream-prefix: "test"
          MemoryReservation: 128
          PortMappings:
            - HostPort: 80
              Protocol: tcp
              ContainerPort: 80

  ########################################################
  ###  ECS Service
  ########################################################
  TestEcsService:
    Type: "AWS::ECS::Service"
    Properties:
      Cluster: !ImportValue TestEcsCluster
      DesiredCount: 1
      LaunchType: FARGATE
      LoadBalancers:
        -
          TargetGroupArn: !ImportValue TestTargetGroup
          ContainerPort: 80
          ContainerName: "test-ecs-container"
      NetworkConfiguration:
        AwsvpcConfiguration:
          AssignPublicIp: ENABLED
          SecurityGroups:
            - "sg-11111111111111111"
          Subnets:
            - "subnet-11111111111111111"
            - "subnet-22222222222222222"
      ServiceName: "test-ecs-service"
      TaskDefinition: !Ref TestEcsTaskDefinition

まとめ

  • CloudFormationでコード化することで環境構築が楽になる。積極的にインフラをコード化していきたい。
  • 基本的にAWSのドキュメントで公開されているリファレンスを参考に組み立てていく。
  • JSON形式よりもYAML形式で記載するほうがコード化しやすい。

参考

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
What you can do with signing up
8