AWS (CloudFormation)

엄경문·2026년 1월 17일

AWS

목록 보기
5/10

들어가며

이번에는 앞에서 했던 실습 내용중에 VPC 를 만들고 서브넷을 만들고 EC2 를 만들었던 내용들을 직접 콘솔로 수행하는것이 아닌 CloudFormation 이라는 Iac 툴을 통해 코드로 만드는것을 실습할 것이다. 이번 실습에서는 yaml 파일을 해석하는 실습보다는 이미 만들어진 파일을 통해 어떻게 AWS 에서 생성되는지 눈으로 직접 확인하며 IaC 구조의 흐름을 보는것을 위주로 진행하였다.

CloudFormation

CloudFormation

CloudFormation 은 Cloud Native IaC Tools 이다.
즉 인프라를 코드로 관리해주는 서비스로 AWS Resource의 생성, 관리, 업데이트를 자동화 한다.
코드를 템플릿 형태로 만들어서 관리하고 템플릿을 통해 STACK을 생성해 코드 내용을 기반으로 인프라를 생성한다.

CloudFormation Template

템플릿은 AWS를 리소스를 코드로 설명하는 텍스트 파일이고 보통 YAML/JSON 형식을 사용

템플릿안에는 보통

  • Parameters: 배포할 때 값만 바꿔 쓰고 싶은 것들(예: 인스턴스 타입 t3.micro 등)
  • Resources: 실제 생성할 AWS 리소스 정의(핵심)
  • Outputs: 생성 결과로 뽑아줄 값(예: ALB DNS, VPC ID)
  • (추가로) Mappings / Conditions / Metadata 같은 보조 요소들

실습

위와 같은 내용을 오픈소스를 이용해서 CloudFormation 으로 실행


ap-northeast-2 Region에 Network Baseline 추가


fiubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code/ap-northeast-2 sudo sh ./"01. vpc_resource.sh"
Creating S3 bucket: lab-edu-bucket-cf-repository-593927188341...
make_bucket: lab-edu-bucket-cf-repository-593927188341
Bucket created successfully.
Uploading './01. vpc_resource.yaml' to s3://lab-edu-bucket-cf-repository-593927188341/network-baseline.yaml...
Completed 193 Bytes/193 Bytes (3.4 KiB/s) with 1 file(s) remainiupload: ./01. vpc_resource.yaml to s3://lab-edu-bucket-cf-repository-593927188341/network-baseline.yaml
File uploaded successfully.
OBJECT_URL: https://lab-edu-bucket-cf-repository-593927188341.s3.amazonaws.com/network-baseline.yaml
ubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code/ap-northeast-2$ 

위 스크립트는 CloudFormation 템플릿 저장용 S3 버킷을 생성해서 VPC 템플릿 파일을 S3에 업로드 한것이다.

yaml 파일을 확인하면

ubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code/ap-northeast-2$ cat 01.\ vpc_resource.yaml 
Resources:
  VPC:
    Type: AWS::EC2::VPC
    Properties:
      CidrBlock: 10.10.0.0/16
      EnableDnsHostnames: true
      Tags:
        - Key: Name
          Value: lab-edu-vpc-ap-02

yaml 파일을 해석하면 CIDR이 10.10.0.0/16 인 VPC 를 만들고 DNS hostname을 켜고, Name 태그를 lab-edu-vpc-ap-02 로 붙이라는 템플릿이다.


CloudFormation 메인 콘솔 화면 → 스택 리소스 탭 → 스택 생성 버튼 클릭

스택이름: lab-edu-cf-network-baseline-ap

이때 vpc를 보면 위에 yaml 파일에서 한거와 같이 vpc가 만들어진다


Parameter Section 활용 Public Subnet 생성

ubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code/ap-northeast-2$ ls
'01. vpc_resource.sh'    '02. subnet_resource.sh'    '03. resource_output.sh'    '04. metadata_parameter_groups.sh'     network_baseline.sh
'01. vpc_resource.yaml'  '02. subnet_resource.yaml'  '03. resource_output.yaml'  '04. metadata_parameter_groups.yaml'   network_baseline.yaml

ubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code/ap-northeast-2$ cat 02.\ subnet_resource.yaml
Parameters:
  VpcCIDR:
    Description: CIDR Block for VPC
    Type: String
    Default: 10.10.0.0/16
  PublicSubnet01CIDR:
    Description: CIDR Block for Publicsubnet01
    Type: String
    Default: 10.10.0.0/24
  PublicSubnet02CIDR:
    Description: CIDR Block for Publicsubnet01
    Type: String
    Default: 10.10.1.0/24

  VpcId:
    Description: ID for VPC
    Type: String
    Default: lab-edu-vpc-ap-02
  PublicSubnet01Id:
    Description: ID for PublicSubnet01
    Type: String
    Default: lab-edu-sub-2nd-pub-01
  PublicSubnet02Id:
    Description: ID for PublicSubnet02
    Type: String
    Default: lab-edu-sub-2nd-pub-02

  AvailabilityZoneSubnet01:
    Description: AvailabilityZone for every First subnet
    Type: AWS::EC2::AvailabilityZone::Name
  AvailabilityZoneSubnet02:
    Description: AvailabilityZone for every Second subnet
    Type: AWS::EC2::AvailabilityZone::Name

Resources:
  VPC:
    Type: AWS::EC2::VPC
    Properties:
      CidrBlock: !Ref VpcCIDR
      EnableDnsHostnames: true
      Tags:
        - Key: Name
          Value: !Ref VpcId
  PublicSubnet01:
    Type: AWS::EC2::Subnet
    Properties:
      VpcId: !Ref VPC
      CidrBlock: !Ref PublicSubnet01CIDR
      AvailabilityZone: !Ref AvailabilityZoneSubnet01
      MapPublicIpOnLaunch: true
      Tags:
        - Key: Name
          Value: !Ref PublicSubnet01Id
  PublicSubnet02:
    Type: AWS::EC2::Subnet
    Properties:
      VpcId: !Ref VPC
      CidrBlock: !Ref PublicSubnet02CIDR
      AvailabilityZone: !Ref AvailabilityZoneSubnet02
      MapPublicIpOnLaunch: true
      Tags:
        - Key: Name
          Value: !Ref PublicSubnet02Id

ubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code/ap-northeast-2$ sudo sh 02.\ subnet_resource.sh 
Uploading './02. subnet_resource.yaml' to s3://lab-edu-bucket-cf-repository-593927188341/network-baseline.yaml...
upload: ./02. subnet_resource.yaml to s3://lab-edu-bucket-cf-repository-593927188341/network-baseline.yaml
File uploaded successfully.
OBJECT_URL: https://lab-edu-bucket-cf-repository-593927188341.s3.amazonaws.com/network-baseline.yaml

위 yaml 은 VPC 1개 퍼블릭 서브넷 2개를 만들고 CIDR/NAME/AZ는 파라미터로 바꿀수있게 해둔 코드이다. 방법은 동일하게 위에서 생성한 S3에 업로드에서 사용한다.

스택 업데이트 → 직접 업데이트

yaml에서 defualt 값이 없으면 사용자가 직접 입력 (적혀있는값은 적혀있는값으로)

업데이트 후 확인해보면
새로운 pub 서브넷이 2개 생긴것을 볼 수 있다.


Output Section 활용 (업데이트를 화면에서 확인)
프라이빗 서브넷, (IGW & Route Table) 만들고 (결과 내보내기)

ubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code/ap-northeast-2$ cat 03.\ resource_output.yaml
Parameters:
  VpcCIDR:
    Description: CIDR Block for VPC
    Type: String
    Default: 10.10.0.0/16
  PublicSubnet01CIDR:
    Description: CIDR Block for Publicsubnet01
    Type: String
    Default: 10.10.0.0/24
  PublicSubnet02CIDR:
    Description: CIDR Block for Publicsubnet01
    Type: String
    Default: 10.10.1.0/24
 .
 .
 .
 .
 .
 .
 


ubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code/ap-northeast-2$ sudo sh 03.\ resource_output.sh 
Uploading './03. resource_output.yaml' to s3://lab-edu-bucket-cf-repository-593927188341/network-baseline.yaml...
upload: ./03. resource_output.yaml to s3://lab-edu-bucket-cf-repository-593927188341/network-baseline.yaml
File uploaded successfully.
OBJECT_URL: https://lab-edu-bucket-cf-repository-593927188341.s3.amazonaws.com/network-baseline.yaml

위 yaml 템플릿은 VPC + Public Subnet 2 + Private Subnet 2 + IGW + Public RouteTable(0.0.0.0/0→IGW) + 각 서브넷 라우팅 연결까지 만들고 마지막에 VPC/서브넷 ID를 Outputs/Export로 뽑아서 다른 스택에서 재사용할 수 있게 해둔 CloudFormation 코드이다.
(yaml 파일자체는 의미적으로만 해석하고 넘김)


Metadatea Section의 ParameterGroups 활용

ubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code/ap-northeast-2$ cat 04.\ metadata_parameter_groups.yaml
AWSTemplateFormatVersion: '2010-09-09'
Description: AWS CloudFormation Natwork Baseline for Education Environment. (Second VPC)
Parameters:
  VpcCIDR:
    Description: CIDR Block for VPC
    Type: String
    Default: 10.10.0.0/16
  PublicSubnet01CIDR:
    Description: CIDR Block for Publicsubnet01
    Type: String
    Default: 10.10.0.0/24
 .
 .
 .
 .
 .
 .
      
 ubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code/ap-northeast-2$ sudo sh 04.\ metadata_parameter_groups.sh 
Uploading './04. metadata_parameter_groups.yaml' to s3://lab-edu-bucket-cf-repository-593927188341/network-baseline.yaml...
upload: ./04. metadata_parameter_groups.yaml to s3://lab-edu-bucket-cf-repository-593927188341/network-baseline.yaml
File uploaded successfully.
OBJECT_URL: https://lab-edu-bucket-cf-repository-593927188341.s3.amazonaws.com/network-baseline.yaml

위 yaml 파일은 VPC(10.10.0.0/16) + Public Subnet 2 + Private Subnet 2 + Database Subnet 2 + TransitGW Subnet 2 를 만들고 IGW + NAT Gateway 2(EIP 2개) 를 구성한 뒤
Public RouteTable(0.0.0.0/0 → IGW) + Private RouteTable(0.0.0.0/0 → NAT) + 각 서브넷 라우팅 테이블 연결(Association) 까지 생성한다.
또한 S3 Gateway Endpoint + STS/SSM 계열 Interface Endpoint 를 Private Subnet에 붙여 내부 통신을 가능하게 하고
마지막에 VPC/서브넷/EC2 Private IP 등을 Outputs/Export로 뽑아 다른 스택에서 Import 해서 재사용할 수 있게 해둔 CloudFormation 코드이다.

aws에서 스택에서 확인 후 업데이트하면 업데이트되는것을 볼 수 있다.

출력에서 확인해보면 의도대로 만들어진것을 볼 수 있다.


us-east-1 Region에 Network Baseline 추가
VS Code 서버에 CloudFormation 실행 권한 할당

ubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code$ ls
ap-northeast-2  eu-central-1  us-east-1
ubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code$ cd us-east-1
ubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code/us-east-1$ ls
attach_iam_policy.sh  create_cloudformation_stack.sh  network_baseline.yaml
ubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code/us-east-1$ cat attach_iam_policy.sh 
#!/bin/bash
aws iam attach-role-policy --role-name lab-edu-role-vscode --policy-arn arn:aws:iam::aws:policy/AWSCloudFormationFullAccess
aws iam attach-role-policy --role-name lab-edu-role-vscode --policy-arn arn:aws:iam::aws:policy/AmazonVPCFullAccess

echo "The attached role policies in lab-edu-role-vscode: "
aws iam list-attached-role-policies --role-name lab-edu-role-vscode

ubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code/us-east-1$ sudo sh ./attach_iam_policy.sh
The attached role policies in lab-edu-role-vscode: 
{
    "AttachedPolicies": [
        {
            "PolicyName": "AmazonEC2FullAccess",
            "PolicyArn": "arn:aws:iam::aws:policy/AmazonEC2FullAccess"
        },
        {
            "PolicyName": "IAMFullAccess",
            "PolicyArn": "arn:aws:iam::aws:policy/IAMFullAccess"
        },
        {
            "PolicyName": "AmazonVPCFullAccess",
            "PolicyArn": "arn:aws:iam::aws:policy/AmazonVPCFullAccess"
        },
        {
            "PolicyName": "AmazonS3FullAccess",
            "PolicyArn": "arn:aws:iam::aws:policy/AmazonS3FullAccess"
        },
        {
            "PolicyName": "AWSCloudFormationFullAccess",
            "PolicyArn": "arn:aws:iam::aws:policy/AWSCloudFormationFullAccess"
        }
    ]
}

이 스크립트는 IAM Role(lab-edu-role-vscode)에 AWSCloudFormationFullAccess + AmazonVPCFullAccess 정책을 attach(연결) 해서
이 Role로 실행되는 AWS CLI가 CloudFormation 스택 생성/관리와 VPC 리소스 생성/수정을 할 수 있게 권한을 추가해주는 쉘 스크립트이다.

버지니아 리전 network_baseline.yaml 배포

ubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code/us-east-1$ sudo sh create_cloudformation_stack.sh
{
    "StackId": "arn:aws:cloudformation:us-east-1:593927188341:stack/lab-edu-cf-network-baseline-us/d8c2e050-f29e-11f0-a639-0affd8af3937",
    "OperationId": "acf5c46d-0616-4c13-b2e7-c2b8b701ac22"
}
CloudFormation stack 'lab-edu-cf-network-baseline-us' created successfully.

aws 콘솔로 버지니아로 들어와서 확인하면

실제로 리소스들을 확인하면 추가된것을 볼 수 있다.


us-east-1 Region에 Network Baseline 추가
프랑크프루트 리전 network_baseline.yaml 배포

ubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code/eu-central-1$ sudo sh create_cloudformation_stack.sh 
{
    "StackId": "arn:aws:cloudformation:eu-central-1:593927188341:stack/lab-edu-cf-network-baseline-us/d7319c80-f29f-11f0-9af0-0a16b282b13d",
    "OperationId": "a160c897-a74b-47f8-b247-fd2194515583"
}
CloudFormation stack 'lab-edu-cf-network-baseline-us' created successfully.
ubuntu@ip-10-0-1-211:/Workshop/support_files/infra_as_a_code/eu-central-1$ cat network_baseline.yaml 
AWSTemplateFormatVersion: '2010-09-09'
Description: AWS CloudFormation Natwork Baseline for Education Environment. (Frankfurt Region VPC)
Parameters:
  VpcCIDR:
    Description: CIDR Block for VPC
    Type: String
    Default: 10.30.0.0/16
  PublicSubnet01CIDR:
    Description: CIDR Block for Publicsubnet01
    Type: String
    Default: 10.30.0.0/24
 .
 .
 .
 .
 .
 .
 

이 작업은 프랑크푸르트 리전(eu-central-1)에 network_baseline.yaml을 CloudFormation으로 배포(스택 생성) 하기 위해 create_cloudformation_stack.sh 스크립트를 실행해서 스택 이름 lab-edu-cf-network-baseline-us로 생성 요청을 보낸 것이다.

위 yaml은 VPC(10.30.0.0/16) + Public Subnet 2 + Private Subnet 2 + Database Subnet 2 + TransitGW Subnet 2 를 만들고 IGW + Public RouteTable(0.0.0.0/0 → IGW) + Public Subnet 라우팅 연결(Association) 까지 구성한다.
추가로 Private/Database/TransitGW 전용 RouteTable을 각각 만들고 각 서브넷에 연결하며
S3 Gateway Endpoint(라우팅테이블에 연결) + STS/SSM 계열 Interface Endpoint(Private Subnet에 생성) + Endpoint용 SG(443,53 허용) 까지 포함해 프라이빗 환경에서도 AWS 서비스 접근이 가능하도록 해둔다.
또한 EC2 2대(WebServer는 PublicSubnet01에 배치 + 80포트 오픈 + UserData로 Streamlit 설치/실행 NetworkServer는 PrivateSubnet01에 배치 + 내부(10.0.0.0/8) 전체 허용 SG) 를 만들고
두 EC2 모두에 붙일 InstanceProfile/Role(SSM + EC2 FullAccess 등 관리형 정책 포함) 을 생성한다.
마지막에 VPC/각 서브넷 ID + WebServer Public IP + NetworkServer Private IP를 Outputs/Export로 뽑아 다른 스택에서 Import해서 재사용할 수 있게 해둔 CloudFormation 코드이다.

프랑크부르트에서도 만들어지는것을 볼 수있다.

작동 방식 (How it works) - 서울리전과 버지니아, 프랑크부르트 차이

마무리

이번 실습에서는 Iac 로 동작하는 흐름을 공부하였다. 완성된 파일 소스를 이용해서 한것이고 yaml 자체는 AI 한테 물어보면 충분히 원하는 yaml 파일을 만들 수 있으므로 이번 실습에서는 yaml 파일에 내용보다는 기본적인 yaml 문법과 yaml 파일을 통해 Iac 로 진행하면 어떤식으로 aws에 만들어지는에 대해 포커스를 맞춰 공부하였다. IaC 라는것에 관심이 생겨서 추후에 프로젝트를 진행할때 테라폼 또는 엔서블을 통해 직접 배포해보고 싶다.

0개의 댓글